From ea31b0018ce93b0db502fd25628716106383bb40 Mon Sep 17 00:00:00 2001 From: Jiri Mencak Date: Sun, 6 Dec 2020 10:40:53 +0100 Subject: [PATCH 01/24] Partial revert of Special chars sanitization. https://github.com/edumeet/edumeet/commit/540eaff37d475bdc07d0998e29f7e7c0580e0b93 Correctly replaced encodeURI() by encodeURIComponent() in ChooseRoom.js and JoinDialog.js. However, the new code added in server.js caused an extra issue: https://github.com/edumeet/edumeet/issues/634 As entering the rooms with special characters (e.g. @) seems to work without issues with just s/encodeURI/encodeURIComponent/ remove the problematic code. --- server/server.js | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/server/server.js b/server/server.js index 77323018..a348fe14 100755 --- a/server/server.js +++ b/server/server.js @@ -620,20 +620,7 @@ async function runHttpsServer() res.redirect(ltiURL); } else - { - const specialChars = "<>@!^*()[]{}:;|'\"\\,~`"; - - for (let i = 0; i < specialChars.length; i++) - { - if (req.url.substring(1).indexOf(specialChars[i]) > -1) - { - req.url = `/${encodeURIComponent(encodeURI(req.url.substring(1)))}`; - res.redirect(`${req.url}`); - } - } - return next(); - } } else res.redirect(`https://${req.hostname}${req.url}`); From 6ecafd8e178a73870942c51f3fdc9878771e2c22 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Fri, 18 Dec 2020 10:10:50 +0100 Subject: [PATCH 02/24] Added setting of a local picture to display if no video is sent --- app/package.json | 4 +- app/src/RoomClient.js | 22 +++++- app/src/actions/settingsActions.js | 7 +- app/src/components/Containers/Me.js | 6 ++ app/src/components/Containers/Peer.js | 22 +++++- app/src/components/Controls/TopBar.js | 12 +-- app/src/components/JoinDialog.js | 23 ++---- app/src/components/Settings/MediaSettings.js | 83 ++++++++++++++++++++ app/src/reducers/settings.js | 8 ++ app/src/translations/cn.json | 4 + app/src/translations/cs.json | 4 + app/src/translations/de.json | 4 + app/src/translations/dk.json | 4 + app/src/translations/el.json | 4 + app/src/translations/en.json | 4 + app/src/translations/es.json | 4 + app/src/translations/fr.json | 4 + app/src/translations/hi.json | 4 + app/src/translations/hr.json | 4 + app/src/translations/hu.json | 4 + app/src/translations/it.json | 4 + app/src/translations/kk.json | 4 + app/src/translations/lv.json | 4 + app/src/translations/nb.json | 4 + app/src/translations/pl.json | 4 + app/src/translations/pt.json | 4 + app/src/translations/ro.json | 4 + app/src/translations/ru.json | 4 + app/src/translations/tr.json | 4 + app/src/translations/tw.json | 4 + app/src/translations/uk.json | 4 + server/package.json | 2 +- 32 files changed, 246 insertions(+), 31 deletions(-) diff --git a/app/package.json b/app/package.json index 4a82bd0b..58d422c5 100644 --- a/app/package.json +++ b/app/package.json @@ -29,7 +29,7 @@ "is-electron": "^2.2.0", "marked": "^0.8.0", "material-ui-popup-state": "^1.7.0", - "mediasoup-client": "^3.6.5", + "mediasoup-client": "^3.6.21", "notistack": "^0.9.5", "prop-types": "^15.7.2", "random-string": "^0.2.0", @@ -37,6 +37,8 @@ "react-cookie-consent": "^2.5.0", "react-dom": "^16.10.2", "react-flip-toolkit": "^7.0.9", + "react-image-file-resizer": "^0.3.8", + "react-images-upload": "^1.2.0", "react-intl": "^3.4.0", "react-intl-redux": "^2.2.0", "react-redux": "^7.1.1", diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index 4cb33c14..6a74ee1a 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -259,6 +259,10 @@ export default class RoomClient this.setLocale(store.getState().intl.locale); + if (store.getState().settings.localPicture) + { + store.dispatch(meActions.setPicture(store.getState().settings.localPicture)); + } } close() @@ -542,6 +546,13 @@ export default class RoomClient } + setPicture(picture) + { + store.dispatch(settingsActions.setLocalPicture(picture)); + store.dispatch(meActions.setPicture(picture)); + this.changePicture(picture); + } + receiveLoginChildWindow(data) { logger.debug('receiveFromChildWindow() | [data:"%o"]', data); @@ -549,7 +560,11 @@ export default class RoomClient const { displayName, picture } = data; store.dispatch(settingsActions.setDisplayName(displayName)); - store.dispatch(meActions.setPicture(picture)); + + if (!store.getState().settings.localPicture) + { + store.dispatch(meActions.setPicture(picture)); + } store.dispatch(meActions.loggedIn(true)); @@ -566,7 +581,10 @@ export default class RoomClient { logger.debug('receiveLogoutChildWindow()'); - store.dispatch(meActions.setPicture(null)); + if (!store.getState().settings.localPicture) + { + store.dispatch(meActions.setPicture(null)); + } store.dispatch(meActions.loggedIn(false)); diff --git a/app/src/actions/settingsActions.js b/app/src/actions/settingsActions.js index 28a8c71a..50a72b40 100644 --- a/app/src/actions/settingsActions.js +++ b/app/src/actions/settingsActions.js @@ -149,4 +149,9 @@ export const setVideoMuted = (videoMuted) => ({ type : 'SET_VIDEO_MUTED', payload : { videoMuted } - }); \ No newline at end of file + }); +export const setLocalPicture = (localPicture) => + ({ + type : 'SET_LOCAL_PICTURE', + payload : { localPicture } + }); diff --git a/app/src/components/Containers/Me.js b/app/src/components/Containers/Me.js index 93d7cb7c..3437a1b6 100644 --- a/app/src/components/Containers/Me.js +++ b/app/src/components/Containers/Me.js @@ -316,6 +316,12 @@ const Me = (props) => 'margin' : spacing }; + if (me.picture) + { + spacingStyle.backgroundImage = `url(${me.picture})`; + spacingStyle.backgroundSize = 'auto 100%'; + } + let audioScore = null; if (micProducer && micProducer.score) diff --git a/app/src/components/Containers/Peer.js b/app/src/components/Containers/Peer.js index c81627bc..19ae2026 100644 --- a/app/src/components/Containers/Peer.js +++ b/app/src/components/Containers/Peer.js @@ -110,6 +110,15 @@ const styles = (theme) => alignItems : 'center', padding : theme.spacing(1), zIndex : 20, + '&.hide' : + { + transition : 'opacity 0.1s ease-in-out', + opacity : 0 + }, + '&.hover' : + { + opacity : 1 + }, '& p' : { padding : '6px 12px', @@ -176,6 +185,12 @@ const Peer = (props) => ...style }; + if (peer.picture) + { + rootStyle.backgroundImage = `url(${peer.picture})`; + rootStyle.backgroundSize = 'auto 100%'; + } + return (
>
{ !videoVisible && -
+

loggedIn ? roomClient.logout() : roomClient.login(); }} > - { myPicture ? - - : - - } + } @@ -692,11 +688,7 @@ const TopBar = (props) => loggedIn ? roomClient.logout() : roomClient.login(); }} > - { myPicture ? - - : - - } + { loggedIn ?

roomClient.login(roomId) } > - { myPicture ? - - : - - } + diff --git a/app/src/components/Settings/MediaSettings.js b/app/src/components/Settings/MediaSettings.js index b6eb8404..aacb2d7c 100644 --- a/app/src/components/Settings/MediaSettings.js +++ b/app/src/components/Settings/MediaSettings.js @@ -21,6 +21,11 @@ import ListItemText from '@material-ui/core/ListItemText'; import ExpandLess from '@material-ui/icons/ExpandLess'; import ExpandMore from '@material-ui/icons/ExpandMore'; import Switch from '@material-ui/core/Switch'; +import ImageUploader from 'react-images-upload'; +import Resizer from 'react-image-file-resizer'; +import Logger from '../../Logger'; + +const logger = new Logger('MediaSettings'); const NoiseSlider = withStyles( { @@ -98,6 +103,30 @@ const MediaSettings = ({ const [ audioSettingsOpen, setAudioSettingsOpen ] = React.useState(false); const [ videoSettingsOpen, setVideoSettingsOpen ] = React.useState(false); + const onDrop = (picture) => + { + if (picture.length > 0) + { + Resizer.imageFileResizer(picture[0], 1280, 720, 'JPEG', 99, 0, + (uri) => + { + const reader = new FileReader(); + + reader.addEventListener('load', () => + { + roomClient.setPicture(reader.result); + }); + + reader.readAsDataURL(uri); + }, + 'blob'); + } + else + { + roomClient.setPicture(null); + } + }; + const resolutions = [ { value : 'low', label : intl.formatMessage({ @@ -159,6 +188,32 @@ const MediaSettings = ({

+ + { + if (event.target.value) + roomClient.updateWebcam({ newResolution: event.target.value }); + }} + name='Video resolution' + autoWidth + className={classes.selectEmpty} + > + {resolutions.map((resolution, index) => + { + return ( + + {resolution.label} + + ); + })} + + + + + setVideoSettingsOpen(!videoSettingsOpen)}> return { ...state, videoMuted }; } + case 'SET_LOCAL_PICTURE': + { + const { localPicture } = action.payload; + + return { ...state, localPicture }; + } + default: return state; } diff --git a/app/src/translations/cn.json b/app/src/translations/cn.json index 5f7ea044..4102adc0 100644 --- a/app/src/translations/cn.json +++ b/app/src/translations/cn.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "无法保存文件", "filesharing.startingFileShare": "正在尝试共享文件", diff --git a/app/src/translations/cs.json b/app/src/translations/cs.json index 349cc469..5825d026 100644 --- a/app/src/translations/cs.json +++ b/app/src/translations/cs.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Mezní hodnota hluku", "settings.mirrorOwnVideo": "Zrcadlové zobrazení vlastního videa", "settings.language": "Vyberte jazyk", + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Není možné uložit soubor", "filesharing.startingFileShare": "Pokouším se sdílet soubor", diff --git a/app/src/translations/de.json b/app/src/translations/de.json index bfc4ead0..aaa8d713 100644 --- a/app/src/translations/de.json +++ b/app/src/translations/de.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Geräuschepegel", "settings.mirrorOwnVideo": "Ansicht des eigenen Videos spiegeln", "settings.language": "Sprache auswählen", + "settings.myPhotoButton": "Mein Foto festlegen", + "settings.myPhotoLabel": "Maximale Dateigröße: 5MB, akzeptiert: jpg, jpeg, png", + "settings.myPhotoSizeError": " Datei ist zu groß", + "settings.myPhotoTypeError": " ist keine unterstützte Dateierweiterung", "filesharing.saveFileError": "Fehler beim Speichern der Datei", "filesharing.startingFileShare": "Starte Teilen der Datei", diff --git a/app/src/translations/dk.json b/app/src/translations/dk.json index 19f23710..f06a97fe 100644 --- a/app/src/translations/dk.json +++ b/app/src/translations/dk.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Kan ikke gemme fil", "filesharing.startingFileShare": "Forsøger at dele filen", diff --git a/app/src/translations/el.json b/app/src/translations/el.json index 5968466b..c60edea2 100644 --- a/app/src/translations/el.json +++ b/app/src/translations/el.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Αδυναμία αποθήκευσης του αρχείου", "filesharing.startingFileShare": "Προσπάθεια διαμοιρασμού αρχείου", diff --git a/app/src/translations/en.json b/app/src/translations/en.json index 01489b7c..c8261f2a 100644 --- a/app/src/translations/en.json +++ b/app/src/translations/en.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Noise threshold", "settings.mirrorOwnVideo": "Mirror view of own video", "settings.language": "Select language", + "settings.myPhotoButton": "Set my photo", + "settings.myPhotoLabel": "Max. file size: 5MB, accepted: jpg, jpeg, png", + "settings.myPhotoSizeError": " file is too large", + "settings.myPhotoTypeError": " is not a supported file extension", "filesharing.saveFileError": "Unable to save file", "filesharing.startingFileShare": "Attempting to share file", diff --git a/app/src/translations/es.json b/app/src/translations/es.json index de3b2802..35f4100b 100644 --- a/app/src/translations/es.json +++ b/app/src/translations/es.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "No ha sido posible guardar el fichero", "filesharing.startingFileShare": "Intentando compartir el fichero", diff --git a/app/src/translations/fr.json b/app/src/translations/fr.json index 0265b044..4ba7dbc0 100644 --- a/app/src/translations/fr.json +++ b/app/src/translations/fr.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Impossible d'enregistrer le fichier", "filesharing.startingFileShare": "Début du transfert de fichier", diff --git a/app/src/translations/hi.json b/app/src/translations/hi.json index 6b6ebd1d..035a7742 100644 --- a/app/src/translations/hi.json +++ b/app/src/translations/hi.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "शोर सीमा", "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "फ़ाइल सहेजने में असमर्थ", "filesharing.startingFileShare": "फ़ाइल के आदान-प्रदान का प्रयास है", diff --git a/app/src/translations/hr.json b/app/src/translations/hr.json index c8e4d644..c13371d8 100644 --- a/app/src/translations/hr.json +++ b/app/src/translations/hr.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Nije moguće spremiti datoteku", "filesharing.startingFileShare": "Pokušaj dijeljenja datoteke", diff --git a/app/src/translations/hu.json b/app/src/translations/hu.json index 72e30b33..00f0a486 100644 --- a/app/src/translations/hu.json +++ b/app/src/translations/hu.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Zajszint", "settings.mirrorOwnVideo": "Saját videókép tükrözése", "settings.language": "Nyelv", + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "A file-t nem sikerült elmenteni", "filesharing.startingFileShare": "Fájl megosztása", diff --git a/app/src/translations/it.json b/app/src/translations/it.json index 7fdf48ce..b093d0bf 100644 --- a/app/src/translations/it.json +++ b/app/src/translations/it.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Soglia di rumore", "settings.mirrorOwnVideo": "Specchiare il proprio video", "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Impossibile salvare file", "filesharing.startingFileShare": "Tentativo di condivisione file", diff --git a/app/src/translations/kk.json b/app/src/translations/kk.json index e3b61fe1..ebc405bc 100644 --- a/app/src/translations/kk.json +++ b/app/src/translations/kk.json @@ -169,6 +169,10 @@ "settings.noiseThreshold": "Шу деңгейі", "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Файлды сақтау мүмкін емес", "filesharing.startingFileShare": "Файлды бөлісу әрекеті", diff --git a/app/src/translations/lv.json b/app/src/translations/lv.json index db230606..005d71a2 100644 --- a/app/src/translations/lv.json +++ b/app/src/translations/lv.json @@ -165,6 +165,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Nav iespējams saglabāt failu", "filesharing.startingFileShare": "Tiek mēģināts kopīgot failu", diff --git a/app/src/translations/nb.json b/app/src/translations/nb.json index 4d02d198..f2d91dbb 100644 --- a/app/src/translations/nb.json +++ b/app/src/translations/nb.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Støyterskel", "settings.mirrorOwnVideo": "Vis eget bilde speilet for deg", "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Klarte ikke å lagre fil", "filesharing.startingFileShare": "Starter fildeling", diff --git a/app/src/translations/pl.json b/app/src/translations/pl.json index 9580b52d..50ae6f19 100644 --- a/app/src/translations/pl.json +++ b/app/src/translations/pl.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Próg szumu", "settings.mirrorOwnVideo": "Lustrzany widok własnego wideo", "settings.language": "Wybór języka", + "settings.myPhotoButton": "Ustaw moje zdjęcie", + "settings.myPhotoLabel": "Maksymalny rozmiar pliku: 5MB, dozwolone: jpg, jpeg, png", + "settings.myPhotoSizeError": " plik jest zbyt duży", + "settings.myPhotoTypeError": " nie jest obsługiwanym rozszerzeniem pliku", "filesharing.saveFileError": "Nie można zapisać pliku", "filesharing.startingFileShare": "Próba udostępnienia pliku", diff --git a/app/src/translations/pt.json b/app/src/translations/pt.json index f3e9d624..eca1cf0b 100644 --- a/app/src/translations/pt.json +++ b/app/src/translations/pt.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Impossível de gravar o ficheiro", "filesharing.startingFileShare": "Tentando partilha de ficheiro", diff --git a/app/src/translations/ro.json b/app/src/translations/ro.json index 67e3154e..668e2e62 100644 --- a/app/src/translations/ro.json +++ b/app/src/translations/ro.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Încercarea de a salva fișierul a eșuat", "filesharing.startingFileShare": "Partajarea fișierului", diff --git a/app/src/translations/ru.json b/app/src/translations/ru.json index e51cce42..e2bee72b 100644 --- a/app/src/translations/ru.json +++ b/app/src/translations/ru.json @@ -169,6 +169,10 @@ "settings.noiseThreshold": "Порог шума", "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Невозможно сохранить файл", "filesharing.startingFileShare": "Попытка поделиться файлом", diff --git a/app/src/translations/tr.json b/app/src/translations/tr.json index 92994fa7..03e40a20 100644 --- a/app/src/translations/tr.json +++ b/app/src/translations/tr.json @@ -171,6 +171,10 @@ "settings.noiseThreshold": "Gürültü eşiği", "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Dosya kaydedilemiyor", "filesharing.startingFileShare": "Paylaşılan dosyaya erişiliyor", diff --git a/app/src/translations/tw.json b/app/src/translations/tw.json index 64b338c3..5bbdacc5 100644 --- a/app/src/translations/tw.json +++ b/app/src/translations/tw.json @@ -170,6 +170,10 @@ "settings.noiseThreshold": null, "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "無法保存文件", "filesharing.startingFileShare": "開始分享文件", diff --git a/app/src/translations/uk.json b/app/src/translations/uk.json index dad79833..6a61c599 100644 --- a/app/src/translations/uk.json +++ b/app/src/translations/uk.json @@ -170,6 +170,10 @@ "settings.noiseThreshold": "Поріг шуму", "settings.mirrorOwnVideo": null, "settings.language": null, + "settings.myPhotoButton": null, + "settings.myPhotoLabel": null, + "settings.myPhotoSizeError": null, + "settings.myPhotoTypeError": null, "filesharing.saveFileError": "Неможливо зберегти файл", "filesharing.startingFileShare": "Спроба поділитися файлом", diff --git a/server/package.json b/server/package.json index 2dd31057..ba27cad0 100644 --- a/server/package.json +++ b/server/package.json @@ -35,7 +35,7 @@ "helmet": "^3.21.2", "ims-lti": "^3.0.2", "jsonwebtoken": "^8.5.1", - "mediasoup": "^3.5.14", + "mediasoup": "^3.6.27", "openid-client": "^3.7.3", "passport": "^0.4.0", "passport-local": "^1.0.0", From e9b06ae2c136a61e4941783a0ba921f192cec80d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Fri, 18 Dec 2020 10:15:05 +0100 Subject: [PATCH 03/24] Fix lint --- app/src/components/Containers/Peer.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/components/Containers/Peer.js b/app/src/components/Containers/Peer.js index 19ae2026..9407287b 100644 --- a/app/src/components/Containers/Peer.js +++ b/app/src/components/Containers/Peer.js @@ -119,7 +119,7 @@ const styles = (theme) => { opacity : 1 }, - '& p' : + '& p' : { padding : '6px 12px', borderRadius : 6, From 42afa6f91182645394b19c3c6d952fa7a4ca5cc3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Fri, 18 Dec 2020 10:19:08 +0100 Subject: [PATCH 04/24] Cleanup --- app/src/components/Controls/TopBar.js | 4 ---- app/src/components/JoinDialog.js | 4 ---- app/src/components/Settings/MediaSettings.js | 3 --- 3 files changed, 11 deletions(-) diff --git a/app/src/components/Controls/TopBar.js b/app/src/components/Controls/TopBar.js index 7575ca6b..64336cc9 100644 --- a/app/src/components/Controls/TopBar.js +++ b/app/src/components/Controls/TopBar.js @@ -23,7 +23,6 @@ import Popover from '@material-ui/core/Popover'; import Typography from '@material-ui/core/Typography'; import IconButton from '@material-ui/core/IconButton'; import MenuIcon from '@material-ui/icons/Menu'; -import Avatar from '@material-ui/core/Avatar'; import Badge from '@material-ui/core/Badge'; import Paper from '@material-ui/core/Paper'; import AccountCircle from '@material-ui/icons/AccountCircle'; @@ -217,7 +216,6 @@ const TopBar = (props) => drawerOverlayed, toolAreaOpen, isMobile, - myPicture, loggedIn, loginEnabled, fullscreenEnabled, @@ -926,7 +924,6 @@ TopBar.propTypes = permanentTopBar : PropTypes.bool.isRequired, drawerOverlayed : PropTypes.bool.isRequired, toolAreaOpen : PropTypes.bool.isRequired, - myPicture : PropTypes.string, loggedIn : PropTypes.bool.isRequired, loginEnabled : PropTypes.bool.isRequired, fullscreenEnabled : PropTypes.bool, @@ -974,7 +971,6 @@ const makeMapStateToProps = () => toolAreaOpen : state.toolarea.toolAreaOpen, loggedIn : state.me.loggedIn, loginEnabled : state.me.loginEnabled, - myPicture : state.me.picture, unread : state.toolarea.unreadMessages + state.toolarea.unreadFiles + raisedHandsSelector(state), canProduceExtraVideo : hasExtraVideoPermission(state), diff --git a/app/src/components/JoinDialog.js b/app/src/components/JoinDialog.js index 33efee48..3d284e48 100644 --- a/app/src/components/JoinDialog.js +++ b/app/src/components/JoinDialog.js @@ -11,7 +11,6 @@ import { useIntl, FormattedMessage } from 'react-intl'; import Dialog from '@material-ui/core/Dialog'; import DialogContentText from '@material-ui/core/DialogContentText'; import AccountCircle from '@material-ui/icons/AccountCircle'; -import Avatar from '@material-ui/core/Avatar'; import Typography from '@material-ui/core/Typography'; import FormControl from '@material-ui/core/FormControl'; import FormLabel from '@material-ui/core/FormLabel'; @@ -169,7 +168,6 @@ const JoinDialog = ({ displayName, displayNameInProgress, loggedIn, - myPicture, changeDisplayName, setMediaPerms, classes, @@ -775,7 +773,6 @@ JoinDialog.propTypes = displayNameInProgress : PropTypes.bool.isRequired, loginEnabled : PropTypes.bool.isRequired, loggedIn : PropTypes.bool.isRequired, - myPicture : PropTypes.string, changeDisplayName : PropTypes.func.isRequired, setMediaPerms : PropTypes.func.isRequired, classes : PropTypes.object.isRequired, @@ -796,7 +793,6 @@ const mapStateToProps = (state) => displayNameInProgress : state.me.displayNameInProgress, loginEnabled : state.me.loginEnabled, loggedIn : state.me.loggedIn, - myPicture : state.me.picture, locale : state.intl.locale, localesList : state.intl.list diff --git a/app/src/components/Settings/MediaSettings.js b/app/src/components/Settings/MediaSettings.js index aacb2d7c..e5ecdf35 100644 --- a/app/src/components/Settings/MediaSettings.js +++ b/app/src/components/Settings/MediaSettings.js @@ -23,9 +23,6 @@ import ExpandMore from '@material-ui/icons/ExpandMore'; import Switch from '@material-ui/core/Switch'; import ImageUploader from 'react-images-upload'; import Resizer from 'react-image-file-resizer'; -import Logger from '../../Logger'; - -const logger = new Logger('MediaSettings'); const NoiseSlider = withStyles( { From ec47517660541b2a4140c1d1c57dc7317c5f2a2b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Fri, 18 Dec 2020 10:51:50 +0100 Subject: [PATCH 05/24] Enable on server side --- server/lib/Room.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/lib/Room.js b/server/lib/Room.js index 53be1869..5505c3c6 100644 --- a/server/lib/Room.js +++ b/server/lib/Room.js @@ -1372,7 +1372,7 @@ class Room extends EventEmitter break; } - /* case 'changePicture': + case 'changePicture': { // Ensure the Peer is joined. if (!peer.joined) @@ -1392,7 +1392,7 @@ class Room extends EventEmitter cb(); break; - } */ + } case 'chatMessage': { From ba6a2322252edf1dc00bc816152798b157ca9ce2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Tue, 29 Dec 2020 00:35:36 +0100 Subject: [PATCH 06/24] Fix autoMuteTreshold bug --- app/src/RoomClient.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index 4cb33c14..e0cc16a9 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -3377,8 +3377,10 @@ export default class RoomClient { autoMuteThreshold = window.config.autoMuteThreshold; } - if (autoMuteThreshold && peers.length >= autoMuteThreshold) + if (autoMuteThreshold >= 0 && peers.length >= autoMuteThreshold) + { this.muteMic(); + } } } From d3bb985784d7e7ed6057ea0c6d4d0b67fb23cd8f Mon Sep 17 00:00:00 2001 From: Roman Drozd Date: Fri, 8 Jan 2021 10:01:27 +0100 Subject: [PATCH 07/24] Replace default png logo with svg one --- .gitignore | 2 +- app/public/config/config.example.js | 2 +- app/public/images/logo.example.png | Bin 10022 -> 0 bytes app/public/images/logo.example.svg | 88 ++++++++++++++++++ .../components/AccessControl/LoginDialog.js | 7 +- app/src/components/Controls/About.js | 2 + app/src/components/Controls/TopBar.js | 2 + app/src/components/JoinDialog.js | 7 +- 8 files changed, 104 insertions(+), 6 deletions(-) delete mode 100644 app/public/images/logo.example.png create mode 100644 app/public/images/logo.example.svg diff --git a/.gitignore b/.gitignore index 5c12d1eb..8ad7020f 100644 --- a/.gitignore +++ b/.gitignore @@ -3,7 +3,7 @@ node_modules/ /app/build/ /app/public/config/config.js /app/public/images/logo.* -!/app/public/images/logo.example.png +!/app/public/images/logo.example.svg /server/config/ !/server/config/config.example.js /server/public/ diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index 1742aab2..7ba284bb 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -163,7 +163,7 @@ var config = lockLastN : false, // Show logo if "logo" is not null, else show title // Set logo file name using logo.* pattern like "logo.png" to not track it by git - logo : 'images/logo.example.png', + logo : 'images/logo.example.svg', title : 'edumeet', // Service & Support URL // if not set then not displayed on the about modals diff --git a/app/public/images/logo.example.png b/app/public/images/logo.example.png deleted file mode 100644 index 514f602dea50fa46b3ea019febe2901ef86e162a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 10022 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 diff --git a/app/public/images/logo.example.svg b/app/public/images/logo.example.svg new file mode 100644 index 00000000..5c89ee7a --- /dev/null +++ b/app/public/images/logo.example.svg @@ -0,0 +1,88 @@ + + + +image/svg+xml \ No newline at end of file diff --git a/app/src/components/AccessControl/LoginDialog.js b/app/src/components/AccessControl/LoginDialog.js index e795cdc7..5c33c30b 100644 --- a/app/src/components/AccessControl/LoginDialog.js +++ b/app/src/components/AccessControl/LoginDialog.js @@ -52,8 +52,9 @@ const styles = (theme) => }, logo : { - display : 'block', - paddingBottom : '1vh' + width : '139px', + height : '30px', + display : 'block' }, loginButton : { @@ -117,7 +118,7 @@ const ChooseRoom = ({ { window.config.logo !=='' ? - Logo : + Logo : {window.config.title} }
diff --git a/app/src/components/Controls/About.js b/app/src/components/Controls/About.js index 17866524..0980dcc9 100644 --- a/app/src/components/Controls/About.js +++ b/app/src/components/Controls/About.js @@ -39,6 +39,8 @@ const styles = (theme) => }, logo : { + width : '139px', + height : '30px', marginRight : 'auto' }, link : diff --git a/app/src/components/Controls/TopBar.js b/app/src/components/Controls/TopBar.js index 12e94acb..7dbdd388 100644 --- a/app/src/components/Controls/TopBar.js +++ b/app/src/components/Controls/TopBar.js @@ -77,6 +77,8 @@ const styles = (theme) => }, logo : { + width : '139px', + height : '30px', display : 'none', marginLeft : 20, [theme.breakpoints.up('sm')] : diff --git a/app/src/components/JoinDialog.js b/app/src/components/JoinDialog.js index c1c1e6a7..e1f643cb 100644 --- a/app/src/components/JoinDialog.js +++ b/app/src/components/JoinDialog.js @@ -131,6 +131,11 @@ const styles = (theme) => loginLabel : { fontSize : '12px' + }, + logo : + { + width : '139px', + height : '30px' } }); @@ -337,7 +342,7 @@ const JoinDialog = ({ > { window.config.logo !=='' ? - Logo : + Logo : {window.config.title} } From 7add5b20295a8f38f4fcbc63803105d9aad020da Mon Sep 17 00:00:00 2001 From: Roman Drozd Date: Sun, 10 Jan 2021 03:57:44 +0100 Subject: [PATCH 08/24] Revert "Replace default png logo with svg one" This reverts commit d3bb985784d7e7ed6057ea0c6d4d0b67fb23cd8f. --- .gitignore | 2 +- app/public/config/config.example.js | 2 +- app/public/images/logo.example.png | Bin 0 -> 10022 bytes app/public/images/logo.example.svg | 88 ------------------ .../components/AccessControl/LoginDialog.js | 7 +- app/src/components/Controls/About.js | 2 - app/src/components/Controls/TopBar.js | 2 - app/src/components/JoinDialog.js | 7 +- 8 files changed, 6 insertions(+), 104 deletions(-) create mode 100644 app/public/images/logo.example.png delete mode 100644 app/public/images/logo.example.svg diff --git a/.gitignore b/.gitignore index 8ad7020f..5c12d1eb 100644 --- a/.gitignore +++ b/.gitignore @@ -3,7 +3,7 @@ node_modules/ /app/build/ /app/public/config/config.js /app/public/images/logo.* -!/app/public/images/logo.example.svg +!/app/public/images/logo.example.png /server/config/ !/server/config/config.example.js /server/public/ diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index 7ba284bb..1742aab2 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -163,7 +163,7 @@ var config = lockLastN : false, // Show logo if "logo" is not null, else show title // Set logo file name using logo.* pattern like "logo.png" to not track it by git - logo : 'images/logo.example.svg', + logo : 'images/logo.example.png', title : 'edumeet', // Service & Support URL // if not set then not displayed on the about modals diff --git a/app/public/images/logo.example.png b/app/public/images/logo.example.png new file mode 100644 index 0000000000000000000000000000000000000000..514f602dea50fa46b3ea019febe2901ef86e162a GIT binary patch literal 10022 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 literal 0 HcmV?d00001 diff --git a/app/public/images/logo.example.svg b/app/public/images/logo.example.svg deleted file mode 100644 index 5c89ee7a..00000000 --- a/app/public/images/logo.example.svg +++ /dev/null @@ -1,88 +0,0 @@ - - - -image/svg+xml \ No newline at end of file diff --git a/app/src/components/AccessControl/LoginDialog.js b/app/src/components/AccessControl/LoginDialog.js index 5c33c30b..e795cdc7 100644 --- a/app/src/components/AccessControl/LoginDialog.js +++ b/app/src/components/AccessControl/LoginDialog.js @@ -52,9 +52,8 @@ const styles = (theme) => }, logo : { - width : '139px', - height : '30px', - display : 'block' + display : 'block', + paddingBottom : '1vh' }, loginButton : { @@ -118,7 +117,7 @@ const ChooseRoom = ({ { window.config.logo !=='' ? - Logo : + Logo : {window.config.title} }
diff --git a/app/src/components/Controls/About.js b/app/src/components/Controls/About.js index 0980dcc9..17866524 100644 --- a/app/src/components/Controls/About.js +++ b/app/src/components/Controls/About.js @@ -39,8 +39,6 @@ const styles = (theme) => }, logo : { - width : '139px', - height : '30px', marginRight : 'auto' }, link : diff --git a/app/src/components/Controls/TopBar.js b/app/src/components/Controls/TopBar.js index 7dbdd388..12e94acb 100644 --- a/app/src/components/Controls/TopBar.js +++ b/app/src/components/Controls/TopBar.js @@ -77,8 +77,6 @@ const styles = (theme) => }, logo : { - width : '139px', - height : '30px', display : 'none', marginLeft : 20, [theme.breakpoints.up('sm')] : diff --git a/app/src/components/JoinDialog.js b/app/src/components/JoinDialog.js index e1f643cb..c1c1e6a7 100644 --- a/app/src/components/JoinDialog.js +++ b/app/src/components/JoinDialog.js @@ -131,11 +131,6 @@ const styles = (theme) => loginLabel : { fontSize : '12px' - }, - logo : - { - width : '139px', - height : '30px' } }); @@ -342,7 +337,7 @@ const JoinDialog = ({ > { window.config.logo !=='' ? - Logo : + Logo : {window.config.title} } From 2810fdbbfbf96c779c5501c0d449491323b42c77 Mon Sep 17 00:00:00 2001 From: Roman Drozd Date: Sun, 10 Jan 2021 04:09:41 +0100 Subject: [PATCH 09/24] Replace default png logo with svg one (with sizes placed inside svg file) --- .gitignore | 2 +- app/public/config/config.example.js | 2 +- app/public/images/logo.edumeet.svg | 88 ++++++++++++++++++++++++++++ app/public/images/logo.example.png | Bin 10022 -> 0 bytes 4 files changed, 90 insertions(+), 2 deletions(-) create mode 100644 app/public/images/logo.edumeet.svg delete mode 100644 app/public/images/logo.example.png diff --git a/.gitignore b/.gitignore index 5c12d1eb..1799638a 100644 --- a/.gitignore +++ b/.gitignore @@ -3,7 +3,7 @@ node_modules/ /app/build/ /app/public/config/config.js /app/public/images/logo.* -!/app/public/images/logo.example.png +!/app/public/images/logo.edumeet.svg /server/config/ !/server/config/config.example.js /server/public/ diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index 1742aab2..f09acd59 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -163,7 +163,7 @@ var config = lockLastN : false, // Show logo if "logo" is not null, else show title // Set logo file name using logo.* pattern like "logo.png" to not track it by git - logo : 'images/logo.example.png', + logo : 'images/logo.edumeet.svg', title : 'edumeet', // Service & Support URL // if not set then not displayed on the about modals diff --git a/app/public/images/logo.edumeet.svg b/app/public/images/logo.edumeet.svg new file mode 100644 index 00000000..717c04e8 --- /dev/null +++ b/app/public/images/logo.edumeet.svg @@ -0,0 +1,88 @@ + + + +image/svg+xml diff --git a/app/public/images/logo.example.png b/app/public/images/logo.example.png deleted file mode 100644 index 514f602dea50fa46b3ea019febe2901ef86e162a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 10022 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 From 8c0fa8a4f412368ffc8e5318a5bf0f955c7b633e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Pawa=C5=82owski?= Date: Thu, 14 Jan 2021 11:36:58 +0100 Subject: [PATCH 10/24] Add notification of peers on a transportclose event --- server/lib/Room.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/lib/Room.js b/server/lib/Room.js index 53be1869..8f44f9a7 100644 --- a/server/lib/Room.js +++ b/server/lib/Room.js @@ -1884,6 +1884,8 @@ class Room extends EventEmitter { // Remove from its map. consumerPeer.removeConsumer(consumer.id); + + this._notification(consumerPeer.socket, 'consumerClosed', { consumerId: consumer.id }); }); consumer.on('producerclose', () => From 4001844884e1b411aca7bad5ad3ea02f696b58b7 Mon Sep 17 00:00:00 2001 From: Roman Drozd Date: Sun, 17 Jan 2021 19:03:43 +0100 Subject: [PATCH 11/24] Improve username visibility in brighter video --- app/src/components/VideoContainers/VideoView.js | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/app/src/components/VideoContainers/VideoView.js b/app/src/components/VideoContainers/VideoView.js index a9e0821b..6180b177 100644 --- a/app/src/components/VideoContainers/VideoView.js +++ b/app/src/components/VideoContainers/VideoView.js @@ -143,16 +143,19 @@ const styles = (theme) => color : 'rgba(255, 255, 255, 0.85)', border : 'none', borderBottom : '1px solid #aeff00', - backgroundColor : 'transparent' + backgroundColor : 'rgba(0, 0, 0, 0.25)', + padding : theme.spacing(0.6) }, displayNameStatic : { - userSelect : 'none', - cursor : 'text', - fontSize : 14, - fontWeight : 400, - color : 'rgba(255, 255, 255, 0.85)', - '&:hover' : + userSelect : 'none', + cursor : 'text', + fontSize : 14, + fontWeight : 400, + color : 'rgba(255, 255, 255, 0.85)', + backgroundColor : 'rgba(0, 0, 0, 0.25)', + padding : theme.spacing(0.6), + '&:hover' : { backgroundColor : 'rgb(174, 255, 0, 0.25)' } From 85eb8d2d8549a8ad5a8f8b910a5117c45e65a6bf Mon Sep 17 00:00:00 2001 From: stefkamarton Date: Thu, 28 Jan 2021 21:04:17 +0100 Subject: [PATCH 12/24] Fix Login Cache Issue --- server/lib/Room.js | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/server/lib/Room.js b/server/lib/Room.js index 8f44f9a7..415b79aa 100644 --- a/server/lib/Room.js +++ b/server/lib/Room.js @@ -614,6 +614,13 @@ class Room extends EventEmitter this._roomId); this.close(); } + else if(this.checkEmpty() && !this._lobby.checkEmpty() && this.isLocked()){ + logger.info( + 'Room deserted for some time, closing the room [roomId:"%s"] and kick peers from the lobby', + this._roomId); + + this.close(); + } else logger.debug('selfDestructCountdown() aborted; room is not empty!'); }, 10000); @@ -847,6 +854,12 @@ class Room extends EventEmitter // lobby is empty, close the room after a while. if (this.checkEmpty() && this._lobby.checkEmpty()) this.selfDestructCountdown(); + // If this is the last Peer in the room, + // lobby is not empty and room is locked, + // close the room after a while. + else if(this.checkEmpty() && !this._lobby.checkEmpty() && this.isLocked()){ + this.selfDestructCountdown(); + } } async _handleSocketRequest(peer, request, cb) From 221aa4b0187a83889cd8351dd4507acf44f65e7b Mon Sep 17 00:00:00 2001 From: MrSnoozles Date: Mon, 1 Feb 2021 15:56:30 +0100 Subject: [PATCH 13/24] Add optional configuration property "serverHostname" --- app/src/urlFactory.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/src/urlFactory.js b/app/src/urlFactory.js index ae97dbd7..bdfd9dcc 100644 --- a/app/src/urlFactory.js +++ b/app/src/urlFactory.js @@ -1,12 +1,13 @@ export function getSignalingUrl(peerId, roomId) { + const hostname = window.config.serverHostname || window.location.hostname; const port = process.env.NODE_ENV !== 'production' ? window.config.developmentPort : window.config.productionPort; - const url = `wss://${window.location.hostname}:${port}/?peerId=${peerId}&roomId=${roomId}`; + const url = `wss://${hostname}:${port}/?peerId=${peerId}&roomId=${roomId}`; return url; } From 88ab41a1f551cb5e06ee201f2a8bb34eefeb7aee Mon Sep 17 00:00:00 2001 From: MrSnoozles Date: Mon, 1 Feb 2021 16:44:43 +0100 Subject: [PATCH 14/24] Add example serverHostname configuration --- app/public/config/config.example.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index f09acd59..5e64c6dd 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -4,6 +4,9 @@ var config = loginEnabled : false, developmentPort : 3443, productionPort : 443, + // of the server component runs on a different host than the app + // you can uncomment the following line and specify the host name. + // serverHostname : 'external-server.com', /** * Supported browsers version From 7614074e6f7687c03a5b80d337b76187ab65ed04 Mon Sep 17 00:00:00 2001 From: MrSnoozles Date: Mon, 1 Feb 2021 16:48:23 +0100 Subject: [PATCH 15/24] Update config.example.js --- app/public/config/config.example.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index 5e64c6dd..71e2645c 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -4,9 +4,9 @@ var config = loginEnabled : false, developmentPort : 3443, productionPort : 443, - // of the server component runs on a different host than the app + // If the server component runs on a different host than the app // you can uncomment the following line and specify the host name. - // serverHostname : 'external-server.com', + //serverHostname : 'external-server.com', /** * Supported browsers version From ad32708054e30879bc194d3d4838a9c8dbfcf021 Mon Sep 17 00:00:00 2001 From: Jiri Mencak Date: Wed, 3 Feb 2021 20:39:10 +0100 Subject: [PATCH 16/24] Restart ICE on disconnected/failed connection states. Resolves issue #656. --- app/src/RoomClient.js | 62 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 62 insertions(+) diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index e0cc16a9..ffc79217 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -2084,6 +2084,38 @@ export default class RoomClient } } + async restartIce() + { + logger.debug('restartIce()'); + + try + { + if (this._sendTransport) + { + const iceParameters = await this.sendRequest( + 'restartIce', + { transportId: this._sendTransport.id }); + + await this._sendTransport.restartIce({ iceParameters }); + } + + if (this._recvTransport) + { + const iceParameters = await this.sendRequest( + 'restartIce', + { transportId: this._recvTransport.id }); + + await this._recvTransport.restartIce({ iceParameters }); + } + + logger.debug('ICE restarted'); + } + catch (error) + { + logger.error('restartIce() | failed:%o', error); + } + } + async setConsumerPriority(consumerId, priority) { logger.debug( @@ -3186,6 +3218,21 @@ export default class RoomClient .catch(errback); }); + this._sendTransport.on( + 'connectionstatechange', (connectState) => + { + switch (connectState) + { + case 'disconnected': + case 'failed': + this.restartIce(); + break; + + default: + break; + } + }); + this._sendTransport.on( 'produce', async ({ kind, rtpParameters, appData }, callback, errback) => { @@ -3249,6 +3296,21 @@ export default class RoomClient .catch(errback); }); + this._recvTransport.on( + 'connectionstatechange', (connectState) => + { + switch (connectState) + { + case 'disconnected': + case 'failed': + this.restartIce(); + break; + + default: + break; + } + }); + // Set our media capabilities. store.dispatch(meActions.setMediaCapabilities( { From 1d92112b6c7e7b9b40b573f39c3cda3d99abd9f6 Mon Sep 17 00:00:00 2001 From: N7Remus Date: Thu, 4 Feb 2021 08:17:47 +0100 Subject: [PATCH 17/24] fix nodejs version in readme #611 --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 210557ce..1c6cde41 100644 --- a/README.md +++ b/README.md @@ -29,7 +29,7 @@ If you want the ansible approach, you can find ansible role [here](https://githu If you want to install it on the Debian & Ubuntu based operating systems. * Prerequisites: -edumeet will run on nodejs v10.x and later versions. (v12.x has a know issue for now, please until it will be fixed use the 10.x version) +edumeet will run on nodejs v14.x (tested with v14.15.4 version). To install see here [here](https://github.com/nodesource/distributions/blob/master/README.md#debinstall). * Download .deb package from [here](https://github.com/edumeet/edumeet/actions?query=workflow%3ADeployer+branch%3Amaster+is%3Asuccess) (job artifact) @@ -61,7 +61,7 @@ $ sudo systemctl start edumeet ## Manual installation * Prerequisites: -Currently edumeet will only run on nodejs v13.x +Currently edumeet will run on nodejs v14.x To install see here [here](https://github.com/nodesource/distributions/blob/master/README.md#debinstall). ```bash From 9e83c2bac71eb1cf51f93d8b69bdc8fad02e7ecd Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Thu, 11 Feb 2021 10:49:53 +0100 Subject: [PATCH 18/24] WIP adding adaptive video quality switch tracking page size --- .gitignore | 3 +- app/package.json | 1 + app/src/RoomClient.js | 88 ++++++++++++++++++- app/src/components/Containers/Peer.js | 63 +++++++++++-- app/src/components/Containers/SpeakerPeer.js | 74 ++++++++++++---- app/src/components/MeetingViews/Democratic.js | 3 + app/src/components/MeetingViews/Filmstrip.js | 5 ++ .../VideoContainers/FullScreenView.js | 39 ++++++-- .../components/VideoContainers/VideoView.js | 20 ++++- app/src/components/appPropTypes.js | 2 + 10 files changed, 262 insertions(+), 36 deletions(-) diff --git a/.gitignore b/.gitignore index 1799638a..aaed6d85 100644 --- a/.gitignore +++ b/.gitignore @@ -10,4 +10,5 @@ node_modules/ /server/certs/ !/server/certs/mediasoup-demo.localhost.* .vscode -/app/public/config/*.pem \ No newline at end of file +/app/public/config/*.pem +yarn.lock \ No newline at end of file diff --git a/app/package.json b/app/package.json index 58d422c5..085c4025 100644 --- a/app/package.json +++ b/app/package.json @@ -18,6 +18,7 @@ "@material-ui/core": "^4.5.1", "@material-ui/icons": "^4.5.1", "@material-ui/lab": "^4.0.0-alpha.56", + "@react-hook/window-size": "^3.0.7", "bowser": "^2.7.0", "classnames": "^2.2.6", "create-torrent": "^4.4.1", diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index d35ab231..60e2a8cf 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -1497,7 +1497,7 @@ export default class RoomClient ([ track ] = stream.getVideoTracks()); - const { deviceId: trackDeviceId } = track.getSettings(); + const { deviceId: trackDeviceId, width, height } = track.getSettings(); store.dispatch(settingsActions.setSelectedWebcamDevice(trackDeviceId)); @@ -1528,7 +1528,9 @@ export default class RoomClient }, appData : { - source : 'webcam' + source : 'webcam', + width, + height } }); } @@ -1538,7 +1540,9 @@ export default class RoomClient track, appData : { - source : 'webcam' + source : 'webcam', + width, + height } }); } @@ -2134,6 +2138,82 @@ export default class RoomClient } } + setConsumerPreferredLayersMax(consumer) + { + if (consumer.type === 'simple') + { + return; + } + + logger.debug( + 'setConsumerPreferredLayersMax() [consumerId:"%s"]', consumer.id); + + if (consumer.preferredSpatialLayer !== consumer.spatialLayers -1 || + consumer.preferredTemporalLayer !== consumer.temporalLayers -1) + { + return this.setConsumerPreferredLayers(consumer.id, + consumer.spatialLayers - 1, consumer.temporalLayers - 1); + } + } + + adaptConsumerPreferredLayers(consumer, viewportWidth, viewportHeight) + { + if (consumer.type === 'simple') + { + return; + } + + if (!viewportWidth || !viewportHeight) + { + return; + } + + const { id, preferredSpatialLayer, preferredTemporalLayer, width, height } = consumer; + const availableArea = Math.round(viewportWidth * viewportHeight); + + logger.debug( + 'adaptConsumerPreferredLayers() [consumerId:"%s", width:"%d", height:"%d" viewportWidth:"%d", viewportHeight:"%d"]', + consumer.id, width, height, viewportWidth, viewportHeight); + + let spatialLayer = 0; + + for (let i = 0; i < window.config.simulcastEncodings.length; i++) + { + const levelArea = width * height / + (window.config.simulcastEncodings[i].scaleResolutionDownBy ** 2); + + if (availableArea >= levelArea) + { + spatialLayer = i; + } + else + { + break; + } + } + + let temporalLayer = 2; + + if (spatialLayer === 0) + { + if (viewportWidth < width * 0.5) + { + temporalLayer = 1; + } + if (viewportWidth < width * 0.25) + { + temporalLayer = 0; + } + } + + if (preferredSpatialLayer !== spatialLayer || + preferredTemporalLayer !== temporalLayer) + { + return this.setConsumerPreferredLayers(id, spatialLayer, temporalLayer); + } + + } + async setConsumerPriority(consumerId, priority) { logger.debug( @@ -2394,6 +2474,8 @@ export default class RoomClient remotelyPaused : producerPaused, rtpParameters : consumer.rtpParameters, source : consumer.appData.source, + width : consumer.appData.width, + height : consumer.appData.height, spatialLayers : spatialLayers, temporalLayers : temporalLayers, preferredSpatialLayer : spatialLayers - 1, diff --git a/app/src/components/Containers/Peer.js b/app/src/components/Containers/Peer.js index 9407287b..7ecf3591 100644 --- a/app/src/components/Containers/Peer.js +++ b/app/src/components/Containers/Peer.js @@ -1,4 +1,4 @@ -import React, { useState } from 'react'; +import React, { useState, useEffect } from 'react'; import { connect } from 'react-redux'; import { makePeerConsumerSelector } from '../Selectors'; import PropTypes from 'prop-types'; @@ -155,8 +155,12 @@ const Peer = (props) => style, smallContainer, windowConsumer, + fullScreenConsumer, classes, - theme + theme, + enableLayersSwitch, + width, + height } = props; const micEnabled = ( @@ -191,6 +195,34 @@ const Peer = (props) => rootStyle.backgroundSize = 'auto 100%'; } + useEffect(() => + { + const handler = setTimeout(() => + { + if (!webcamConsumer) + return; + + if (windowConsumer === webcamConsumer.id) + { + // if playing in external window, set the maximum quality levels + roomClient.setConsumerPreferredLayersMax(webcamConsumer); + } + else if (enableLayersSwitch && webcamConsumer?.type !== 'simple' + && fullScreenConsumer !== webcamConsumer.id) + { + roomClient.adaptConsumerPreferredLayers(webcamConsumer, width, height); + } + }, 1000); + + return () => { clearTimeout(handler); }; + }, [ + enableLayersSwitch, + webcamConsumer, + windowConsumer, + fullScreenConsumer, + roomClient, width, height + ]); + return (
videoCodec={webcamConsumer && webcamConsumer.codec} audioScore={micConsumer ? micConsumer.score : null} videoScore={webcamConsumer ? webcamConsumer.score : null} + width={width} + height={height} > @@ -634,6 +668,8 @@ const Peer = (props) => videoVisible={videoVisible} videoCodec={consumer && consumer.codec} videoScore={consumer ? consumer.score : null} + width={width} + height={height} />
@@ -778,6 +814,8 @@ const Peer = (props) => videoVisible={screenVisible} videoCodec={screenConsumer && screenConsumer.codec} videoScore={screenConsumer ? screenConsumer.score : null} + width={width} + height={height} />
@@ -796,6 +834,7 @@ Peer.propTypes = screenConsumer : appPropTypes.Consumer, extraVideoConsumers : PropTypes.arrayOf(appPropTypes.Consumer), windowConsumer : PropTypes.string, + fullScreenConsumer : PropTypes.string, activeSpeaker : PropTypes.bool, browser : PropTypes.object.isRequired, spacing : PropTypes.number, @@ -804,7 +843,10 @@ Peer.propTypes = toggleConsumerFullscreen : PropTypes.func.isRequired, toggleConsumerWindow : PropTypes.func.isRequired, classes : PropTypes.object.isRequired, - theme : PropTypes.object.isRequired + theme : PropTypes.object.isRequired, + enableLayersSwitch : PropTypes.bool, + width : PropTypes.number, + height : PropTypes.number }; const makeMapStateToProps = (initialState, { id }) => @@ -814,11 +856,12 @@ const makeMapStateToProps = (initialState, { id }) => const mapStateToProps = (state) => { return { - peer : state.peers[id], + peer : state.peers[id], ...getPeerConsumers(state, id), - windowConsumer : state.room.windowConsumer, - activeSpeaker : id === state.room.activeSpeakerId, - browser : state.me.browser + windowConsumer : state.room.windowConsumer, + fullScreenConsumer : state.room.fullScreenConsumer, + activeSpeaker : id === state.room.activeSpeakerId, + browser : state.me.browser }; }; @@ -853,7 +896,11 @@ export default withRoomContext(connect( prev.consumers === next.consumers && prev.room.activeSpeakerId === next.room.activeSpeakerId && prev.room.windowConsumer === next.room.windowConsumer && - prev.me.browser === next.me.browser + prev.room.fullScreenConsumer === next.room.fullScreenConsumer && + prev.me.browser === next.me.browser && + prev.enableLayersSwitch === next.enableLayersSwitch && + prev.width === next.width && + prev.height === next.height ); } } diff --git a/app/src/components/Containers/SpeakerPeer.js b/app/src/components/Containers/SpeakerPeer.js index 3edb7c00..b4389a40 100644 --- a/app/src/components/Containers/SpeakerPeer.js +++ b/app/src/components/Containers/SpeakerPeer.js @@ -1,9 +1,10 @@ -import React from 'react'; +import React, { useEffect } from 'react'; import { connect } from 'react-redux'; import { makePeerConsumerSelector } from '../Selectors'; import PropTypes from 'prop-types'; import classnames from 'classnames'; import * as appPropTypes from '../appPropTypes'; +import { withRoomContext } from '../../RoomContext'; import { withStyles } from '@material-ui/core/styles'; import { FormattedMessage } from 'react-intl'; import VideoView from '../VideoContainers/VideoView'; @@ -69,14 +70,19 @@ const styles = (theme) => const SpeakerPeer = (props) => { const { + roomClient, advancedMode, peer, micConsumer, webcamConsumer, screenConsumer, + windowConsumer, + fullScreenConsumer, spacing, style, - classes + classes, + width, + height } = props; const videoVisible = ( @@ -96,6 +102,33 @@ const SpeakerPeer = (props) => 'margin' : spacing }; + useEffect(() => + { + const handler = setTimeout(() => + { + if (!webcamConsumer) + return; + + if (windowConsumer === webcamConsumer.id) + { + // if playing in external window, set the maximum quality levels + roomClient.setConsumerPreferredLayersMax(webcamConsumer); + } + else if (webcamConsumer?.type !== 'simple' + && fullScreenConsumer !== webcamConsumer.id) + { + roomClient.adaptConsumerPreferredLayers(webcamConsumer, width, height); + } + }, 1000); + + return () => { clearTimeout(handler); }; + }, [ + webcamConsumer, + windowConsumer, + fullScreenConsumer, + roomClient, width, height + ]); + return (
videoCodec={webcamConsumer && webcamConsumer.codec} audioScore={micConsumer ? micConsumer.score : null} videoScore={webcamConsumer ? webcamConsumer.score : null} + width={width} + height={height} > @@ -205,14 +240,19 @@ const SpeakerPeer = (props) => SpeakerPeer.propTypes = { - advancedMode : PropTypes.bool, - peer : appPropTypes.Peer, - micConsumer : appPropTypes.Consumer, - webcamConsumer : appPropTypes.Consumer, - screenConsumer : appPropTypes.Consumer, - spacing : PropTypes.number, - style : PropTypes.object, - classes : PropTypes.object.isRequired + roomClient : PropTypes.any.isRequired, + advancedMode : PropTypes.bool, + peer : appPropTypes.Peer, + micConsumer : appPropTypes.Consumer, + webcamConsumer : appPropTypes.Consumer, + screenConsumer : appPropTypes.Consumer, + windowConsumer : PropTypes.string, + fullScreenConsumer : PropTypes.string, + spacing : PropTypes.number, + style : PropTypes.object, + classes : PropTypes.object.isRequired, + width : PropTypes.number, + height : PropTypes.number }; const mapStateToProps = (state, { id }) => @@ -220,12 +260,14 @@ const mapStateToProps = (state, { id }) => const getPeerConsumers = makePeerConsumerSelector(); return { - peer : state.peers[id], - ...getPeerConsumers(state, id) + peer : state.peers[id], + ...getPeerConsumers(state, id), + windowConsumer : state.room.windowConsumer, + fullScreenConsumer : state.room.fullScreenConsumer }; }; -export default connect( +export default withRoomContext(connect( mapStateToProps, null, null, @@ -235,8 +277,10 @@ export default connect( return ( prev.peers === next.peers && prev.consumers === next.consumers && - prev.room.activeSpeakerId === next.room.activeSpeakerId + prev.room.activeSpeakerId === next.room.activeSpeakerId && + prev.width === next.width && + prev.height === next.height ); } } -)(withStyles(styles, { withTheme: true })(SpeakerPeer)); +)(withStyles(styles, { withTheme: true })(SpeakerPeer))); diff --git a/app/src/components/MeetingViews/Democratic.js b/app/src/components/MeetingViews/Democratic.js index 27319e7a..eb9c68e8 100644 --- a/app/src/components/MeetingViews/Democratic.js +++ b/app/src/components/MeetingViews/Democratic.js @@ -192,6 +192,9 @@ class Democratic extends React.PureComponent id={peer} spacing={6} style={style} + enableLayersSwitch + width={this.state.peerWidth} + height={this.state.peerHeight} /> ); })} diff --git a/app/src/components/MeetingViews/Filmstrip.js b/app/src/components/MeetingViews/Filmstrip.js index 5e533e10..124e2a91 100644 --- a/app/src/components/MeetingViews/Filmstrip.js +++ b/app/src/components/MeetingViews/Filmstrip.js @@ -276,6 +276,8 @@ class Filmstrip extends React.PureComponent advancedMode={advancedMode} id={activePeerId} style={speakerStyle} + width={speakerStyle.width} + height={speakerStyle.height} /> }
@@ -317,6 +319,9 @@ class Filmstrip extends React.PureComponent id={peerId} style={peerStyle} smallContainer + enableLayersSwitch={activePeerId !== peerId} + width={peerStyle.width} + height={peerStyle.height} />
diff --git a/app/src/components/VideoContainers/FullScreenView.js b/app/src/components/VideoContainers/FullScreenView.js index 06579607..4ebe483d 100644 --- a/app/src/components/VideoContainers/FullScreenView.js +++ b/app/src/components/VideoContainers/FullScreenView.js @@ -1,10 +1,12 @@ -import React from 'react'; +import React, { useRef, useEffect } from 'react'; +import { useWindowSize } from '@react-hook/window-size'; import { connect } from 'react-redux'; import PropTypes from 'prop-types'; import classnames from 'classnames'; import { withStyles } from '@material-ui/core/styles'; import * as appPropTypes from '../appPropTypes'; import * as roomActions from '../../actions/roomActions'; +import { withRoomContext } from '../../RoomContext'; import FullScreenExitIcon from '@material-ui/icons/FullscreenExit'; import VideoView from './VideoView'; @@ -79,14 +81,32 @@ const styles = (theme) => const FullScreenView = (props) => { const { + roomClient, advancedMode, consumer, + fullScreenConsumer, toggleConsumerFullscreen, toolbarsVisible, permanentTopBar, classes } = props; + const elementRef = useRef(null); + const size = useWindowSize({ + wait : 400 + }); + + useEffect(() => + { + if (!elementRef.current) + return; + + if (consumer && consumer.type !== 'simple') + { + roomClient.adaptConsumerPreferredLayers(consumer, size[0], size[1]); + } + }, [ size, fullScreenConsumer ]); + if (!consumer) return null; @@ -97,7 +117,7 @@ const FullScreenView = (props) => ); return ( -
+
videoVisible={consumerVisible} videoCodec={consumer && consumer.codec} videoScore={consumer ? consumer.score : null} + width={size[0]} + height={size[1]} />
); @@ -142,8 +164,10 @@ const FullScreenView = (props) => FullScreenView.propTypes = { + roomClient : PropTypes.any.isRequired, advancedMode : PropTypes.bool, consumer : appPropTypes.Consumer, + fullScreenConsumer : PropTypes.string, toggleConsumerFullscreen : PropTypes.func.isRequired, toolbarsVisible : PropTypes.bool, permanentTopBar : PropTypes.bool, @@ -152,9 +176,10 @@ FullScreenView.propTypes = const mapStateToProps = (state) => ({ - consumer : state.consumers[state.room.fullScreenConsumer], - toolbarsVisible : state.room.toolbarsVisible, - permanentTopBar : state.settings.permanentTopBar + consumer : state.consumers[state.room.fullScreenConsumer], + toolbarsVisible : state.room.toolbarsVisible, + permanentTopBar : state.settings.permanentTopBar, + fullScreenConsumer : state.room.fullScreenConsumer }); const mapDispatchToProps = (dispatch) => @@ -166,7 +191,7 @@ const mapDispatchToProps = (dispatch) => } }); -export default connect( +export default withRoomContext(connect( mapStateToProps, mapDispatchToProps, null, @@ -181,4 +206,4 @@ export default connect( ); } } -)(withStyles(styles)(FullScreenView)); +)(withStyles(styles)(FullScreenView))); diff --git a/app/src/components/VideoContainers/VideoView.js b/app/src/components/VideoContainers/VideoView.js index 6180b177..57325bee 100644 --- a/app/src/components/VideoContainers/VideoView.js +++ b/app/src/components/VideoContainers/VideoView.js @@ -92,6 +92,7 @@ const styles = (theme) => "AcodL Acod Acod Acod Acod" \ "VcodL Vcod Vcod Vcod Vcod" \ "ResL Res Res Res Res" \ + "VPortL VPort VPort VPort VPort" \ "RecvL RecvBps RecvBps RecvSum RecvSum" \ "SendL SendBps SendBps SendSum SendSum" \ "IPlocL IPloc IPloc IPloc IPloc" \ @@ -105,6 +106,8 @@ const styles = (theme) => '& .Vcod' : { gridArea: 'Vcod' }, '& .ResL' : { gridArea: 'ResL' }, '& .Res' : { gridArea: 'Res' }, + '& .VPortL' : { gridArea: 'VPortL' }, + '& .VPort' : { gridArea: 'VPort' }, '& .RecvL' : { gridArea: 'RecvL' }, '& .RecvBps' : { gridArea: 'RecvBps', justifySelf: 'flex-end' }, '& .RecvSum' : { gridArea: 'RecvSum', justifySelf: 'flex-end' }, @@ -207,7 +210,9 @@ class VideoView extends React.PureComponent onChangeDisplayName, children, classes, - netInfo + netInfo, + width, + height } = this.props; const { @@ -308,6 +313,15 @@ class VideoView extends React.PureComponent } + { (videoVisible && width && height) && + + VPort: + + {Math.round(width)}x{Math.round(height)} + + + } + { isMe && !isScreen && !isExtraVideo && (netInfo.recv && netInfo.send && netInfo.send.iceSelectedTuple) && @@ -528,7 +542,9 @@ VideoView.propTypes = onChangeDisplayName : PropTypes.func, children : PropTypes.object, classes : PropTypes.object.isRequired, - netInfo : PropTypes.object + netInfo : PropTypes.object, + width : PropTypes.number, + height : PropTypes.number }; export default withStyles(styles)(VideoView); diff --git a/app/src/components/appPropTypes.js b/app/src/components/appPropTypes.js index 0ae4fc20..1492ece7 100644 --- a/app/src/components/appPropTypes.js +++ b/app/src/components/appPropTypes.js @@ -40,6 +40,8 @@ export const Consumer = PropTypes.shape( source : PropTypes.oneOf([ 'mic', 'webcam', 'screen', 'extravideo' ]).isRequired, locallyPaused : PropTypes.bool.isRequired, remotelyPaused : PropTypes.bool.isRequired, + width : PropTypes.number, + height : PropTypes.number, profile : PropTypes.oneOf([ 'none', 'default', 'low', 'medium', 'high' ]), track : PropTypes.any, codec : PropTypes.string From 5a558e4e0255fadafb1ba8e61e1612e1da2d8398 Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Thu, 11 Feb 2021 11:49:37 +0100 Subject: [PATCH 19/24] estimate the temporal layer using the available screen area --- app/src/RoomClient.js | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index 60e2a8cf..ddb1487b 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -2192,15 +2192,18 @@ export default class RoomClient } } - let temporalLayer = 2; + let temporalLayer = consumer.temporalLayers - 1; if (spatialLayer === 0) { - if (viewportWidth < width * 0.5) + const lowestLevelArea = width * height / + (window.config.simulcastEncodings[0].scaleResolutionDownBy ** 2); + + if (availableArea < lowestLevelArea * 0.5) { temporalLayer = 1; } - if (viewportWidth < width * 0.25) + if (availableArea < lowestLevelArea * 0.25) { temporalLayer = 0; } From 62e2739306e5f285f1b9f9ecbf4835c69883582d Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Fri, 12 Feb 2021 12:06:16 +0100 Subject: [PATCH 20/24] Avoid crashing the server process when exiting interactive socket sessions When using the interactive socket connection (`socat - UNIX-CONNECT:/tmp/edumeet-server.sock`), closing the command line session throws a not handled exception that crashes the server process. --- server/lib/interactiveServer.js | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/server/lib/interactiveServer.js b/server/lib/interactiveServer.js index 78eaf92c..1f34ac89 100644 --- a/server/lib/interactiveServer.js +++ b/server/lib/interactiveServer.js @@ -684,6 +684,11 @@ module.exports = async function(rooms, peers) const interactive = new Interactive(socket); interactive.openCommandConsole(); + + socket.on('error', (error) => + { + console.error(`interactiveServer socket error:`, error.message); + }); }); await new Promise((resolve) => From e6a63ecb93c49e67b22cb9855b63ad0d5f1ec42e Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Sat, 20 Feb 2021 15:13:50 +0100 Subject: [PATCH 21/24] When missing or when using SVC, infer the correct resolution scalings from WebRTC standard --- app/src/RoomClient.js | 113 ++++++++++++++++++++++++++++++++++-------- 1 file changed, 93 insertions(+), 20 deletions(-) diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index ddb1487b..bc38d70f 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -20,6 +20,7 @@ import Spotlights from './Spotlights'; import { permissions } from './permissions'; import * as locales from './translations/locales'; import { createIntl } from 'react-intl'; +import { parseScalabilityMode } from 'mediasoup-client'; let createTorrent; @@ -102,6 +103,67 @@ const VIDEO_SVC_ENCODINGS = { scalabilityMode: 'S3T3', dtx: true } ]; +/** + * Validates the simulcast `encodings` array extracting the resolution scalings + * array. + * ref. https://www.w3.org/TR/webrtc/#rtp-media-api + * + * @param {*} encodings + * @returns the resolution scalings array + */ +function getResolutionScalings(encodings) +{ + const resolutionScalings = []; + + // SVC encodings + if (encodings.length === 1) + { + const { spatialLayers, temporalLayers } = + mediasoupClient.parseScalabilityMode(encodings[0].scalabilityMode); + + for (let i=0; i < spatialLayers; i++) + { + resolutionScalings.push(2 ** (spatialLayers - i - 1)); + } + + return resolutionScalings; + } + + // Simulcast encodings + let scaleResolutionDownByDefined = false; + + encodings.forEach((encoding) => + { + if (encoding.scaleResolutionDownBy !== undefined) + { + // at least one scaleResolutionDownBy is defined + scaleResolutionDownByDefined = true; + // scaleResolutionDownBy must be >= 1.0 + resolutionScalings.push(Math.max(1.0, encoding.scaleResolutionDownBy)); + } + else + { + // If encodings contains any encoding whose scaleResolutionDownBy + // attribute is defined, set any undefined scaleResolutionDownBy + // of the other encodings to 1.0. + resolutionScalings.push(1.0); + } + }); + + // If the scaleResolutionDownBy attribues of sendEncodings are + // still undefined, initialize each encoding's scaleResolutionDownBy + // to 2^(length of sendEncodings - encoding index - 1). + if (!scaleResolutionDownByDefined) + { + encodings.forEach((encoding, index) => + { + resolutionScalings[index] = 2 ** (encodings.length - index - 1); + }); + } + + return resolutionScalings; +} + let store; let intl; @@ -1518,6 +1580,8 @@ export default class RoomClient else encodings = VIDEO_SIMULCAST_ENCODINGS; + const resolutionScalings = getResolutionScalings(encodings); + this._webcamProducer = await this._sendTransport.produce( { track, @@ -1530,7 +1594,8 @@ export default class RoomClient { source : 'webcam', width, - height + height, + resolutionScalings } }); } @@ -2168,23 +2233,30 @@ export default class RoomClient return; } - const { id, preferredSpatialLayer, preferredTemporalLayer, width, height } = consumer; + const { + id, + preferredSpatialLayer, + preferredTemporalLayer, + width, + height, + resolutionScalings + } = consumer; const availableArea = Math.round(viewportWidth * viewportHeight); logger.debug( - 'adaptConsumerPreferredLayers() [consumerId:"%s", width:"%d", height:"%d" viewportWidth:"%d", viewportHeight:"%d"]', - consumer.id, width, height, viewportWidth, viewportHeight); + 'adaptConsumerPreferredLayers() [consumerId:"%s", width:"%d", height:"%d" resolutionScalings:[%s] viewportWidth:"%d", viewportHeight:"%d"]', + consumer.id, width, height, resolutionScalings.join(', '), + viewportWidth, viewportHeight); - let spatialLayer = 0; + let newPreferredSpatialLayer = 0; - for (let i = 0; i < window.config.simulcastEncodings.length; i++) + for (let i = 0; i < resolutionScalings.length; i++) { - const levelArea = width * height / - (window.config.simulcastEncodings[i].scaleResolutionDownBy ** 2); + const levelArea = width * height / (resolutionScalings[i] ** 2); if (availableArea >= levelArea) { - spatialLayer = i; + newPreferredSpatialLayer = i; } else { @@ -2192,27 +2264,27 @@ export default class RoomClient } } - let temporalLayer = consumer.temporalLayers - 1; + let newPreferredTemporalLayer = consumer.temporalLayers - 1; - if (spatialLayer === 0) + if (newPreferredSpatialLayer === 0) { - const lowestLevelArea = width * height / - (window.config.simulcastEncodings[0].scaleResolutionDownBy ** 2); + const lowestLevelArea = width * height / (resolutionScalings[0] ** 2); - if (availableArea < lowestLevelArea * 0.5) + if (availableArea < lowestLevelArea * 0.5 && newPreferredTemporalLayer > 0) { - temporalLayer = 1; + newPreferredTemporalLayer -= 1; } - if (availableArea < lowestLevelArea * 0.25) + if (availableArea < lowestLevelArea * 0.25 && newPreferredTemporalLayer > 0) { - temporalLayer = 0; + newPreferredTemporalLayer -= 1; } } - if (preferredSpatialLayer !== spatialLayer || - preferredTemporalLayer !== temporalLayer) + if (preferredSpatialLayer !== newPreferredSpatialLayer || + preferredTemporalLayer !== newPreferredTemporalLayer) { - return this.setConsumerPreferredLayers(id, spatialLayer, temporalLayer); + return this.setConsumerPreferredLayers(id, + newPreferredSpatialLayer, newPreferredTemporalLayer); } } @@ -2479,6 +2551,7 @@ export default class RoomClient source : consumer.appData.source, width : consumer.appData.width, height : consumer.appData.height, + resolutionScalings : consumer.appData.resolutionScalings, spatialLayers : spatialLayers, temporalLayers : temporalLayers, preferredSpatialLayer : spatialLayers - 1, From b7f07dcce9466204a901122dc881bc58af28b250 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?M=C3=A9sz=C3=A1ros=20Mih=C3=A1ly?= Date: Mon, 22 Feb 2021 10:36:22 +0100 Subject: [PATCH 22/24] Update promExporter.js Await metrics data Fix docker issue: UnhandledPromiseRejectionWarning at /opt/edumeet/server/lib/promExporter.js:272:8 TODO: Maybe we need to add more error handling to make it more robust. --- server/lib/promExporter.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/lib/promExporter.js b/server/lib/promExporter.js index 82bb7a13..3f921abf 100644 --- a/server/lib/promExporter.js +++ b/server/lib/promExporter.js @@ -267,7 +267,7 @@ module.exports = async function(rooms, peers, config) await collect(registry); res.set('Content-Type', registry.contentType); - const data = registry.metrics(); + const data = await registry.metrics(); res.end(data); }); From 9c87b9c60d2872044dd10bd8cf76a74055455887 Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Thu, 25 Feb 2021 18:04:45 +0100 Subject: [PATCH 23/24] added `adaptiveScalingFactor` configuration variable (#701) * added `adaptiveScalingFactor` configuration variable * adapt consumer layers using viewport width and height --- app/public/config/config.example.js | 5 +++++ app/src/RoomClient.js | 20 +++++++++++++------- 2 files changed, 18 insertions(+), 7 deletions(-) diff --git a/app/public/config/config.example.js b/app/public/config/config.example.js index 71e2645c..16836056 100644 --- a/app/public/config/config.example.js +++ b/app/public/config/config.example.js @@ -77,6 +77,11 @@ var config = { scaleResolutionDownBy: 2 }, { scaleResolutionDownBy: 1 } ], + // The adaptive spatial layer selection scaling factor (in the range [0.5, 1.0]) + // example: + // with level width=640px, the minimum width required to trigger the + // level change will be: 640 * 0.75 = 480px + adaptiveScalingFactor: 0.75, /** * Alternative simulcast setting: diff --git a/app/src/RoomClient.js b/app/src/RoomClient.js index bc38d70f..02ad2896 100644 --- a/app/src/RoomClient.js +++ b/app/src/RoomClient.js @@ -2241,7 +2241,8 @@ export default class RoomClient height, resolutionScalings } = consumer; - const availableArea = Math.round(viewportWidth * viewportHeight); + const adaptiveScalingFactor = Math.min(Math.max( + window.config.adaptiveScalingFactor || 0.75, 0.5), 1.0); logger.debug( 'adaptConsumerPreferredLayers() [consumerId:"%s", width:"%d", height:"%d" resolutionScalings:[%s] viewportWidth:"%d", viewportHeight:"%d"]', @@ -2252,9 +2253,10 @@ export default class RoomClient for (let i = 0; i < resolutionScalings.length; i++) { - const levelArea = width * height / (resolutionScalings[i] ** 2); + const levelWidth = adaptiveScalingFactor * width / resolutionScalings[i]; + const levelHeight = adaptiveScalingFactor * height / resolutionScalings[i]; - if (availableArea >= levelArea) + if (viewportWidth >= levelWidth || viewportHeight >= levelHeight) { newPreferredSpatialLayer = i; } @@ -2266,15 +2268,19 @@ export default class RoomClient let newPreferredTemporalLayer = consumer.temporalLayers - 1; - if (newPreferredSpatialLayer === 0) + if (newPreferredSpatialLayer === 0 && newPreferredTemporalLayer > 0) { - const lowestLevelArea = width * height / (resolutionScalings[0] ** 2); + const lowestLevelWidth = width / resolutionScalings[0]; + const lowestLevelHeight = height / resolutionScalings[0]; - if (availableArea < lowestLevelArea * 0.5 && newPreferredTemporalLayer > 0) + if (viewportWidth < lowestLevelWidth * 0.5 + && viewportHeight < lowestLevelHeight * 0.5) { newPreferredTemporalLayer -= 1; } - if (availableArea < lowestLevelArea * 0.25 && newPreferredTemporalLayer > 0) + if (newPreferredTemporalLayer > 0 + && viewportWidth < lowestLevelWidth * 0.25 + && viewportHeight < lowestLevelHeight * 0.25) { newPreferredTemporalLayer -= 1; } From 5c35671e4f435dce11e10f6bda3215f3cfeda6d9 Mon Sep 17 00:00:00 2001 From: Vittorio Palmisano Date: Wed, 3 Mar 2021 13:41:26 +0100 Subject: [PATCH 24/24] distribute workers port ranges, closes #708 (#709) * distribute workers port ranges, closes #708 * fixed i index increment --- server/server.js | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/server/server.js b/server/server.js index a348fe14..02dfaee5 100755 --- a/server/server.js +++ b/server/server.js @@ -794,14 +794,18 @@ async function runMediasoupWorkers() logger.info('running %d mediasoup Workers...', numWorkers); - for (let i = 0; i < numWorkers; ++i) + const { logLevel, logTags, rtcMinPort, rtcMaxPort } = config.mediasoup.worker; + const portInterval = Math.floor((rtcMaxPort - rtcMinPort) / numWorkers); + + for (let i = 0; i < numWorkers; i++) { const worker = await mediasoup.createWorker( { - logLevel : config.mediasoup.worker.logLevel, - logTags : config.mediasoup.worker.logTags, - rtcMinPort : config.mediasoup.worker.rtcMinPort, - rtcMaxPort : config.mediasoup.worker.rtcMaxPort + logLevel, + logTags, + rtcMinPort : rtcMinPort + i * portInterval, + rtcMaxPort : i === numWorkers - 1 ? rtcMaxPort + : rtcMinPort + (i + 1) * portInterval - 1 }); worker.on('died', () =>