Each time a message is received from the WebSocket, I aim to update the properties totalRequests
, payloadSize
, and payloadSizeType
. The console logs confirm that these values are being updated correctly. However, the issue lies in the fact that my template fails to reflect these changes.
I have ruled out any underlying errors by testing a function that manually updates the values on click, resulting in the template reflecting these changes. Thus, it seems that the problem may lie in how I am passing the WS callbacks...unless there is another factor at play that I am not aware of.
import { Component, OnInit } from '@angular/core';
import { AttackService } from './attack.service';
import { WebSocketService } from '../../../lib/service/websocket/websocket.service';
import { WebSocketConfig } from '../../../lib/service/websocket/websocket.config';
@Component({
selector: 'attack',
templateUrl: './attack.component.html',
styleUrls: ['./attack.component.css'],
providers: [AttackService, WebSocketService]
})
export class AttackComponent implements OnInit {
private model: Object = {
url: "http://localhost",
kb_per_request: 5,
duration: 5
};
private hasReceivedMessage: boolean = false;
private totalRequests: number = 0;
private payloadSize: number = 0;
private payloadSizeType: string = 'KB';
constructor(private attackService: AttackService, private socket: WebSocketService) {}
ngOnInit(): void {
this.socket.create(new WebSocketConfig(this.sOnOpen, this.sOnClose, this.sOnMessage, this.sOnError));
}
sOnOpen(): void {
console.log('WebSocket connection successfully established.');
}
sOnClose(code: number): void {
console.log(`WebSocket connection closed (${code}).`);
}
sOnMessage(data: any): void {
this.hasReceivedMessage = true;
this.totalRequests = data.total_requests;
this.payloadSize = data.payload_size;
this.payloadSizeType = data.payload_size_type;
console.log('====================================');
console.log('Total requests: ', this.totalRequests);
console.log('Payload size: ', this.payloadSize);
console.log('Payload type: ', this.payloadSizeType);
}
sOnError(data: any): void {
console.log('WebSocket error occurred: ', data);
}
submit(): void {
this.attackService.attack(this.model).subscribe(
res => {
let data = res.json();
if (data.success) {
console.log(data.message);
}
},
err => {
console.log('Error:', err);
}
);
}
}
Initially, I suspected that the methods were passed with an incorrect this
context. Even after binding the correct context, the template still does not reflect the changes.
constructor(private attackService: AttackService, private socket: WebSocketService) {
this.sOnOpen = this.sOnOpen.bind(this);
this.sOnClose = this.sOnClose.bind(this);
this.sOnMessage = this.sOnMessage.bind(this);
this.sOnError = this.sOnError.bind(this);
}
If anyone has a solution to this issue, please share.
UPDATE:
WebSocketService:
import { Injectable } from '@angular/core';
import { WebSocketConfig } from './websocket.config';
@Injectable()
export class WebSocketService {
private socket = null;
private uri = "ws://localhost:80/ws";
create(config: WebSocketConfig): void {
window.onload = () => {
this.socket = new WebSocket(this.uri);
this.socket.onopen = config.onOpen;
this.socket.onclose = config.onClose;
this.socket.onmessage = res => config.onMessage(JSON.parse(res.data));
this.socket.onerror = config.onError;
};
}
send(data: any): void {
this.socket.send(data);
}
}