mirror of
https://github.com/jambonz/webrtc-client.git
synced 2025-12-19 08:37:45 +00:00
fix multi sessions bug
This commit is contained in:
@@ -5,22 +5,26 @@ import {
|
|||||||
|
|
||||||
export default class SipSessionManager {
|
export default class SipSessionManager {
|
||||||
|
|
||||||
#sessions: SipModel.SipSessionState[];
|
#sessions: Map<string, SipModel.SipSessionState>;
|
||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
this.#sessions = [];
|
this.#sessions = new Map();
|
||||||
}
|
}
|
||||||
|
|
||||||
activate(session: SipSession) {
|
activate(session: SipSession) {
|
||||||
this.#sessions.forEach(state => {
|
this.#sessions.forEach((v, k) => {
|
||||||
if (session.id !== state.id) {
|
if (k !== session.id) {
|
||||||
state.active = false;
|
v.active = false;
|
||||||
session.setActive(false);
|
session.setActive(false);
|
||||||
|
} else {
|
||||||
|
v.active = true;
|
||||||
|
session.setActive(true);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
updateSession(field: string, session: SipSession, args: any): void {
|
updateSession(field: string, session: SipSession, args: any): void {
|
||||||
|
|
||||||
const state: SipModel.SipSessionState = this.getSessionState(session.id);
|
const state: SipModel.SipSessionState = this.getSessionState(session.id);
|
||||||
if (state) {
|
if (state) {
|
||||||
switch (field) {
|
switch (field) {
|
||||||
@@ -30,7 +34,8 @@ export default class SipSessionManager {
|
|||||||
case SipConstants.SESSION_ANSWERED:
|
case SipConstants.SESSION_ANSWERED:
|
||||||
state.status = args.status;
|
state.status = args.status;
|
||||||
break;
|
break;
|
||||||
case SipConstants.SESSION_FAILED || SipConstants.SESSION_ENDED:
|
case SipConstants.SESSION_FAILED:
|
||||||
|
case SipConstants.SESSION_ENDED:
|
||||||
state.status = args.status;
|
state.status = args.status;
|
||||||
state.endState = {
|
state.endState = {
|
||||||
cause: args.cause,
|
cause: args.cause,
|
||||||
@@ -38,6 +43,7 @@ export default class SipSessionManager {
|
|||||||
originator: args.endState,
|
originator: args.endState,
|
||||||
description: args.description
|
description: args.description
|
||||||
}
|
}
|
||||||
|
this.#sessions.delete(session.id);
|
||||||
break;
|
break;
|
||||||
case SipConstants.SESSION_MUTED:
|
case SipConstants.SESSION_MUTED:
|
||||||
state.muteStatus = args.status;
|
state.muteStatus = args.status;
|
||||||
@@ -59,7 +65,7 @@ export default class SipSessionManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
getSessionState(id: string): SipModel.SipSessionState {
|
getSessionState(id: string): SipModel.SipSessionState {
|
||||||
const state = this.#sessions.find(value => value.id === id);
|
const state = this.#sessions.get(id);
|
||||||
if (!state) {
|
if (!state) {
|
||||||
throw new Error("Session not found");
|
throw new Error("Session not found");
|
||||||
}
|
}
|
||||||
@@ -73,27 +79,30 @@ export default class SipSessionManager {
|
|||||||
|
|
||||||
|
|
||||||
newSession(session: SipSession): void {
|
newSession(session: SipSession): void {
|
||||||
this.#sessions.push({
|
this.#sessions.set(session.id,
|
||||||
id: session.id,
|
{
|
||||||
sipSession: session,
|
id: session.id,
|
||||||
startDateTime: new Date(),
|
sipSession: session,
|
||||||
active: true,
|
startDateTime: new Date(),
|
||||||
status: 'init',
|
active: true,
|
||||||
|
status: 'init',
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
get activeSession(): SipSession {
|
get activeSession(): SipSession {
|
||||||
const state = this.#sessions.find(value => value.active);
|
if (this.#sessions.size === 0) {
|
||||||
if (state) {
|
|
||||||
return state.sipSession;
|
|
||||||
}
|
|
||||||
if (this.#sessions.length === 0) {
|
|
||||||
throw new Error("No sessions");
|
throw new Error("No sessions");
|
||||||
}
|
}
|
||||||
return this.#sessions[0].sipSession;
|
|
||||||
|
const state = [...this.#sessions.values()].filter((s) => s.active);
|
||||||
|
if (state.length) {
|
||||||
|
return state[0].sipSession;
|
||||||
|
} else {
|
||||||
|
throw new Error("No Active sessions");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
get count() {
|
get count() {
|
||||||
return this.#sessions.length;
|
return this.#sessions.size;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -51,20 +51,25 @@ export default class SipUA extends events.EventEmitter {
|
|||||||
const rtcSession: RTCSession = data.session;
|
const rtcSession: RTCSession = data.session;
|
||||||
const session: SipSession = new SipSession(rtcSession, this.#rtcConfig, new SipAudioElements());
|
const session: SipSession = new SipSession(rtcSession, this.#rtcConfig, new SipAudioElements());
|
||||||
this.#sessionManager.newSession(session);
|
this.#sessionManager.newSession(session);
|
||||||
session.on(SipConstants.SESSION_RINGING, args => this.#sessionManager.updateSession(SipConstants.SESSION_RINGING, session, args));
|
session.on(SipConstants.SESSION_RINGING, args => this.updateSession(SipConstants.SESSION_RINGING, session, args, client));
|
||||||
session.on(SipConstants.SESSION_ANSWERED, args => this.#sessionManager.updateSession(SipConstants.SESSION_ANSWERED, session, args));
|
session.on(SipConstants.SESSION_ANSWERED, args => this.updateSession(SipConstants.SESSION_ANSWERED, session, args, client));
|
||||||
session.on(SipConstants.SESSION_FAILED, args => this.#sessionManager.updateSession(SipConstants.SESSION_FAILED, session, args));
|
session.on(SipConstants.SESSION_FAILED, args => this.updateSession(SipConstants.SESSION_FAILED, session, args, client));
|
||||||
session.on(SipConstants.SESSION_ENDED, args => this.#sessionManager.updateSession(SipConstants.SESSION_ENDED, session, args));
|
session.on(SipConstants.SESSION_ENDED, args => this.updateSession(SipConstants.SESSION_ENDED, session, args, client));
|
||||||
session.on(SipConstants.SESSION_MUTED, args => this.#sessionManager.updateSession(SipConstants.SESSION_MUTED, session, args));
|
session.on(SipConstants.SESSION_MUTED, args => this.updateSession(SipConstants.SESSION_MUTED, session, args, client));
|
||||||
session.on(SipConstants.SESSION_HOLD, args => this.#sessionManager.updateSession(SipConstants.SESSION_HOLD, session, args));
|
session.on(SipConstants.SESSION_HOLD, args => this.updateSession(SipConstants.SESSION_HOLD, session, args, client));
|
||||||
session.on(SipConstants.SESSION_ICE_READY, args => this.#sessionManager.updateSession(SipConstants.SESSION_ICE_READY, session, args));
|
session.on(SipConstants.SESSION_ICE_READY, args => this.updateSession(SipConstants.SESSION_ICE_READY, session, args, client));
|
||||||
session.on(SipConstants.SESSION_ACTIVE, args => {
|
session.on(SipConstants.SESSION_ACTIVE, args => {
|
||||||
this.#sessionManager.updateSession(SipConstants.SESSION_ACTIVE, session, args);
|
this.updateSession(SipConstants.SESSION_ACTIVE, session, args, client);
|
||||||
});
|
});
|
||||||
session.setActive(true);
|
session.setActive(true);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
updateSession(field: string, session: SipSession, args: any, client: SipModel.ClientAuth) {
|
||||||
|
this.emit(field, {...args, client});
|
||||||
|
this.#sessionManager.updateSession(field, session, args);
|
||||||
|
}
|
||||||
|
|
||||||
start(): void {
|
start(): void {
|
||||||
this.#ua.start();
|
this.#ua.start();
|
||||||
this.emit(SipConstants.UA_START);
|
this.emit(SipConstants.UA_START);
|
||||||
|
|||||||
@@ -2,6 +2,9 @@ import {LitElement, html, css} from 'lit-element';
|
|||||||
import {SipUA} from "../lib";
|
import {SipUA} from "../lib";
|
||||||
import {SipConstants} from "../lib";
|
import {SipConstants} from "../lib";
|
||||||
|
|
||||||
|
const CALL_LABEL = "Call";
|
||||||
|
const CALLING_LABEL = "Dialing...";
|
||||||
|
const HANGUP_LABEL = "Hang Up";
|
||||||
class Phone extends LitElement {
|
class Phone extends LitElement {
|
||||||
static styles = css`
|
static styles = css`
|
||||||
.number-display {
|
.number-display {
|
||||||
@@ -76,7 +79,9 @@ class Phone extends LitElement {
|
|||||||
static get properties() {
|
static get properties() {
|
||||||
return {
|
return {
|
||||||
props: {type: Object},
|
props: {type: Object},
|
||||||
toNumber: {type: String}
|
toNumber: {type: String},
|
||||||
|
callButtionLabel: {type: String},
|
||||||
|
isButtonDisabled: { type: Boolean }
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -85,6 +90,8 @@ class Phone extends LitElement {
|
|||||||
this.props = {};
|
this.props = {};
|
||||||
this.toNumber = '';
|
this.toNumber = '';
|
||||||
this.sipClient = this._createSipClient();
|
this.sipClient = this._createSipClient();
|
||||||
|
this.callButtionLabel = CALL_LABEL;
|
||||||
|
this.isButtonDisabled = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
@@ -121,8 +128,8 @@ class Phone extends LitElement {
|
|||||||
})}
|
})}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<button class="call-button" @click="${this._handleCall}">
|
<button class="call-button" ${this.isButtonDisabled ? "disabled" : ""} @click="${this._handleCall}">
|
||||||
Call
|
${this.callButtionLabel}
|
||||||
</button>
|
</button>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
@@ -130,15 +137,15 @@ class Phone extends LitElement {
|
|||||||
_createSipClient() {
|
_createSipClient() {
|
||||||
|
|
||||||
const client = {
|
const client = {
|
||||||
username: "xxx@jambonz.org",
|
username: "abcs@hoan.jambonz.one",
|
||||||
password: "1234",
|
password: "123457",
|
||||||
name: "Antony Jukes"
|
name: "Hoan HL"
|
||||||
}
|
}
|
||||||
const settings = {
|
const settings = {
|
||||||
pcConfig: {
|
pcConfig: {
|
||||||
iceServers: [{urls: ['stun:stun.l.google.com:19302']}],
|
iceServers: [{urls: ['stun:stun.l.google.com:19302']}],
|
||||||
},
|
},
|
||||||
wsUri: "wss://foo.jambonz.org:8443",
|
wsUri: "wss://jambonz.org:8443",
|
||||||
};
|
};
|
||||||
const sipUA = new SipUA(client, settings);
|
const sipUA = new SipUA(client, settings);
|
||||||
sipUA.on(SipConstants.UA_CONNECTING, args => {
|
sipUA.on(SipConstants.UA_CONNECTING, args => {
|
||||||
@@ -146,20 +153,40 @@ class Phone extends LitElement {
|
|||||||
});
|
});
|
||||||
sipUA.on(SipConstants.UA_REGISTERED, args => {
|
sipUA.on(SipConstants.UA_REGISTERED, args => {
|
||||||
console.log(SipConstants.UA_REGISTERED, args);
|
console.log(SipConstants.UA_REGISTERED, args);
|
||||||
|
this.isButtonDisabled = false;
|
||||||
});
|
});
|
||||||
sipUA.on(SipConstants.UA_UNREGISTERED, args => {
|
sipUA.on(SipConstants.UA_UNREGISTERED, args => {
|
||||||
console.log(SipConstants.UA_UNREGISTERED, args);
|
console.log(SipConstants.UA_UNREGISTERED, args);
|
||||||
|
this.isButtonDisabled = true;
|
||||||
|
});
|
||||||
|
sipUA.on(SipConstants.SESSION_ANSWERED, args => {
|
||||||
|
console.log(SipConstants.SESSION_ANSWERED, args);
|
||||||
|
this.callButtionLabel = HANGUP_LABEL;
|
||||||
|
});
|
||||||
|
sipUA.on(SipConstants.SESSION_ENDED, args => {
|
||||||
|
console.log(SipConstants.SESSION_ENDED, args);
|
||||||
|
this.callButtionLabel = CALL_LABEL;
|
||||||
});
|
});
|
||||||
sipUA.start();
|
sipUA.start();
|
||||||
|
|
||||||
|
return sipUA;
|
||||||
}
|
}
|
||||||
|
|
||||||
_handleClick(num) {
|
_handleClick(num) {
|
||||||
this.toNumber += num;
|
this.toNumber += num;
|
||||||
|
if (this.callButtionLabel !== CALL_LABEL) {
|
||||||
|
this.sipClient.dtmf(num);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_handleCall() {
|
_handleCall() {
|
||||||
console.log(`Calling...`);
|
if (this.callButtionLabel === CALL_LABEL) {
|
||||||
this.sipClient.call(this.toNumber, '121241231');
|
this.callButtionLabel = CALLING_LABEL;
|
||||||
|
this.sipClient.call(this.toNumber);
|
||||||
|
} else {
|
||||||
|
this.sipClient.terminate(480, "Finished Call");
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
_handleInput(event) {
|
_handleInput(event) {
|
||||||
|
|||||||
Reference in New Issue
Block a user