Browse Source

feat: restart Jingle session on ICE failed

If ICE fails will set the special request restart attribute
in the 'session-terminate' sent to Jicofo in order to restart
the Jingle session.
dev1
paweldomas 4 years ago
parent
commit
ca6b08a775

+ 29
- 3
modules/connectivity/IceFailedHandling.js View File

33
      * @returns {void}
33
      * @returns {void}
34
      */
34
      */
35
     _actOnIceFailed() {
35
     _actOnIceFailed() {
36
-        if (!this._conference.options.config.enableIceRestart) {
36
+        const { enableIceRestart } = this._conference.options.config;
37
+        const explicitlyDisabled = typeof enableIceRestart !== 'undefined' && !enableIceRestart;
38
+        const supportsRestartByTerminate = this._conference.room.supportsRestartByTerminate();
39
+        const useTerminateForRestart = supportsRestartByTerminate && !enableIceRestart;
40
+
41
+        logger.info('ICE failed,'
42
+            + ` enableIceRestart: ${enableIceRestart},`
43
+            + ` supports restart by terminate: ${supportsRestartByTerminate}`);
44
+
45
+        if (explicitlyDisabled || (!enableIceRestart && !supportsRestartByTerminate)) {
37
             logger.info('ICE failed, but ICE restarts are disabled');
46
             logger.info('ICE failed, but ICE restarts are disabled');
38
             this._conference.eventEmitter.emit(
47
             this._conference.eventEmitter.emit(
39
                 JitsiConferenceEvents.CONFERENCE_FAILED,
48
                 JitsiConferenceEvents.CONFERENCE_FAILED,
50
         } else if (jvbConnIceState === 'connected') {
59
         } else if (jvbConnIceState === 'connected') {
51
             logger.info('ICE connection restored - not sending ICE failed');
60
             logger.info('ICE connection restored - not sending ICE failed');
52
         } else {
61
         } else {
53
-            logger.info(`Sending ICE failed - the connection has not recovered: ${jvbConnIceState}`);
54
-            jvbConnection.sendIceFailedNotification();
62
+            logger.info('Sending ICE failed - the connection did not recover, '
63
+                + `ICE state: ${jvbConnIceState}, `
64
+                + `use 'session-terminate': ${useTerminateForRestart}`);
65
+            if (useTerminateForRestart) {
66
+                this._conference.jvbJingleSession.terminate(
67
+                    () => {
68
+                        logger.info('session-terminate for ice restart - done');
69
+                    },
70
+                    error => {
71
+                        logger.error(`session-terminate for ice restart - error: ${error.message}`);
72
+                    }, {
73
+                        reason: 'connectivity-error',
74
+                        reasonDescription: 'ICE FAILED',
75
+                        requestRestart: true,
76
+                        sendSessionTerminate: true
77
+                    });
78
+            } else {
79
+                this._conference.jvbJingleSession.sendIceFailedNotification();
80
+            }
55
         }
81
         }
56
     }
82
     }
57
 
83
 

+ 35
- 0
modules/connectivity/IceFailedHandling.spec.js View File

33
             // eslint-disable-next-line no-empty-function
33
             // eslint-disable-next-line no-empty-function
34
             emit: () => { }
34
             emit: () => { }
35
         };
35
         };
36
+        mockConference.room = {
37
+            supportsRestartByTerminate: () => false
38
+        };
36
         mockConference.xmpp = {
39
         mockConference.xmpp = {
37
             ping: () => Promise.resolve()
40
             ping: () => Promise.resolve()
38
         };
41
         };
112
                 });
115
                 });
113
         });
116
         });
114
     });
117
     });
118
+    describe('if Jingle session restarts are supported', () => {
119
+        let sendSessionTerminateSpy;
120
+
121
+        beforeEach(() => {
122
+            mockConference.options.config.enableIceRestart = undefined;
123
+            mockConference.room = {
124
+                supportsRestartByTerminate: () => true
125
+            };
126
+            mockConference.jvbJingleSession = {
127
+                getIceConnectionState: () => 'failed',
128
+                // eslint-disable-next-line no-empty-function
129
+                terminate: () => { }
130
+            };
131
+            sendSessionTerminateSpy = spyOn(mockConference.jvbJingleSession, 'terminate');
132
+        });
133
+        it('send "session-terminate" with the request restart attribute', () => {
134
+            iceFailedHandling.start();
135
+
136
+            return nextTick() // tick for ping
137
+                .then(() => nextTick(2500)) // tick for ice timeout
138
+                .then(() => {
139
+                    expect(sendSessionTerminateSpy).toHaveBeenCalledWith(
140
+                        jasmine.any(Function),
141
+                        jasmine.any(Function), {
142
+                            reason: 'connectivity-error',
143
+                            reasonDescription: 'ICE FAILED',
144
+                            requestRestart: true,
145
+                            sendSessionTerminate: true
146
+                        });
147
+                });
148
+        });
149
+    });
115
 });
150
 });

+ 16
- 0
modules/xmpp/ChatRoom.js View File

761
         this.focusMucJid = from;
761
         this.focusMucJid = from;
762
 
762
 
763
         logger.info(`Ignore focus: ${from}, real JID: ${mucJid}`);
763
         logger.info(`Ignore focus: ${from}, real JID: ${mucJid}`);
764
+        this.xmpp.caps.getFeatures(mucJid, 15000).then(features => {
765
+            this.focusFeatures = features;
766
+            logger.info(`Jicofo supports restart by terminate: ${this.supportsRestartByTerminate()}`);
767
+        }, error => {
768
+            logger.error('Failed to discover Jicofo features', error && error.message);
769
+        });
764
     }
770
     }
765
 
771
 
766
     /**
772
     /**
771
         this.participantPropertyListener = listener;
777
         this.participantPropertyListener = listener;
772
     }
778
     }
773
 
779
 
780
+    /**
781
+     * Checks if Jicofo supports restarting Jingle session after 'session-terminate'.
782
+     * @returns {boolean}
783
+     */
784
+    supportsRestartByTerminate() {
785
+        return this.focusFeatures
786
+            ? this.focusFeatures.has('https://jitsi.org/meet/jicofo/terminate-restart')
787
+            : false;
788
+    }
789
+
774
     /**
790
     /**
775
      *
791
      *
776
      * @param node
792
      * @param node

Loading…
Cancel
Save