68 lines
2.2 KiB
TypeScript
68 lines
2.2 KiB
TypeScript
import type { ISignalingClient } from '../interfaces/ISignalingClient';
|
|
import type { IPeerConnectionOperations } from '../interfaces/IPeerConnectionOperations';
|
|
import type { ILogger } from '@techniker-me/logger';
|
|
import { LoggerFactory } from '@techniker-me/logger';
|
|
|
|
/**
|
|
* Caller class - responsible for initiating WebRTC calls
|
|
* Follows Single Responsibility Principle - only handles offer creation flow
|
|
* Follows Dependency Inversion Principle - depends on abstractions (interfaces)
|
|
*/
|
|
export class Caller {
|
|
private readonly _logger: ILogger = LoggerFactory.getLogger('Caller');
|
|
private readonly _signalingClient: ISignalingClient;
|
|
private readonly _peerConnection: IPeerConnectionOperations;
|
|
|
|
constructor(
|
|
signalingClient: ISignalingClient,
|
|
peerConnection: IPeerConnectionOperations
|
|
) {
|
|
this._signalingClient = signalingClient;
|
|
this._peerConnection = peerConnection;
|
|
}
|
|
|
|
/**
|
|
* Create and send an offer following the sequence diagram:
|
|
* 1. Create Offer
|
|
* 2. Set local description to offer
|
|
* 3. Send Offer to signaling server
|
|
*/
|
|
public async createAndSendOffer(): Promise<void> {
|
|
try {
|
|
this._logger.info('Creating offer...');
|
|
|
|
// Step 1: Create Offer
|
|
const offer = await this._peerConnection.createOffer();
|
|
|
|
// Step 2: Set local description to offer
|
|
await this._peerConnection.setLocalDescription(offer);
|
|
this._logger.info('Local description set to offer');
|
|
|
|
// Step 3: Send Offer to signaling server
|
|
await this._signalingClient.sendOffer(offer);
|
|
this._logger.info('Offer sent to signaling server');
|
|
} catch (error) {
|
|
this._logger.error('Failed to create and send offer', error);
|
|
throw error;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Handle receiving an answer from the callee
|
|
* Sets the answer as remote description
|
|
*/
|
|
public async handleAnswer(answer: RTCSessionDescriptionInit): Promise<void> {
|
|
try {
|
|
this._logger.info('Handling answer from callee...');
|
|
|
|
// Set Answer as remote description
|
|
await this._peerConnection.setRemoteDescription(answer);
|
|
this._logger.info('Answer set as remote description');
|
|
} catch (error) {
|
|
this._logger.error('Failed to handle answer', error);
|
|
throw error;
|
|
}
|
|
}
|
|
}
|
|
|