Merge pull request #189 from TeaSpeak/develop

Develop
master^2
WolverinDEV 2021-07-11 14:23:30 +02:00 committed by GitHub
commit 508706c93a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
29 changed files with 493 additions and 464 deletions

View File

@ -1,4 +1,11 @@
# Changelog: # Changelog:
* **11.06.21**
- Fixed the bug that cause the file transfer to timeout if the user hasn't been quick enough to save his file
- Fixed the emoji picker being cut off
- Fixed the file transfer sidebar not working
- Instantly reflect changes to the server icon for the bookmark menu bar
- Fixed a bug which prevented the proper context menu appear within the bookmark manage modal
* **26.05.21** * **26.05.21**
- Fixed automated builds - Fixed automated builds
- Fixed the bookmark UI popout window - Fixed the bookmark UI popout window

661
package-lock.json generated
View File

@ -344,16 +344,24 @@
} }
}, },
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"chalk": { "chalk": {
@ -377,9 +385,9 @@
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.695", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.695.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-lz66RliUqLHU1Ojxx1A4QUxKydjiQ79Y4dZyPobs2Dmxj5aVL2TM3KoQ2Gs7HS703Bfny+ukI3KOxwAB0xceHQ==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"escalade": { "escalade": {
@ -395,9 +403,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
}, },
"semver": { "semver": {
@ -2215,16 +2223,24 @@
} }
}, },
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"chalk": { "chalk": {
@ -2248,9 +2264,9 @@
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.695", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.695.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-lz66RliUqLHU1Ojxx1A4QUxKydjiQ79Y4dZyPobs2Dmxj5aVL2TM3KoQ2Gs7HS703Bfny+ukI3KOxwAB0xceHQ==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"escalade": { "escalade": {
@ -2281,9 +2297,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
}, },
"semver": { "semver": {
@ -3248,16 +3264,24 @@
} }
}, },
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"chalk": { "chalk": {
@ -3299,9 +3323,9 @@
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.695", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.695.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-lz66RliUqLHU1Ojxx1A4QUxKydjiQ79Y4dZyPobs2Dmxj5aVL2TM3KoQ2Gs7HS703Bfny+ukI3KOxwAB0xceHQ==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"escalade": { "escalade": {
@ -3343,9 +3367,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
}, },
"regexpu-core": { "regexpu-core": {
@ -4225,6 +4249,26 @@
"integrity": "sha1-qCJQ3bABXponyoLoLqYDu/pF768=", "integrity": "sha1-qCJQ3bABXponyoLoLqYDu/pF768=",
"dev": true "dev": true
}, },
"anymatch": {
"version": "3.1.2",
"resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz",
"integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==",
"dev": true,
"optional": true,
"requires": {
"normalize-path": "^3.0.0",
"picomatch": "^2.0.4"
},
"dependencies": {
"normalize-path": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz",
"integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==",
"dev": true,
"optional": true
}
}
},
"append-buffer": { "append-buffer": {
"version": "1.0.2", "version": "1.0.2",
"resolved": "https://registry.npmjs.org/append-buffer/-/append-buffer-1.0.2.tgz", "resolved": "https://registry.npmjs.org/append-buffer/-/append-buffer-1.0.2.tgz",
@ -4534,22 +4578,30 @@
}, },
"dependencies": { "dependencies": {
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.690", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.690.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-zPbaSv1c8LUKqQ+scNxJKv01RYFkVVF1xli+b+3Ty8ONujHjAMg+t/COmdZqrtnS1gT+g4hbSodHillymt1Lww==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"escalade": { "escalade": {
@ -4559,9 +4611,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
} }
} }
@ -5034,16 +5086,24 @@
}, },
"dependencies": { "dependencies": {
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"core-js-compat": { "core-js-compat": {
@ -5057,9 +5117,9 @@
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.695", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.695.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-lz66RliUqLHU1Ojxx1A4QUxKydjiQ79Y4dZyPobs2Dmxj5aVL2TM3KoQ2Gs7HS703Bfny+ukI3KOxwAB0xceHQ==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"escalade": { "escalade": {
@ -5069,9 +5129,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
}, },
"semver": { "semver": {
@ -5977,15 +6037,42 @@
} }
}, },
"browserslist": { "browserslist": {
"version": "4.13.0", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.13.0.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-MINatJ5ZNrLnQ6blGvePd/QOz9Xtu+Ne+x29iQSCHfkU5BugKVJwZKn/iiL8UbpIpa3JhviKjz+XxMo0m2caFQ==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001093", "caniuse-lite": "^1.0.30001219",
"electron-to-chromium": "^1.3.488", "colorette": "^1.2.2",
"escalade": "^3.0.1", "electron-to-chromium": "^1.3.723",
"node-releases": "^1.1.58" "escalade": "^3.1.1",
"node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
},
"electron-to-chromium": {
"version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true
},
"escalade": {
"version": "3.1.1",
"resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz",
"integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==",
"dev": true
},
"node-releases": {
"version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true
}
} }
}, },
"buffer": { "buffer": {
@ -6305,6 +6392,66 @@
"integrity": "sha512-YpeKZngUmG65rLudJ4taU7VLkOCTMhNl/u4ctNC56LQS/zJTyNH0Lrtwm1tfTsbLlwvlfsA2d1c8vCf/Kh2KwQ==", "integrity": "sha512-YpeKZngUmG65rLudJ4taU7VLkOCTMhNl/u4ctNC56LQS/zJTyNH0Lrtwm1tfTsbLlwvlfsA2d1c8vCf/Kh2KwQ==",
"dev": true "dev": true
}, },
"chokidar": {
"version": "3.5.1",
"resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.1.tgz",
"integrity": "sha512-9+s+Od+W0VJJzawDma/gvBNQqkTiqYTWLuZoyAsivsI4AaWTCzHG06/TMjsf1cYe9Cb97UCEhjz7HvnPk2p/tw==",
"dev": true,
"optional": true,
"requires": {
"anymatch": "~3.1.1",
"braces": "~3.0.2",
"fsevents": "~2.3.1",
"glob-parent": "~5.1.0",
"is-binary-path": "~2.1.0",
"is-glob": "~4.0.1",
"normalize-path": "~3.0.0",
"readdirp": "~3.5.0"
},
"dependencies": {
"binary-extensions": {
"version": "2.2.0",
"resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz",
"integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==",
"dev": true,
"optional": true
},
"fsevents": {
"version": "2.3.2",
"resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz",
"integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==",
"dev": true,
"optional": true
},
"is-binary-path": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz",
"integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==",
"dev": true,
"optional": true,
"requires": {
"binary-extensions": "^2.0.0"
}
},
"normalize-path": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz",
"integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==",
"dev": true,
"optional": true
},
"readdirp": {
"version": "3.5.0",
"resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.5.0.tgz",
"integrity": "sha512-cMhu7c/8rdhkHXWsY+osBhfSy0JikwpHK/5+imo+LpeasTF8ouErHrlYkwT0++njiyuDvc7OFY5T3ukvZ8qmFQ==",
"dev": true,
"optional": true,
"requires": {
"picomatch": "^2.2.1"
}
}
}
},
"chrome-trace-event": { "chrome-trace-event": {
"version": "1.0.2", "version": "1.0.2",
"resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.2.tgz", "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.2.tgz",
@ -7977,9 +8124,9 @@
} }
}, },
"dompurify": { "dompurify": {
"version": "2.0.8", "version": "2.2.8",
"resolved": "https://registry.npmjs.org/dompurify/-/dompurify-2.0.8.tgz", "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-2.2.8.tgz",
"integrity": "sha512-vIOSyOXkMx81ghEalh4MLBtDHMx1bhKlaqHDMqM2yeitJ996SLOk5mGdDpI9ifJAgokred8Rmu219fX4OltqXw==" "integrity": "sha512-9H0UL59EkDLgY3dUFjLV6IEUaHm5qp3mxSqWw7Yyx4Zhk2Jn2cmLe+CNPP3xy13zl8Bqg+0NehQzkdMoVhGRww=="
}, },
"domutils": { "domutils": {
"version": "2.0.0", "version": "2.0.0",
@ -8070,12 +8217,6 @@
"integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=", "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=",
"dev": true "dev": true
}, },
"electron-to-chromium": {
"version": "1.3.496",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.496.tgz",
"integrity": "sha512-TXY4mwoyowwi4Lsrq9vcTUYBThyc1b2hXaTZI13p8/FRhY2CTaq5lK+DVjhYkKiTLsKt569Xes+0J5JsVXFurQ==",
"dev": true
},
"elliptic": { "elliptic": {
"version": "6.5.4", "version": "6.5.4",
"resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.5.4.tgz", "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.5.4.tgz",
@ -8293,12 +8434,6 @@
"es6-symbol": "^3.1.1" "es6-symbol": "^3.1.1"
} }
}, },
"escalade": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/escalade/-/escalade-3.0.1.tgz",
"integrity": "sha512-DR6NO3h9niOT+MZs7bjxlj2a1k+POu5RN8CLTPX2+i78bRi9eLe7+0zXgUHMnGXWybYcL61E9hGhPKqedy8tQA==",
"dev": true
},
"escape-goat": { "escape-goat": {
"version": "2.1.1", "version": "2.1.1",
"resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz",
@ -11697,9 +11832,9 @@
"integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="
}, },
"ini": { "ini": {
"version": "1.3.5", "version": "1.3.8",
"resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz",
"integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==",
"dev": true "dev": true
}, },
"inline-chunks-html-webpack-plugin": { "inline-chunks-html-webpack-plugin": {
@ -13588,9 +13723,9 @@
"integrity": "sha512-INOFj37C7k3AfaNTtX8RhsTw7qRy7eLET14cROi9+5HAVbbHuIWUHEauBv5qT4Av2tWasiTY1Jw6puUNqRJXQg==" "integrity": "sha512-INOFj37C7k3AfaNTtX8RhsTw7qRy7eLET14cROi9+5HAVbbHuIWUHEauBv5qT4Av2tWasiTY1Jw6puUNqRJXQg=="
}, },
"nanoid": { "nanoid": {
"version": "3.1.22", "version": "3.1.23",
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.22.tgz", "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.23.tgz",
"integrity": "sha512-/2ZUaJX2ANuLtTvqTlgqBQNJoQO398KyJgZloL0PZkC0dpysjncRUPsFe3DUPzz/y3h+u7C46np8RMuvF3jsSQ==", "integrity": "sha512-FiB0kzdP0FFVGDKlRLEQ1BgDzU87dy5NnzjeW9YZNt+/c3+q82EQDUwniSAUxp/F0gFNI1ZhKU1FqYsMuqZVnw==",
"dev": true "dev": true
}, },
"nanomatch": { "nanomatch": {
@ -13702,12 +13837,6 @@
} }
} }
}, },
"node-releases": {
"version": "1.1.59",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.59.tgz",
"integrity": "sha512-H3JrdUczbdiwxN5FuJPyCHnGHIFqQ0wWxo+9j1kAXAzqNMAHlo+4I/sYYxpyK0irQ73HgdiyzD32oqQDcU2Osw==",
"dev": true
},
"node-sass": { "node-sass": {
"version": "4.14.1", "version": "4.14.1",
"resolved": "https://registry.npmjs.org/node-sass/-/node-sass-4.14.1.tgz", "resolved": "https://registry.npmjs.org/node-sass/-/node-sass-4.14.1.tgz",
@ -14504,14 +14633,14 @@
"integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=" "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs="
}, },
"postcss": { "postcss": {
"version": "8.2.8", "version": "8.3.0",
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.2.8.tgz", "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.3.0.tgz",
"integrity": "sha512-1F0Xb2T21xET7oQV9eKuctbM9S7BC0fetoHCc4H13z0PT6haiRLP4T0ZY4XWh7iLP0usgqykT6p9B2RtOf4FPw==", "integrity": "sha512-+ogXpdAjWGa+fdYY5BQ96V/6tAo+TdSSIMP5huJBIygdWwKtVoB5JWZ7yUd4xZ8r+8Kvvx4nyg/PQ071H4UtcQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"colorette": "^1.2.2", "colorette": "^1.2.2",
"nanoid": "^3.1.20", "nanoid": "^3.1.23",
"source-map": "^0.6.1" "source-map-js": "^0.6.2"
} }
}, },
"postcss-calc": { "postcss-calc": {
@ -18671,6 +18800,12 @@
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
"integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g=="
}, },
"source-map-js": {
"version": "0.6.2",
"resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-0.6.2.tgz",
"integrity": "sha512-/3GptzWzu0+0MBQFrDKzw/DvvMTUORvgY6k6jd/VS6iCR4RDTKWH6v6WPwQoUO8667uQEf9Oe38DxAYWY5F/Ug==",
"dev": true
},
"source-map-resolve": { "source-map-resolve": {
"version": "0.5.3", "version": "0.5.3",
"resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.3.tgz", "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.3.tgz",
@ -20587,14 +20722,25 @@
"dev": true "dev": true
}, },
"watchpack": { "watchpack": {
"version": "1.6.1", "version": "1.7.5",
"resolved": "https://registry.npmjs.org/watchpack/-/watchpack-1.6.1.tgz", "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-1.7.5.tgz",
"integrity": "sha512-+IF9hfUFOrYOOaKyfaI7h7dquUIOgyEMoQMLA7OP5FxegKA2+XdXThAZ9TU2kucfhDH7rfMHs1oPYziVGWRnZA==", "integrity": "sha512-9P3MWk6SrKjHsGkLT2KHXdQ/9SNkyoJbabxnKOoJepsvJjJG8uYTR3yTPxPQvNDI3w4Nz1xnE0TLHK4RIVe/MQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"chokidar": "^2.1.8", "chokidar": "^3.4.1",
"graceful-fs": "^4.1.2", "graceful-fs": "^4.1.2",
"neo-async": "^2.5.0" "neo-async": "^2.5.0",
"watchpack-chokidar2": "^2.0.1"
}
},
"watchpack-chokidar2": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/watchpack-chokidar2/-/watchpack-chokidar2-2.0.1.tgz",
"integrity": "sha512-nCFfBIPKr5Sh61s4LPpy1Wtfi0HE8isJ3d2Yb5/Ppw2P2B/3eVSEBjKfN0fmHJSK14+31KwMKmcrzs2GM4P0Ww==",
"dev": true,
"optional": true,
"requires": {
"chokidar": "^2.1.8"
}, },
"dependencies": { "dependencies": {
"anymatch": { "anymatch": {
@ -20602,6 +20748,7 @@
"resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz",
"integrity": "sha512-5teOsQWABXHHBFP9y3skS5P3d/WfWXpv3FUpy+LorMrNYaT9pI4oLMQX7jzQ2KklNpGpWHzdCXTDT2Y3XGlZBw==", "integrity": "sha512-5teOsQWABXHHBFP9y3skS5P3d/WfWXpv3FUpy+LorMrNYaT9pI4oLMQX7jzQ2KklNpGpWHzdCXTDT2Y3XGlZBw==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"micromatch": "^3.1.4", "micromatch": "^3.1.4",
"normalize-path": "^2.1.1" "normalize-path": "^2.1.1"
@ -20612,29 +20759,19 @@
"resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz",
"integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"remove-trailing-separator": "^1.0.1" "remove-trailing-separator": "^1.0.1"
} }
} }
} }
}, },
"arr-diff": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz",
"integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=",
"dev": true
},
"array-unique": {
"version": "0.3.2",
"resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz",
"integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=",
"dev": true
},
"braces": { "braces": {
"version": "2.3.2", "version": "2.3.2",
"resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz",
"integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"arr-flatten": "^1.1.0", "arr-flatten": "^1.1.0",
"array-unique": "^0.3.2", "array-unique": "^0.3.2",
@ -20646,17 +20783,6 @@
"snapdragon-node": "^2.0.1", "snapdragon-node": "^2.0.1",
"split-string": "^3.0.2", "split-string": "^3.0.2",
"to-regex": "^3.0.1" "to-regex": "^3.0.1"
},
"dependencies": {
"extend-shallow": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true,
"requires": {
"is-extendable": "^0.1.0"
}
}
} }
}, },
"chokidar": { "chokidar": {
@ -20664,6 +20790,7 @@
"resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.8.tgz", "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.8.tgz",
"integrity": "sha512-ZmZUazfOzf0Nve7duiCKD23PFSCs4JPoYyccjUFF3aQkQadqBhfzhjkwBH2mNOG9cTBwhamM37EIsIkZw3nRgg==", "integrity": "sha512-ZmZUazfOzf0Nve7duiCKD23PFSCs4JPoYyccjUFF3aQkQadqBhfzhjkwBH2mNOG9cTBwhamM37EIsIkZw3nRgg==",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"anymatch": "^2.0.0", "anymatch": "^2.0.0",
"async-each": "^1.0.1", "async-each": "^1.0.1",
@ -20679,132 +20806,14 @@
"upath": "^1.1.1" "upath": "^1.1.1"
} }
}, },
"expand-brackets": { "extend-shallow": {
"version": "2.1.4", "version": "2.0.1",
"resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"debug": "^2.3.3", "is-extendable": "^0.1.0"
"define-property": "^0.2.5",
"extend-shallow": "^2.0.1",
"posix-character-classes": "^0.1.0",
"regex-not": "^1.0.0",
"snapdragon": "^0.8.1",
"to-regex": "^3.0.1"
},
"dependencies": {
"define-property": {
"version": "0.2.5",
"resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz",
"integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=",
"dev": true,
"requires": {
"is-descriptor": "^0.1.0"
}
},
"extend-shallow": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true,
"requires": {
"is-extendable": "^0.1.0"
}
},
"is-accessor-descriptor": {
"version": "0.1.6",
"resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz",
"integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=",
"dev": true,
"requires": {
"kind-of": "^3.0.2"
},
"dependencies": {
"kind-of": {
"version": "3.2.2",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
"integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
"dev": true,
"requires": {
"is-buffer": "^1.1.5"
}
}
}
},
"is-data-descriptor": {
"version": "0.1.4",
"resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
"integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=",
"dev": true,
"requires": {
"kind-of": "^3.0.2"
},
"dependencies": {
"kind-of": {
"version": "3.2.2",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
"integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
"dev": true,
"requires": {
"is-buffer": "^1.1.5"
}
}
}
},
"is-descriptor": {
"version": "0.1.6",
"resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz",
"integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==",
"dev": true,
"requires": {
"is-accessor-descriptor": "^0.1.6",
"is-data-descriptor": "^0.1.4",
"kind-of": "^5.0.0"
}
},
"kind-of": {
"version": "5.1.0",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz",
"integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==",
"dev": true
}
}
},
"extglob": {
"version": "2.0.4",
"resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz",
"integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==",
"dev": true,
"requires": {
"array-unique": "^0.3.2",
"define-property": "^1.0.0",
"expand-brackets": "^2.1.4",
"extend-shallow": "^2.0.1",
"fragment-cache": "^0.2.1",
"regex-not": "^1.0.0",
"snapdragon": "^0.8.1",
"to-regex": "^3.0.1"
},
"dependencies": {
"define-property": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz",
"integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=",
"dev": true,
"requires": {
"is-descriptor": "^1.0.0"
}
},
"extend-shallow": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true,
"requires": {
"is-extendable": "^0.1.0"
}
}
} }
}, },
"fill-range": { "fill-range": {
@ -20812,22 +20821,12 @@
"resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz",
"integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"extend-shallow": "^2.0.1", "extend-shallow": "^2.0.1",
"is-number": "^3.0.0", "is-number": "^3.0.0",
"repeat-string": "^1.6.1", "repeat-string": "^1.6.1",
"to-regex-range": "^2.1.0" "to-regex-range": "^2.1.0"
},
"dependencies": {
"extend-shallow": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
"integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
"dev": true,
"requires": {
"is-extendable": "^0.1.0"
}
}
} }
}, },
"glob-parent": { "glob-parent": {
@ -20835,6 +20834,7 @@
"resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz",
"integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"is-glob": "^3.1.0", "is-glob": "^3.1.0",
"path-dirname": "^1.0.0" "path-dirname": "^1.0.0"
@ -20845,114 +20845,29 @@
"resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz",
"integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"is-extglob": "^2.1.0" "is-extglob": "^2.1.0"
} }
} }
} }
}, },
"is-accessor-descriptor": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz",
"integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==",
"dev": true,
"requires": {
"kind-of": "^6.0.0"
}
},
"is-data-descriptor": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz",
"integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==",
"dev": true,
"requires": {
"kind-of": "^6.0.0"
}
},
"is-descriptor": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz",
"integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==",
"dev": true,
"requires": {
"is-accessor-descriptor": "^1.0.0",
"is-data-descriptor": "^1.0.0",
"kind-of": "^6.0.2"
}
},
"is-extglob": {
"version": "2.1.1",
"resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz",
"integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=",
"dev": true
},
"is-glob": {
"version": "4.0.1",
"resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz",
"integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==",
"dev": true,
"requires": {
"is-extglob": "^2.1.1"
}
},
"is-number": { "is-number": {
"version": "3.0.0", "version": "3.0.0",
"resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz",
"integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=",
"dev": true, "dev": true,
"optional": true,
"requires": { "requires": {
"kind-of": "^3.0.2" "kind-of": "^3.0.2"
},
"dependencies": {
"kind-of": {
"version": "3.2.2",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
"integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
"dev": true,
"requires": {
"is-buffer": "^1.1.5"
}
}
}
},
"isobject": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
"integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
"dev": true
},
"kind-of": {
"version": "6.0.3",
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz",
"integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==",
"dev": true
},
"micromatch": {
"version": "3.1.10",
"resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz",
"integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==",
"dev": true,
"requires": {
"arr-diff": "^4.0.0",
"array-unique": "^0.3.2",
"braces": "^2.3.1",
"define-property": "^2.0.2",
"extend-shallow": "^3.0.2",
"extglob": "^2.0.4",
"fragment-cache": "^0.2.1",
"kind-of": "^6.0.2",
"nanomatch": "^1.2.9",
"object.pick": "^1.3.0",
"regex-not": "^1.0.0",
"snapdragon": "^0.8.1",
"to-regex": "^3.0.2"
} }
}, },
"normalize-path": { "normalize-path": {
"version": "3.0.0", "version": "3.0.0",
"resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz",
"integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==",
"dev": true "dev": true,
"optional": true
} }
} }
}, },
@ -21064,22 +20979,30 @@
"dev": true "dev": true
}, },
"browserslist": { "browserslist": {
"version": "4.16.3", "version": "4.16.6",
"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.3.tgz", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.16.6.tgz",
"integrity": "sha512-vIyhWmIkULaq04Gt93txdh+j02yX/JzlyhLYbV3YQCn/zvES3JnY7TifHHvvr1w5hTDluNKMkV05cs4vy8Q7sw==", "integrity": "sha512-Wspk/PqO+4W9qp5iUTJsa1B/QrYn1keNCcEP5OvP7WBwT4KaDly0uONYmC6Xa3Z5IqnUgS0KcgLYu1l74x0ZXQ==",
"dev": true, "dev": true,
"requires": { "requires": {
"caniuse-lite": "^1.0.30001181", "caniuse-lite": "^1.0.30001219",
"colorette": "^1.2.1", "colorette": "^1.2.2",
"electron-to-chromium": "^1.3.649", "electron-to-chromium": "^1.3.723",
"escalade": "^3.1.1", "escalade": "^3.1.1",
"node-releases": "^1.1.70" "node-releases": "^1.1.71"
},
"dependencies": {
"caniuse-lite": {
"version": "1.0.30001230",
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001230.tgz",
"integrity": "sha512-5yBd5nWCBS+jWKTcHOzXwo5xzcj4ePE/yjtkZyUV1BTUmrBaA9MRGC+e7mxnqXSA90CmCA8L3eKLaSUkt099IQ==",
"dev": true
}
} }
}, },
"electron-to-chromium": { "electron-to-chromium": {
"version": "1.3.690", "version": "1.3.739",
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.690.tgz", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.739.tgz",
"integrity": "sha512-zPbaSv1c8LUKqQ+scNxJKv01RYFkVVF1xli+b+3Ty8ONujHjAMg+t/COmdZqrtnS1gT+g4hbSodHillymt1Lww==", "integrity": "sha512-+LPJVRsN7hGZ9EIUUiWCpO7l4E3qBYHNadazlucBfsXBbccDFNKUBAgzE68FnkWGJPwD/AfKhSzL+G+Iqb8A4A==",
"dev": true "dev": true
}, },
"enhanced-resolve": { "enhanced-resolve": {
@ -21126,9 +21049,9 @@
"dev": true "dev": true
}, },
"node-releases": { "node-releases": {
"version": "1.1.71", "version": "1.1.72",
"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.71.tgz", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.72.tgz",
"integrity": "sha512-zR6HoT6LrLCRBwukmrVbHv0EpEQjksO6GmFcZQQuCAy139BEsoVKPYnf3jongYW83fAa1torLGYwxxky/p28sg==", "integrity": "sha512-LLUo+PpH3dU6XizX3iVoubUNheF/owjXCZZ5yACDxNnPtgFuludV1ZL3ayK1kVep42Rmm0+R9/Y60NQbZ2bifw==",
"dev": true "dev": true
}, },
"p-limit": { "p-limit": {

View File

@ -65,7 +65,7 @@
"mini-css-extract-plugin": "^1.3.9", "mini-css-extract-plugin": "^1.3.9",
"mkdirp": "^0.5.1", "mkdirp": "^0.5.1",
"node-sass": "^4.14.1", "node-sass": "^4.14.1",
"postcss": "^8.2.8", "postcss": "^8.3.0",
"postcss-loader": "^5.2.0", "postcss-loader": "^5.2.0",
"potpack": "^1.0.1", "potpack": "^1.0.1",
"raw-loader": "^4.0.0", "raw-loader": "^4.0.0",
@ -103,7 +103,7 @@
"crypto-browserify": "^3.12.0", "crypto-browserify": "^3.12.0",
"crypto-js": "^4.0.0", "crypto-js": "^4.0.0",
"detect-browser": "^5.2.0", "detect-browser": "^5.2.0",
"dompurify": "^2.0.8", "dompurify": "^2.2.8",
"emoji-mart": "git+https://github.com/WolverinDEV/emoji-mart.git", "emoji-mart": "git+https://github.com/WolverinDEV/emoji-mart.git",
"emoji-regex": "^9.0.0", "emoji-regex": "^9.0.0",
"highlight.js": "^10.1.1", "highlight.js": "^10.1.1",

View File

@ -2,9 +2,10 @@ import {LogCategory, logError, logWarn} from "tc-shared/log";
import {tr, tra} from "tc-shared/i18n/localize"; import {tr, tra} from "tc-shared/i18n/localize";
import * as loader from "tc-loader"; import * as loader from "tc-loader";
import {Stage} from "tc-loader"; import {Stage} from "tc-loader";
import {ConnectionHandler} from "tc-shared/ConnectionHandler"; import {ConnectionHandler, ConnectionState} from "tc-shared/ConnectionHandler";
import {server_connections} from "tc-shared/ConnectionManager"; import {server_connections} from "tc-shared/ConnectionManager";
import {ServerProperties} from "tc-shared/tree/Server"; import {ServerProperties} from "tc-shared/tree/Server";
import {Registry} from "tc-events";
export const kUnknownHistoryServerUniqueId = "unknown"; export const kUnknownHistoryServerUniqueId = "unknown";
@ -44,10 +45,17 @@ export type ConnectionHistoryServerInfo = {
passwordProtected: boolean passwordProtected: boolean
} }
export interface ConnectionHistoryEvents {
notify_server_info_updated: { serverUniqueId: string, keys: (keyof ConnectionHistoryServerInfo)[] }
}
export class ConnectionHistory { export class ConnectionHistory {
readonly events: Registry<ConnectionHistoryEvents>;
private database: IDBDatabase; private database: IDBDatabase;
constructor() { } constructor() {
this.events = new Registry<ConnectionHistoryEvents>();
}
async initializeDatabase() { async initializeDatabase() {
const openRequest = indexedDB.open("connection-log", 1); const openRequest = indexedDB.open("connection-log", 1);
@ -306,16 +314,29 @@ export class ConnectionHistory {
return; return;
} }
await this.updateDatabaseServerInfo(serverUniqueId, databaseValue => { await this.updateDatabaseServerInfo(serverUniqueId, databaseValue => {
databaseValue.name = info.name; const changes: (keyof ConnectionHistoryServerInfo)[] = [];
databaseValue.iconId = info.iconId; const updateValue = (databaseKey: string, infoKey: keyof ConnectionHistoryServerInfo) => {
if(databaseValue[databaseKey] === info[infoKey]) {
return;
}
databaseValue.clientsOnline = info.clientsOnline; databaseValue[databaseKey] = info[infoKey];
databaseValue.clientsMax = info.clientsMax; changes.push(infoKey);
}
databaseValue.hostBannerUrl = info.hostBannerUrl updateValue("name", "name");
databaseValue.hostBannerMode = info.hostBannerMode; updateValue("iconId", "iconId");
updateValue("clientsOnline", "clientsOnline");
updateValue("clientsMax", "clientsMax");
updateValue("hostBannerUrl", "hostBannerUrl");
updateValue("hostBannerMode", "hostBannerMode");
if(changes.length > 0) {
this.events.fire("notify_server_info_updated", { serverUniqueId: serverUniqueId, keys: changes });
}
}); });
} }
@ -470,6 +491,7 @@ export class ConnectionHistory {
} }
if(entry.value.serverUniqueId === kUnknownHistoryServerUniqueId && onlySucceeded) { if(entry.value.serverUniqueId === kUnknownHistoryServerUniqueId && onlySucceeded) {
entry.continue();
continue; continue;
} }
@ -542,7 +564,15 @@ class ConnectionHistoryUpdateListener {
} }
private registerConnectionHandler(handler: ConnectionHandler) { private registerConnectionHandler(handler: ConnectionHandler) {
handler.channelTree.server.events.on("notify_properties_updated", event => { const events = this.listenerConnectionHandler[handler.handlerId] = [];
events.push(handler.channelTree.server.events.on("notify_properties_updated", event => {
switch(handler.connection_state) {
case ConnectionState.UNCONNECTED:
case ConnectionState.DISCONNECTING:
/* We don't want any changes here */
return;
}
if("virtualserver_unique_identifier" in event.updated_properties) { if("virtualserver_unique_identifier" in event.updated_properties) {
if(handler.currentConnectId > 0) { if(handler.currentConnectId > 0) {
this.history.updateConnectionServerUniqueId(handler.currentConnectId, event.server_properties.virtualserver_unique_identifier) this.history.updateConnectionServerUniqueId(handler.currentConnectId, event.server_properties.virtualserver_unique_identifier)
@ -573,7 +603,7 @@ class ConnectionHistoryUpdateListener {
break; break;
} }
} }
}); }));
} }
} }
@ -581,7 +611,7 @@ export let connectionHistory: ConnectionHistory;
let historyInfoListener: ConnectionHistoryUpdateListener; let historyInfoListener: ConnectionHistoryUpdateListener;
loader.register_task(Stage.JAVASCRIPT_INITIALIZING, { loader.register_task(Stage.JAVASCRIPT_INITIALIZING, {
priority: 0, priority: 40,
name: "Chat history setup", name: "Chat history setup",
function: async () => { function: async () => {
if(!('indexedDB' in window)) { if(!('indexedDB' in window)) {

View File

@ -549,9 +549,11 @@ export class FileManager {
const initializeCallback = async () => { const initializeCallback = async () => {
try { try {
transfer.target = await transfer.targetSupplier(transfer); transfer.target = await transfer.targetSupplier(transfer);
if(!transfer.target) if(!transfer.target) {
throw tr("Failed to create transfer target"); throw tr("Failed to create transfer target");
}
transfer.lastStateUpdate = Date.now();
await this.connectionHandler.serverConnection.send_command("ftinitdownload", { await this.connectionHandler.serverConnection.send_command("ftinitdownload", {
"path": options.path, "path": options.path,
"name": options.name, "name": options.name,
@ -565,7 +567,6 @@ export class FileManager {
if(transfer.transferState() === FileTransferState.INITIALIZING) { if(transfer.transferState() === FileTransferState.INITIALIZING) {
throw tr("missing transfer start notify"); throw tr("missing transfer start notify");
} }
} catch (error) { } catch (error) {
transfer.setFailed({ transfer.setFailed({
error: "initialize", error: "initialize",
@ -588,9 +589,11 @@ export class FileManager {
const initializeCallback = async () => { const initializeCallback = async () => {
try { try {
transfer.source = await transfer.sourceSupplier(transfer); transfer.source = await transfer.sourceSupplier(transfer);
if(!transfer.source) if(!transfer.source) {
throw tr("Failed to create transfer source"); throw tr("Failed to create transfer source");
}
transfer.lastStateUpdate = Date.now();
transfer.fileSize = await transfer.source.fileSize(); transfer.fileSize = await transfer.source.fileSize();
await this.connectionHandler.serverConnection.send_command("ftinitupload", { await this.connectionHandler.serverConnection.send_command("ftinitupload", {
"path": options.path, "path": options.path,
@ -604,14 +607,15 @@ export class FileManager {
"proto": 1 "proto": 1
}, { process_result: options.processCommandResult }); }, { process_result: options.processCommandResult });
if(transfer.transferState() === FileTransferState.INITIALIZING) if(transfer.transferState() === FileTransferState.INITIALIZING) {
throw tr("missing transfer start notify"); throw tr("missing transfer start notify");
}
} catch (error) { } catch (error) {
transfer.setFailed({ transfer.setFailed({
error: "initialize", error: "initialize",
commandResult: error commandResult: error
}, error instanceof CommandResult ? error.formattedMessage() : typeof error === "string" ? error : tr("Lookup the console")); }, error instanceof CommandResult ? error.formattedMessage() : typeof error === "string" ? error : tr("lookup the console"));
} }
}; };
@ -735,8 +739,18 @@ export class FileManager {
/* Transfer is locally pending because of some limits */ /* Transfer is locally pending because of some limits */
return false; return false;
case FileTransferState.CONNECTING:
case FileTransferState.INITIALIZING: case FileTransferState.INITIALIZING:
if(entry instanceof FileDownloadTransfer) {
if(!entry.target) {
/* We're still prompting the user for a target file location. Lets apply a timeout of 1 min. */
if(entry.transfer.lastStateUpdate < Date.now() + 60 * 1000) {
return false;
}
}
}
return true;
case FileTransferState.CONNECTING:
case FileTransferState.RUNNING: case FileTransferState.RUNNING:
/* These states can time out */ /* These states can time out */
return true; return true;

View File

@ -9,12 +9,11 @@ import {initializeConnectionListController} from "tc-shared/ui/frames/connection
import * as loader from "tc-loader"; import * as loader from "tc-loader";
import {Stage} from "tc-loader"; import {Stage} from "tc-loader";
import {server_connections} from "tc-shared/ConnectionManager"; import {server_connections} from "tc-shared/ConnectionManager";
import {AppUiEvents, AppUiVariables} from "tc-shared/ui/AppDefinitions"; import {AppUiVariables} from "tc-shared/ui/AppDefinitions";
import {ConnectionHandler} from "tc-shared/ConnectionHandler"; import {ConnectionHandler} from "tc-shared/ConnectionHandler";
import {SideBarController} from "tc-shared/ui/frames/SideBarController"; import {SideBarController} from "tc-shared/ui/frames/SideBarController";
import {ServerEventLogController} from "tc-shared/ui/frames/log/Controller"; import {ServerEventLogController} from "tc-shared/ui/frames/log/Controller";
import {HostBannerController} from "tc-shared/ui/frames/HostBannerController"; import {HostBannerController} from "tc-shared/ui/frames/HostBannerController";
import {UiVariableProvider} from "tc-shared/ui/utils/Variable";
import {createIpcUiVariableProvider, IpcUiVariableProvider} from "tc-shared/ui/utils/IpcVariable"; import {createIpcUiVariableProvider, IpcUiVariableProvider} from "tc-shared/ui/utils/IpcVariable";
export class AppController { export class AppController {
@ -128,7 +127,7 @@ export class AppController {
} }
export let appViewController: AppController; export let appViewController: AppController;
loader.register_task(Stage.JAVASCRIPT_INITIALIZING, { loader.register_task(Stage.LOADED, {
name: "app view", name: "app view",
function: async () => { function: async () => {
appViewController = new AppController(); appViewController = new AppController();
@ -138,5 +137,5 @@ loader.register_task(Stage.JAVASCRIPT_INITIALIZING, {
(window as any).AppController = AppController; (window as any).AppController = AppController;
(window as any).appViewController = appViewController; (window as any).appViewController = appViewController;
}, },
priority: 0 priority: 100
}); });

View File

@ -167,16 +167,6 @@ html:root {
right: 0; right: 0;
} }
.iconContainer {
margin-right: .25em;
display: flex;
flex-direction: column;
flex-shrink: 0;
flex-grow: 0;
}
.dropdownEntry { .dropdownEntry {
position: relative; position: relative;
@ -305,4 +295,11 @@ html:root {
transform: rotate(45deg); transform: rotate(45deg);
-webkit-transform: rotate(45deg); -webkit-transform: rotate(45deg);
} }
}
.iconContainer {
margin-right: .25em;
display: flex;
flex-direction: column;
} }

View File

@ -23,6 +23,8 @@ import {connectionHistory} from "tc-shared/connectionlog/History";
import {RemoteIconInfo} from "tc-shared/file/Icons"; import {RemoteIconInfo} from "tc-shared/file/Icons";
import {spawnModalAddCurrentServerToBookmarks} from "tc-shared/ui/modal/bookmarks-add-server/Controller"; import {spawnModalAddCurrentServerToBookmarks} from "tc-shared/ui/modal/bookmarks-add-server/Controller";
import {getAudioBackend, OutputDevice} from "tc-shared/audio/Player"; import {getAudioBackend, OutputDevice} from "tc-shared/audio/Player";
import {ignorePromise} from "tc-shared/proto";
import {LogCategory, logTrace} from "tc-shared/log";
class InfoController { class InfoController {
private readonly mode: ControlBarMode; private readonly mode: ControlBarMode;
@ -34,6 +36,8 @@ class InfoController {
private handlerRegisteredEvents: (() => void)[] = []; private handlerRegisteredEvents: (() => void)[] = [];
private defaultRecorderListener: () => void; private defaultRecorderListener: () => void;
private bookmarkServerUniqueIds: string[] = [];
constructor(events: Registry<ControlBarEvents>, mode: ControlBarMode) { constructor(events: Registry<ControlBarEvents>, mode: ControlBarMode) {
this.events = events; this.events = events;
this.mode = mode; this.mode = mode;
@ -61,6 +65,16 @@ class InfoController {
this.sendVideoState("camera"); this.sendVideoState("camera");
})); }));
bookmarks.events.on(["notify_bookmark_edited", "notify_bookmark_created", "notify_bookmark_deleted", "notify_bookmarks_imported"], () => this.sendBookmarks()); bookmarks.events.on(["notify_bookmark_edited", "notify_bookmark_created", "notify_bookmark_deleted", "notify_bookmarks_imported"], () => this.sendBookmarks());
events.push(connectionHistory.events.on("notify_server_info_updated", event => {
if(this.bookmarkServerUniqueIds.indexOf(event.serverUniqueId) === -1) {
return;
}
if(event.keys.indexOf("iconId") !== -1) {
/* An icon for a bookmark has changed. Send the full new list. */
ignorePromise(this.sendBookmarks());
}
}));
events.push(getVideoDriver().getEvents().on("notify_device_list_changed", () => this.sendCameraList())); events.push(getVideoDriver().getEvents().on("notify_device_list_changed", () => this.sendCameraList()));
events.push(getRecorderBackend().getDeviceList().getEvents().on("notify_list_updated", () => this.sendMicrophoneList())); events.push(getRecorderBackend().getDeviceList().getEvents().on("notify_list_updated", () => this.sendMicrophoneList()));
events.push(defaultRecorderEvents.on("notify_default_recorder_changed", () => { events.push(defaultRecorderEvents.on("notify_default_recorder_changed", () => {
@ -202,7 +216,9 @@ class InfoController {
}); });
} }
/* Note: This method might be executed concurrently */
public async sendBookmarks() { public async sendBookmarks() {
this.bookmarkServerUniqueIds = [];
const bookmarkList = bookmarks.getOrderedRegisteredBookmarks(); const bookmarkList = bookmarks.getOrderedRegisteredBookmarks();
const parent: Bookmark[] = []; const parent: Bookmark[] = [];
@ -216,15 +232,17 @@ class InfoController {
let icon: RemoteIconInfo; let icon: RemoteIconInfo;
try { try {
const connectInfo = await connectionHistory.lastConnectInfo(bookmark.entry.serverAddress, "address"); const connectInfo = await connectionHistory.lastConnectInfo(bookmark.entry.serverAddress, "address", true);
if(connectInfo) { if(connectInfo) {
this.bookmarkServerUniqueIds.push(connectInfo.serverUniqueId);
const info = await connectionHistory.queryServerInfo(connectInfo.serverUniqueId); const info = await connectionHistory.queryServerInfo(connectInfo.serverUniqueId);
if(info && info.iconId > 0) { if(info && info.iconId > 0) {
icon = { iconId: info.iconId, serverUniqueId: connectInfo.serverUniqueId }; icon = { iconId: info.iconId, serverUniqueId: connectInfo.serverUniqueId };
} }
} }
} catch (_) { } catch (error) {
/* no need for any error handling */ /* No need to warn in prod build */
logTrace(LogCategory.BOOKMARKS, "Failed to query last connect info: %o", error);
} }
parentList.push({ parentList.push({

View File

@ -1,5 +1,4 @@
import * as React from "react"; import * as React from "react";
import {ReactComponentBase} from "tc-shared/ui/react-elements/ReactComponentBase";
import {IconRenderer, RemoteIconRenderer} from "tc-shared/ui/react-elements/Icon"; import {IconRenderer, RemoteIconRenderer} from "tc-shared/ui/react-elements/Icon";
import {getIconManager, RemoteIconInfo} from "tc-shared/file/Icons"; import {getIconManager, RemoteIconInfo} from "tc-shared/file/Icons";
import {joinClassList} from "tc-shared/ui/react-elements/Helper"; import {joinClassList} from "tc-shared/ui/react-elements/Helper";

View File

@ -43,22 +43,23 @@ const LogEntryRenderer = React.memo((props: { entry: LogMessage }) => {
); );
}); });
const ServerLogRenderer = () => { const ServerLogRenderer = (props: { backlog?: number }) => {
const backlog = typeof props.backlog === "number" ? props.backlog : 100;
const handlerId = useContext(HandlerIdContext); const handlerId = useContext(HandlerIdContext);
const events = useContext(EventsContext); const events = useContext(EventsContext);
const refContainer = useRef<HTMLDivElement>();
const scrollOffset = useRef<number | "bottom">("bottom");
const [ , setRevision ] = useState(0);
const [ logs, setLogs ] = useDependentState<LogMessage[] | "loading">(() => { const [ logs, setLogs ] = useDependentState<LogMessage[] | "loading">(() => {
events.fire_react("query_log"); events.fire_react("query_log");
return "loading"; return "loading";
}, [ handlerId ]); }, [ handlerId ]);
const [ revision, setRevision ] = useState(0);
const refContainer = useRef<HTMLDivElement>();
const scrollOffset = useRef<number | "bottom">("bottom");
events.reactUse("notify_log", event => { events.reactUse("notify_log", event => {
const logs = event.events.slice(0); const logs = event.events.slice(0);
logs.splice(0, Math.max(0, logs.length - 100)); logs.splice(0, Math.max(0, logs.length - backlog));
logs.sort((a, b) => a.timestamp - b.timestamp); logs.sort((a, b) => a.timestamp - b.timestamp);
setLogs(logs); setLogs(logs);
}); });
@ -69,10 +70,10 @@ const ServerLogRenderer = () => {
} }
logs.push(event.event); logs.push(event.event);
logs.splice(0, Math.max(0, logs.length - 100)); logs.splice(0, Math.max(0, logs.length - backlog));
logs.sort((a, b) => a.timestamp - b.timestamp); logs.sort((a, b) => a.timestamp - b.timestamp);
setRevision(revision + 1); setRevision(performance.now());
}); }, logs !== "loading", [ logs ]);
const fixScroll = () => { const fixScroll = () => {
if(!refContainer.current) { if(!refContainer.current) {

View File

@ -11,6 +11,7 @@ import {bookmarks} from "tc-shared/Bookmarks";
import {RemoteIconInfo} from "tc-shared/file/Icons"; import {RemoteIconInfo} from "tc-shared/file/Icons";
import {connectionHistory} from "tc-shared/connectionlog/History"; import {connectionHistory} from "tc-shared/connectionlog/History";
import {spawnModalAddCurrentServerToBookmarks} from "tc-shared/ui/modal/bookmarks-add-server/Controller"; import {spawnModalAddCurrentServerToBookmarks} from "tc-shared/ui/modal/bookmarks-add-server/Controller";
import {LogCategory, logTrace} from "tc-shared/log";
function renderConnectionItems() { function renderConnectionItems() {
const items: MenuBarEntry[] = []; const items: MenuBarEntry[] = [];
@ -52,7 +53,9 @@ function renderConnectionItems() {
return items; return items;
} }
let bookmarkServerUniqueIds: string[] = [];
async function renderBookmarkItems() { async function renderBookmarkItems() {
bookmarkServerUniqueIds = [];
const bookmarkList = bookmarks.getOrderedRegisteredBookmarks(); const bookmarkList = bookmarks.getOrderedRegisteredBookmarks();
const bookmarkItems: MenuBarEntry[] = []; const bookmarkItems: MenuBarEntry[] = [];
@ -66,15 +69,17 @@ async function renderBookmarkItems() {
let icon: RemoteIconInfo; let icon: RemoteIconInfo;
try { try {
const connectInfo = await connectionHistory.lastConnectInfo(bookmark.entry.serverAddress, "address"); const connectInfo = await connectionHistory.lastConnectInfo(bookmark.entry.serverAddress, "address", true);
if(connectInfo) { if(connectInfo) {
bookmarkServerUniqueIds.push(connectInfo.serverUniqueId);
const info = await connectionHistory.queryServerInfo(connectInfo.serverUniqueId); const info = await connectionHistory.queryServerInfo(connectInfo.serverUniqueId);
if(info && info.iconId > 0) { if(info && info.iconId > 0) {
icon = { iconId: info.iconId, serverUniqueId: connectInfo.serverUniqueId }; icon = { iconId: info.iconId, serverUniqueId: connectInfo.serverUniqueId };
} }
} }
} catch (_) { } catch (error) {
/* no need for any error handling */ /* No need to warn in prod build */
logTrace(LogCategory.BOOKMARKS, "Failed to query last connect info: %o", error);
} }
parentList.push({ parentList.push({
@ -363,6 +368,16 @@ class MenuBarUpdateListener {
})); }));
this.generalHandlerEvents.push(server_connections.events().on("notify_active_handler_changed", () => updateMenuBar())); this.generalHandlerEvents.push(server_connections.events().on("notify_active_handler_changed", () => updateMenuBar()));
this.generalHandlerEvents.push(bookmarks.events.on(["notify_bookmark_deleted", "notify_bookmark_created", "notify_bookmark_edited", "notify_bookmarks_imported"], () => updateMenuBar())); this.generalHandlerEvents.push(bookmarks.events.on(["notify_bookmark_deleted", "notify_bookmark_created", "notify_bookmark_edited", "notify_bookmarks_imported"], () => updateMenuBar()));
this.generalHandlerEvents.push(connectionHistory.events.on("notify_server_info_updated", event => {
if(bookmarkServerUniqueIds.indexOf(event.serverUniqueId) === -1) {
return;
}
if(event.keys.indexOf("iconId") !== -1) {
/* An icon for a bookmark has changed. Send the menu bar with the new icons. */
updateMenuBar();
}
}));
server_connections.getAllConnectionHandlers().forEach(handler => this.registerHandlerEvents(handler)); server_connections.getAllConnectionHandlers().forEach(handler => this.registerHandlerEvents(handler));
} }

View File

@ -59,6 +59,6 @@ export class ChannelFileBrowserController {
} }
private notifyEvents() { private notifyEvents() {
this.uiEvents.fire_react("notify_events", { browserEvents: this.remoteBrowseEvents, channelId: this.currentChannel?.channelId }); this.uiEvents.fire_react("notify_events", { browserEvents: this.remoteBrowseEvents.generateIpcDescription(), channelId: this.currentChannel?.channelId });
} }
} }

View File

@ -1,11 +1,11 @@
import {FileBrowserEvents} from "tc-shared/ui/modal/transfer/FileDefinitions"; import {FileBrowserEvents} from "tc-shared/ui/modal/transfer/FileDefinitions";
import {Registry} from "tc-shared/events"; import {IpcRegistryDescription} from "tc-shared/events";
export interface ChannelFileBrowserUiEvents { export interface ChannelFileBrowserUiEvents {
query_events: {}, query_events: {},
notify_events: { notify_events: {
browserEvents: Registry<FileBrowserEvents>, browserEvents: IpcRegistryDescription<FileBrowserEvents>,
channelId: number channelId: number
}, },
} }

View File

@ -6,7 +6,7 @@
height: 100%; height: 100%;
width: 100%; width: 100%;
color: #999; color: #999!important;
.navbar { .navbar {
flex-shrink: 0; flex-shrink: 0;
@ -17,13 +17,13 @@
} }
.fileTable { .fileTable {
border: none; border: none!important;
border-radius: 0; border-radius: 0!important;
background-color: var(--chat-background); background-color: var(--chat-background)!important;
.header { .header {
background-color: var(--chat-background); background-color: var(--chat-background)!important;
} }
} }
@ -36,10 +36,10 @@
} }
.boxedInput { .boxedInput {
background-color: var(--side-info-background); background-color: var(--side-info-background)!important;
border-color: #212121; border-color: #212121!important;
&:focus-within { &:focus-within {
background-color: #242424; background-color: #242424!important;
} }
} }

View File

@ -1,5 +1,5 @@
import * as React from "react"; import * as React from "react";
import {useState} from "react"; import {useEffect, useState} from "react";
import {Registry} from "tc-shared/events"; import {Registry} from "tc-shared/events";
import {ChannelFileBrowserUiEvents} from "tc-shared/ui/frames/side/ChannelFileBrowserDefinitions"; import {ChannelFileBrowserUiEvents} from "tc-shared/ui/frames/side/ChannelFileBrowserDefinitions";
import {channelPathPrefix, FileBrowserEvents} from "tc-shared/ui/modal/transfer/FileDefinitions"; import {channelPathPrefix, FileBrowserEvents} from "tc-shared/ui/modal/transfer/FileDefinitions";
@ -32,11 +32,14 @@ export const ChannelFileBrowser = (props: { events: Registry<ChannelFileBrowserU
props.events.fire("query_events"); props.events.fire("query_events");
return undefined; return undefined;
}); });
props.events.reactUse("notify_events", event => setEvents({ props.events.reactUse("notify_events", event => setEvents({
events: event.browserEvents, events: Registry.fromIpcDescription(event.browserEvents),
channelId: event.channelId channelId: event.channelId
})); }));
useEffect(() => () => events?.events?.destroy(), [ events?.events ]);
if(!events) { if(!events) {
return null; return null;
} }

View File

@ -116,7 +116,7 @@ const BlockPing = () => {
return undefined; return undefined;
}); });
events.reactUse("notify_ping", event => setPingInfo(event.ping)); events.reactUse("notify_ping", event => setPingInfo(event.ping), undefined, [ ]);
let value, title; let value, title;
if(!pingInfo) { if(!pingInfo) {

View File

@ -41,7 +41,7 @@ const ExpendArrow = React.memo(() => {
return false; return false;
}); });
events.reactUse("notify_expended", event => setExpended(event.expended), undefined, [ setExpended ]); events.reactUse("notify_expended", event => setExpended(event.expended), undefined, []);
return ( return (
<div className={cssStyle.expendArrow} onClick={() => events.fire("action_toggle_expended", { expended: !expended })}> <div className={cssStyle.expendArrow} onClick={() => events.fire("action_toggle_expended", { expended: !expended })}>
@ -776,8 +776,8 @@ const VisibilityHandler = React.memo((props: {
return false; return false;
}) })
events.reactUse("notify_videos", event => setStreamingCount(event.videoActiveCount)); events.reactUse("notify_videos", event => setStreamingCount(event.videoActiveCount), []);
events.reactUse("notify_expended", event => setExpanded(event.expended)); events.reactUse("notify_expended", event => setExpanded(event.expended), []);
return ( return (
<div className={joinClassList(cssStyle.container, streamingCount === 0 && cssStyle.hidden, expanded && cssStyle.expended)}> <div className={joinClassList(cssStyle.container, streamingCount === 0 && cssStyle.hidden, expanded && cssStyle.expended)}>
{props.children} {props.children}

View File

@ -567,7 +567,7 @@ class BookmarkModalController {
} }
return this.bookmarkUniqueServerIds[bookmarkId] = (async () => { return this.bookmarkUniqueServerIds[bookmarkId] = (async () => {
const info = await connectionHistory.lastConnectInfo(bookmark.serverAddress, "address"); const info = await connectionHistory.lastConnectInfo(bookmark.serverAddress, "address", true);
if(!info) { if(!info) {
return undefined; return undefined;
} }

View File

@ -109,7 +109,7 @@ const BookmarkListEntryRenderer = React.memo((props: { entry: BookmarkListEntry
events.fire("action_connect", { uniqueId: props.entry.uniqueId, newTab: false, closeModal: true }); events.fire("action_connect", { uniqueId: props.entry.uniqueId, newTab: false, closeModal: true });
}} }}
onContextMenu={event => { onContextMenu={event => {
event.preventDefault(); event.stopPropagation();
if(selectedItem.remoteValue?.id !== props.entry.uniqueId) { if(selectedItem.remoteValue?.id !== props.entry.uniqueId) {
selectedItem.setValue({ id: props.entry.uniqueId }); selectedItem.setValue({ id: props.entry.uniqueId });
@ -195,9 +195,8 @@ const BookmarkList = React.memo(() => {
<div <div
className={cssStyle.containerBookmarks} className={cssStyle.containerBookmarks}
onContextMenu={event => { onContextMenu={event => {
event.preventDefault();
if(bookmarks.length === 0) { if(bookmarks.length === 0) {
/* We've an extra overlay for not having any bookmarks. */
return; return;
} }

View File

@ -80,16 +80,14 @@ export function initializeRemoteFileBrowserController(connection: ConnectionHand
events.on("action_navigate_to", event => { events.on("action_navigate_to", event => {
try { try {
const info = parsePath(event.path, connection);
currentPathInfo = info; currentPathInfo = parsePath(event.path, connection);
currentPath = event.path; currentPath = event.path;
selection = []; selection = [];
events.fire_react("notify_current_path", { events.fire_react("notify_current_path", {
path: event.path || "/", path: event.path || "/",
status: "success", status: "success",
pathInfo: info
}); });
} catch (error) { } catch (error) {
events.fire_react("notify_current_path", { events.fire_react("notify_current_path", {
@ -382,7 +380,6 @@ export function initializeRemoteFileBrowserController(connection: ConnectionHand
events.on("query_current_path", () => events.fire_react("notify_current_path", { events.on("query_current_path", () => events.fire_react("notify_current_path", {
status: "success", status: "success",
path: currentPath, path: currentPath,
pathInfo: currentPathInfo
})); }));
events.on("action_rename_file_result", result => { events.on("action_rename_file_result", result => {
@ -689,12 +686,13 @@ export function initializeRemoteFileBrowserController(connection: ConnectionHand
}); });
}); });
events.on("action_start_download", event => { events.on("action_start_download", async event => {
event.files.forEach(file => { for(const file of event.files) {
try { try {
let targetSupplier; let targetSupplier;
if (__build.target === "client" && TransferProvider.provider().targetSupported(TransferTargetType.FILE)) { if (__build.target === "client" && TransferProvider.provider().targetSupported(TransferTargetType.FILE)) {
const target = TransferProvider.provider().createFileTarget(undefined, file.name); /* Get the target file path before we're actiually starting to download the file */
const target = await TransferProvider.provider().createFileTarget(undefined, file.name);
targetSupplier = async () => target; targetSupplier = async () => target;
} else if (TransferProvider.provider().targetSupported(TransferTargetType.DOWNLOAD)) { } else if (TransferProvider.provider().targetSupported(TransferTargetType.DOWNLOAD)) {
targetSupplier = async () => await TransferProvider.provider().createDownloadTarget(); targetSupplier = async () => await TransferProvider.provider().createDownloadTarget();
@ -720,7 +718,7 @@ export function initializeRemoteFileBrowserController(connection: ConnectionHand
} catch (error) { } catch (error) {
logError(LogCategory.FILE_TRANSFER, tr("Failed to parse path for file download: %s"), error); logError(LogCategory.FILE_TRANSFER, tr("Failed to parse path for file download: %s"), error);
} }
}); }
}); });
events.on("action_start_upload", event => { events.on("action_start_upload", event => {

View File

@ -115,7 +115,7 @@ const NavigationEntry = (props: { events: Registry<FileBrowserEvents>, path: str
const oldPath = fileUrl.split("/").slice(0, -1).join("/") + "/"; const oldPath = fileUrl.split("/").slice(0, -1).join("/") + "/";
props.events.fire("action_rename_file", { props.events.fire("action_rename_file", {
newPath: props.path + "/", newPath: props.path.endsWith("/") ? props.path : props.path + "/",
oldPath: oldPath, oldPath: oldPath,
oldName: name, oldName: name,
newName: name newName: name

View File

@ -132,7 +132,6 @@ export interface FileBrowserEvents {
path: string, path: string,
status: "success" | "timeout" | "error"; status: "success" | "timeout" | "error";
error?: string; error?: string;
pathInfo?: PathInfo
}, },
notify_transfer_start: { notify_transfer_start: {

View File

@ -4,6 +4,7 @@ import * as dompurify from "dompurify";
import {ChangeLog, ChangeLogEntry, ChangeSet} from "tc-shared/update/ChangeLog"; import {ChangeLog, ChangeLogEntry, ChangeSet} from "tc-shared/update/ChangeLog";
import {Translatable, VariadicTranslatable} from "tc-shared/ui/react-elements/i18n"; import {Translatable, VariadicTranslatable} from "tc-shared/ui/react-elements/i18n";
import {guid} from "tc-shared/crypto/uid"; import {guid} from "tc-shared/crypto/uid";
import moment from "moment";
const {Remarkable} = require("remarkable"); const {Remarkable} = require("remarkable");
const cssStyle = require("./Renderer.scss"); const cssStyle = require("./Renderer.scss");
@ -108,7 +109,7 @@ export const WhatsNew = (props: { changesUI?: ChangeLog, changesClient?: ChangeL
<VariadicTranslatable key={"info-web"} <VariadicTranslatable key={"info-web"}
text={"The web client has been updated to the version from {}."} text={"The web client has been updated to the version from {}."}
> >
{versionUIDate} {moment(__build.timestamp).format("dd.MM.YY")}
</VariadicTranslatable> </VariadicTranslatable>
); );
} else if (props.changesUI && props.changesClient) { } else if (props.changesUI && props.changesClient) {

View File

@ -29,7 +29,7 @@ export class Checkbox extends React.Component<CheckboxProperties, CheckboxState>
render() { render() {
const disabled = typeof this.state.disabled === "boolean" ? this.state.disabled : this.props.disabled; const disabled = typeof this.state.disabled === "boolean" ? this.state.disabled : this.props.disabled;
const checked = typeof this.props.value === "boolean" ? this.props.value : typeof this.state.checked === "boolean" ? this.state.checked : this.props.initialValue; const checked = (typeof this.props.value === "boolean" ? this.props.value : typeof this.state.checked === "boolean" ? this.state.checked : this.props.initialValue) || false;
const disabledClass = disabled ? cssStyle.disabled : ""; const disabledClass = disabled ? cssStyle.disabled : "";
return ( return (

View File

@ -1,13 +1,17 @@
@import "../../../css/static/mixin"; @import "../../../css/static/mixin";
@import "../../../css/static/properties"; @import "../../../css/static/properties";
$animation_time: $button_hover_animation_time;
.container { .container {
position: relative; position: relative;
overflow: hidden; /* Don't use overflow hidden here since some container may require overflow */
&:hover { &:hover {
.containerButton { .containerButton {
top: 1em; top: 1em;
opacity: 1;
@include transition(top ease-in-out $animation_time, opacity ease-in-out $animation_time / 2 $animation_time / 2);
} }
} }
} }
@ -16,10 +20,12 @@
position: absolute; position: absolute;
z-index: 10; z-index: 10;
top: -3em; opacity: 0;
top: -1em;
right: 1em; right: 1em;
@include transition(all ease-in-out $button_hover_animation_time); @include transition(top ease-in-out $animation_time, opacity ease-in-out $animation_time / 2);
&.disabled { &.disabled {
display: none; display: none;
@ -38,7 +44,7 @@
cursor: pointer; cursor: pointer;
@include transition(all ease-in-out $button_hover_animation_time); @include transition(all ease-in-out $animation_time);
&:hover { &:hover {
background-color: #0000008f; background-color: #0000008f;

View File

@ -2,6 +2,11 @@
width: 1em; width: 1em;
height: 1em; height: 1em;
flex-shrink: 0;
flex-grow: 0;
align-self: center;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
justify-content: stretch; justify-content: stretch;

View File

@ -64,7 +64,7 @@ export const RemoteIconRenderer = React.memo((props: { icon: RemoteIcon | undefi
} }
return ( return (
<IconUrl iconUrl={props.icon.getImageUrl()} title={props.title || ("icon " + props.icon.iconId)} key={"icon-" + props.icon.iconId} /> <IconUrl iconUrl={props.icon.getImageUrl()} title={props.title || ("icon " + props.icon.iconId)} key={"icon-" + props.icon.iconId} className={props.className} />
); );
case "loading": case "loading":

View File

@ -28,6 +28,21 @@ function registerInvokeCallback(callback: () => void) {
} }
} }
function savePostMessage(channel: BroadcastChannel | MessageEventSource, message: any) {
try {
// @ts-ignore
channel.postMessage(message);
} catch (error) {
if(error instanceof Error) {
debugger;
console.error(error);
return;
}
throw error;
}
}
export class IpcUiVariableProvider<Variables extends UiVariableMap> extends UiVariableProvider<Variables> { export class IpcUiVariableProvider<Variables extends UiVariableMap> extends UiVariableProvider<Variables> {
readonly ipcChannelId: string; readonly ipcChannelId: string;
private readonly bundleMaxSize: number; private readonly bundleMaxSize: number;
@ -72,7 +87,7 @@ export class IpcUiVariableProvider<Variables extends UiVariableMap> extends UiVa
const sendResult = (error?: any) => { const sendResult = (error?: any) => {
if(source) { if(source) {
// @ts-ignore // @ts-ignore
source.postMessage({ savePostMessage(source, {
type: "edit-result", type: "edit-result",
token, token,
error error
@ -124,7 +139,7 @@ export class IpcUiVariableProvider<Variables extends UiVariableMap> extends UiVa
*/ */
private broadcastIpcMessage(message: any) { private broadcastIpcMessage(message: any) {
if(this.bundleMaxSize <= 0) { if(this.bundleMaxSize <= 0) {
this.broadcastChannel.postMessage(message); savePostMessage(this.broadcastChannel, message);
return; return;
} }
@ -145,7 +160,7 @@ export class IpcUiVariableProvider<Variables extends UiVariableMap> extends UiVa
return; return;
} }
this.broadcastChannel.postMessage({ savePostMessage(this.broadcastChannel, {
type: "bundled", type: "bundled",
messages: this.enqueuedMessages messages: this.enqueuedMessages
}); });
@ -253,7 +268,7 @@ class IpcUiVariableConsumer<Variables extends UiVariableMap> extends UiVariableC
*/ */
private sendIpcMessage(message: any) { private sendIpcMessage(message: any) {
if(this.bundleMaxSize <= 0) { if(this.bundleMaxSize <= 0) {
this.broadcastChannel.postMessage(message); savePostMessage(this.broadcastChannel, message);
return; return;
} }
@ -274,7 +289,7 @@ class IpcUiVariableConsumer<Variables extends UiVariableMap> extends UiVariableC
return; return;
} }
this.broadcastChannel.postMessage({ savePostMessage(this.broadcastChannel, {
type: "bundled", type: "bundled",
messages: this.enqueuedMessages messages: this.enqueuedMessages
}); });

2
vendor/TeaEventBus vendored

@ -1 +1 @@
Subproject commit 8310382d8a851b2e7095b400807141065811da53 Subproject commit 49041c4069a6ae54649748ff5373f82fe2fde15f