mirror of
https://github.com/cryptpad/cryptpad.git
synced 2026-09-14 11:05:41 +05:00
Merge commit 'refs/pullreqs/2239' into 2026.2.1-test
This commit is contained in:
commit
40f012a315
@ -23,6 +23,9 @@ server {
|
||||
return 301 https://$host$request_uri;
|
||||
}
|
||||
|
||||
# Websocket connections rate limiting
|
||||
limit_req_zone $binary_remote_addr zone=wslimit:20m rate=30r/m;
|
||||
|
||||
server {
|
||||
listen 443 ssl;
|
||||
listen [::]:443 ssl;
|
||||
@ -190,6 +193,10 @@ server {
|
||||
# We prefer to serve static content from nginx directly and to leave the API server to handle
|
||||
# the dynamic content that only it can manage. This is primarily an optimization
|
||||
location ^~ /cryptpad_websocket {
|
||||
# Websocket connections rate limiting
|
||||
limit_req zone=wslimit burst=5 nodelay;
|
||||
limit_req_status 429;
|
||||
|
||||
# XXX
|
||||
# static assets like blobs and blocks are served by clustered workers in the API server
|
||||
# Websocket traffic still needs to be handled by the main process, which means it needs
|
||||
|
||||
@ -1028,6 +1028,17 @@ HK.onChannelMessage = function (Env, Server, channel, msgStruct, cb) {
|
||||
if (!_metadata) { return; }
|
||||
metadata = _metadata;
|
||||
|
||||
if (metadata?.restricted) {
|
||||
const userId = msgStruct[1];
|
||||
// If userId is defined (not a private message) and the user
|
||||
// is not a member of this restricted channel, prevent them
|
||||
// from broadcasting to the pad until they have joined it
|
||||
if (userId && !Server.channelContainsUser(channel.id, userId)) {
|
||||
cb('EFORBIDDEN');
|
||||
return void w.abort();
|
||||
}
|
||||
}
|
||||
|
||||
// don't write messages to expired channels
|
||||
if (checkExpired(Env, Server, channel)) {
|
||||
cb('EEXPIRED');
|
||||
|
||||
259
package-lock.json
generated
259
package-lock.json
generated
@ -67,7 +67,7 @@
|
||||
"@rollup/plugin-commonjs": "^28.0.0",
|
||||
"@rollup/plugin-json": "^6.1.0",
|
||||
"@rollup/plugin-node-resolve": "^15.3.0",
|
||||
"@rollup/plugin-terser": "^0.4.4",
|
||||
"@rollup/plugin-terser": "^1.0.0",
|
||||
"@rollup/plugin-typescript": "^12.1.0",
|
||||
"eslint": "^10.0.0",
|
||||
"eslint-plugin-compat": "^6.0.1",
|
||||
@ -627,16 +627,18 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rollup/plugin-terser": {
|
||||
"version": "0.4.4",
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/plugin-terser/-/plugin-terser-1.0.0.tgz",
|
||||
"integrity": "sha512-FnCxhTBx6bMOYQrar6C8h3scPt8/JwIzw3+AJ2K++6guogH5fYaIFia+zZuhqv0eo1RN7W1Pz630SyvLbDjhtQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"serialize-javascript": "^6.0.1",
|
||||
"serialize-javascript": "^7.0.3",
|
||||
"smob": "^1.0.0",
|
||||
"terser": "^5.17.4"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=14.0.0"
|
||||
"node": ">=20.0.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"rollup": "^2.0.0||^3.0.0||^4.0.0"
|
||||
@ -694,9 +696,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rollup/rollup-android-arm-eabi": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.53.3.tgz",
|
||||
"integrity": "sha512-mRSi+4cBjrRLoaal2PnqH82Wqyb+d3HsPUN/W+WslCXsZsyHa9ZeQQX/pQsZaVIWDkPcpV6jJ+3KLbTbgnwv8w==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.59.0.tgz",
|
||||
"integrity": "sha512-upnNBkA6ZH2VKGcBj9Fyl9IGNPULcjXRlg0LLeaioQWueH30p6IXtJEbKAgvyv+mJaMxSm1l6xwDXYjpEMiLMg==",
|
||||
"cpu": [
|
||||
"arm"
|
||||
],
|
||||
@ -708,9 +710,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-android-arm64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.53.3.tgz",
|
||||
"integrity": "sha512-CbDGaMpdE9sh7sCmTrTUyllhrg65t6SwhjlMJsLr+J8YjFuPmCEjbBSx4Z/e4SmDyH3aB5hGaJUP2ltV/vcs4w==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.59.0.tgz",
|
||||
"integrity": "sha512-hZ+Zxj3SySm4A/DylsDKZAeVg0mvi++0PYVceVyX7hemkw7OreKdCvW2oQ3T1FMZvCaQXqOTHb8qmBShoqk69Q==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -722,9 +724,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-darwin-arm64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.53.3.tgz",
|
||||
"integrity": "sha512-Nr7SlQeqIBpOV6BHHGZgYBuSdanCXuw09hon14MGOLGmXAFYjx1wNvquVPmpZnl0tLjg25dEdr4IQ6GgyToCUA==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.59.0.tgz",
|
||||
"integrity": "sha512-W2Psnbh1J8ZJw0xKAd8zdNgF9HRLkdWwwdWqubSVk0pUuQkoHnv7rx4GiF9rT4t5DIZGAsConRE3AxCdJ4m8rg==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -736,9 +738,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-darwin-x64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.53.3.tgz",
|
||||
"integrity": "sha512-DZ8N4CSNfl965CmPktJ8oBnfYr3F8dTTNBQkRlffnUarJ2ohudQD17sZBa097J8xhQ26AwhHJ5mvUyQW8ddTsQ==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.59.0.tgz",
|
||||
"integrity": "sha512-ZW2KkwlS4lwTv7ZVsYDiARfFCnSGhzYPdiOU4IM2fDbL+QGlyAbjgSFuqNRbSthybLbIJ915UtZBtmuLrQAT/w==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -750,9 +752,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-freebsd-arm64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.53.3.tgz",
|
||||
"integrity": "sha512-yMTrCrK92aGyi7GuDNtGn2sNW+Gdb4vErx4t3Gv/Tr+1zRb8ax4z8GWVRfr3Jw8zJWvpGHNpss3vVlbF58DZ4w==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.59.0.tgz",
|
||||
"integrity": "sha512-EsKaJ5ytAu9jI3lonzn3BgG8iRBjV4LxZexygcQbpiU0wU0ATxhNVEpXKfUa0pS05gTcSDMKpn3Sx+QB9RlTTA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -764,9 +766,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-freebsd-x64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.53.3.tgz",
|
||||
"integrity": "sha512-lMfF8X7QhdQzseM6XaX0vbno2m3hlyZFhwcndRMw8fbAGUGL3WFMBdK0hbUBIUYcEcMhVLr1SIamDeuLBnXS+Q==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.59.0.tgz",
|
||||
"integrity": "sha512-d3DuZi2KzTMjImrxoHIAODUZYoUUMsuUiY4SRRcJy6NJoZ6iIqWnJu9IScV9jXysyGMVuW+KNzZvBLOcpdl3Vg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -778,9 +780,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-arm-gnueabihf": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.53.3.tgz",
|
||||
"integrity": "sha512-k9oD15soC/Ln6d2Wv/JOFPzZXIAIFLp6B+i14KhxAfnq76ajt0EhYc5YPeX6W1xJkAdItcVT+JhKl1QZh44/qw==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.59.0.tgz",
|
||||
"integrity": "sha512-t4ONHboXi/3E0rT6OZl1pKbl2Vgxf9vJfWgmUoCEVQVxhW6Cw/c8I6hbbu7DAvgp82RKiH7TpLwxnJeKv2pbsw==",
|
||||
"cpu": [
|
||||
"arm"
|
||||
],
|
||||
@ -792,9 +794,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-arm-musleabihf": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.53.3.tgz",
|
||||
"integrity": "sha512-vTNlKq+N6CK/8UktsrFuc+/7NlEYVxgaEgRXVUVK258Z5ymho29skzW1sutgYjqNnquGwVUObAaxae8rZ6YMhg==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.59.0.tgz",
|
||||
"integrity": "sha512-CikFT7aYPA2ufMD086cVORBYGHffBo4K8MQ4uPS/ZnY54GKj36i196u8U+aDVT2LX4eSMbyHtyOh7D7Zvk2VvA==",
|
||||
"cpu": [
|
||||
"arm"
|
||||
],
|
||||
@ -806,9 +808,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-arm64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-RGrFLWgMhSxRs/EWJMIFM1O5Mzuz3Xy3/mnxJp/5cVhZ2XoCAxJnmNsEyeMJtpK+wu0FJFWz+QF4mjCA7AUQ3w==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-jYgUGk5aLd1nUb1CtQ8E+t5JhLc9x5WdBKew9ZgAXg7DBk0ZHErLHdXM24rfX+bKrFe+Xp5YuJo54I5HFjGDAA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -820,9 +822,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-arm64-musl": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.53.3.tgz",
|
||||
"integrity": "sha512-kASyvfBEWYPEwe0Qv4nfu6pNkITLTb32p4yTgzFCocHnJLAHs+9LjUu9ONIhvfT/5lv4YS5muBHyuV84epBo/A==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.59.0.tgz",
|
||||
"integrity": "sha512-peZRVEdnFWZ5Bh2KeumKG9ty7aCXzzEsHShOZEFiCQlDEepP1dpUl/SrUNXNg13UmZl+gzVDPsiCwnV1uI0RUA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -834,9 +836,23 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-loong64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-JiuKcp2teLJwQ7vkJ95EwESWkNRFJD7TQgYmCnrPtlu50b4XvT5MOmurWNrCj3IFdyjBQ5p9vnrX4JM6I8OE7g==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-gbUSW/97f7+r4gHy3Jlup8zDG190AuodsWnNiXErp9mT90iCy9NKKU0Xwx5k8VlRAIV2uU9CsMnEFg/xXaOfXg==",
|
||||
"cpu": [
|
||||
"loong64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-loong64-musl": {
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.59.0.tgz",
|
||||
"integrity": "sha512-yTRONe79E+o0FWFijasoTjtzG9EBedFXJMl888NBEDCDV9I2wGbFFfJQQe63OijbFCUZqxpHz1GzpbtSFikJ4Q==",
|
||||
"cpu": [
|
||||
"loong64"
|
||||
],
|
||||
@ -848,9 +864,23 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-ppc64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-EoGSa8nd6d3T7zLuqdojxC20oBfNT8nexBbB/rkxgKj5T5vhpAQKKnD+h3UkoMuTyXkP5jTjK/ccNRmQrPNDuw==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-sw1o3tfyk12k3OEpRddF68a1unZ5VCN7zoTNtSn2KndUE+ea3m3ROOKRCZxEpmT9nsGnogpFP9x6mnLTCaoLkA==",
|
||||
"cpu": [
|
||||
"ppc64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-ppc64-musl": {
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.59.0.tgz",
|
||||
"integrity": "sha512-+2kLtQ4xT3AiIxkzFVFXfsmlZiG5FXYW7ZyIIvGA7Bdeuh9Z0aN4hVyXS/G1E9bTP/vqszNIN/pUKCk/BTHsKA==",
|
||||
"cpu": [
|
||||
"ppc64"
|
||||
],
|
||||
@ -862,9 +892,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-riscv64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-4s+Wped2IHXHPnAEbIB0YWBv7SDohqxobiiPA1FIWZpX+w9o2i4LezzH/NkFUl8LRci/8udci6cLq+jJQlh+0g==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-NDYMpsXYJJaj+I7UdwIuHHNxXZ/b/N2hR15NyH3m2qAtb/hHPA4g4SuuvrdxetTdndfj9b1WOmy73kcPRoERUg==",
|
||||
"cpu": [
|
||||
"riscv64"
|
||||
],
|
||||
@ -876,9 +906,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-riscv64-musl": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.53.3.tgz",
|
||||
"integrity": "sha512-68k2g7+0vs2u9CxDt5ktXTngsxOQkSEV/xBbwlqYcUrAVh6P9EgMZvFsnHy4SEiUl46Xf0IObWVbMvPrr2gw8A==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.59.0.tgz",
|
||||
"integrity": "sha512-nLckB8WOqHIf1bhymk+oHxvM9D3tyPndZH8i8+35p/1YiVoVswPid2yLzgX7ZJP0KQvnkhM4H6QZ5m0LzbyIAg==",
|
||||
"cpu": [
|
||||
"riscv64"
|
||||
],
|
||||
@ -890,9 +920,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-s390x-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-VYsFMpULAz87ZW6BVYw3I6sWesGpsP9OPcyKe8ofdg9LHxSbRMd7zrVrr5xi/3kMZtpWL/wC+UIJWJYVX5uTKg==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-oF87Ie3uAIvORFBpwnCvUzdeYUqi2wY6jRFWJAy1qus/udHFYIkplYRW+wo+GRUP4sKzYdmE1Y3+rY5Gc4ZO+w==",
|
||||
"cpu": [
|
||||
"s390x"
|
||||
],
|
||||
@ -904,7 +934,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-x64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-3AHmtQq/ppNuUspKAlvA8HtLybkDflkMuLK4DPo77DfthRb71V84/c4MlWJXixZz4uruIH4uaa07IqoAkG64fg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -916,7 +948,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-linux-x64-musl": {
|
||||
"version": "4.53.3",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.59.0.tgz",
|
||||
"integrity": "sha512-2UdiwS/9cTAx7qIUZB/fWtToJwvt0Vbo0zmnYt7ED35KPg13Q0ym1g442THLC7VyI6JfYTP4PiSOWyoMdV2/xg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -927,10 +961,24 @@
|
||||
"linux"
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-openbsd-x64": {
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.59.0.tgz",
|
||||
"integrity": "sha512-M3bLRAVk6GOwFlPTIxVBSYKUaqfLrn8l0psKinkCFxl4lQvOSz8ZrKDz2gxcBwHFpci0B6rttydI4IpS4IS/jQ==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"openbsd"
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-openharmony-arm64": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.53.3.tgz",
|
||||
"integrity": "sha512-OueLAWgrNSPGAdUdIjSWXw+u/02BRTcnfw9PN41D2vq/JSEPnJnVuBgw18VkN8wcd4fjUs+jFHVM4t9+kBSNLw==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.59.0.tgz",
|
||||
"integrity": "sha512-tt9KBJqaqp5i5HUZzoafHZX8b5Q2Fe7UjYERADll83O4fGqJ49O1FsL6LpdzVFQcpwvnyd0i+K/VSwu/o/nWlA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -942,9 +990,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-win32-arm64-msvc": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.53.3.tgz",
|
||||
"integrity": "sha512-GOFuKpsxR/whszbF/bzydebLiXIHSgsEUp6M0JI8dWvi+fFa1TD6YQa4aSZHtpmh2/uAlj/Dy+nmby3TJ3pkTw==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.59.0.tgz",
|
||||
"integrity": "sha512-V5B6mG7OrGTwnxaNUzZTDTjDS7F75PO1ae6MJYdiMu60sq0CqN5CVeVsbhPxalupvTX8gXVSU9gq+Rx1/hvu6A==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@ -956,9 +1004,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-win32-ia32-msvc": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.53.3.tgz",
|
||||
"integrity": "sha512-iah+THLcBJdpfZ1TstDFbKNznlzoxa8fmnFYK4V67HvmuNYkVdAywJSoteUszvBQ9/HqN2+9AZghbajMsFT+oA==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.59.0.tgz",
|
||||
"integrity": "sha512-UKFMHPuM9R0iBegwzKF4y0C4J9u8C6MEJgFuXTBerMk7EJ92GFVFYBfOZaSGLu6COf7FxpQNqhNS4c4icUPqxA==",
|
||||
"cpu": [
|
||||
"ia32"
|
||||
],
|
||||
@ -970,9 +1018,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-win32-x64-gnu": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.53.3.tgz",
|
||||
"integrity": "sha512-J9QDiOIZlZLdcot5NXEepDkstocktoVjkaKUtqzgzpt2yWjGlbYiKyp05rWwk4nypbYUNoFAztEgixoLaSETkg==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.59.0.tgz",
|
||||
"integrity": "sha512-laBkYlSS1n2L8fSo1thDNGrCTQMmxjYY5G0WFWjFFYZkKPjsMBsgJfGf4TLxXrF6RyhI60L8TMOjBMvXiTcxeA==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -984,9 +1032,9 @@
|
||||
]
|
||||
},
|
||||
"node_modules/@rollup/rollup-win32-x64-msvc": {
|
||||
"version": "4.53.3",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.53.3.tgz",
|
||||
"integrity": "sha512-UhTd8u31dXadv0MopwGgNOBpUVROFKWVQgAg5N1ESyCz8AuBcMqm4AuTjrwgQKGDfoFuz02EuMRHQIw/frmYKQ==",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.59.0.tgz",
|
||||
"integrity": "sha512-2HRCml6OztYXyJXAvdDXPKcawukWY2GpR5/nxKp4iBgiO3wcoEGkAaqctIbZcNB6KlUQBIqt8VYkNSj2397EfA==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@ -1128,9 +1176,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/ajv": {
|
||||
"version": "6.12.6",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
|
||||
"integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
|
||||
"version": "6.14.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.14.0.tgz",
|
||||
"integrity": "sha512-IWrosm/yrn43eiKqkfkHis7QioDleaXQHdDVPKg0FSwwd/DuvyX79TZnFOnYpB7dcsFAMmtFztZuXPDvSePkFw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@ -3394,9 +3442,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/minimatch": {
|
||||
"version": "10.2.2",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.2.2.tgz",
|
||||
"integrity": "sha512-+G4CpNBxa5MprY+04MbgOw1v7So6n5JY166pFi9KfYwT78fxScCeSNQSNzp6dpPSW2rONOps6Ocam1wFhCgoVw==",
|
||||
"version": "10.2.4",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.2.4.tgz",
|
||||
"integrity": "sha512-oRjTw/97aTBN0RHbYCdtF1MQfvusSIBQM0IZEgzl6426+8jSC0nF1a/GmnVLpfB9yyr6g6FTqWqiZVbxrtaCIg==",
|
||||
"license": "BlueOak-1.0.0",
|
||||
"dependencies": {
|
||||
"brace-expansion": "^5.0.2"
|
||||
@ -3906,14 +3954,6 @@
|
||||
],
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/randombytes": {
|
||||
"version": "2.1.0",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"safe-buffer": "^5.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/range-parser": {
|
||||
"version": "1.2.1",
|
||||
"license": "MIT",
|
||||
@ -4038,7 +4078,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/rollup": {
|
||||
"version": "4.53.3",
|
||||
"version": "4.59.0",
|
||||
"resolved": "https://registry.npmjs.org/rollup/-/rollup-4.59.0.tgz",
|
||||
"integrity": "sha512-2oMpl67a3zCH9H79LeMcbDhXW/UmWG/y2zuqnF2jQq5uq9TbM9TVyXvA4+t+ne2IIkBdrLpAaRQAvo7YI/Yyeg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@ -4052,28 +4094,31 @@
|
||||
"npm": ">=8.0.0"
|
||||
},
|
||||
"optionalDependencies": {
|
||||
"@rollup/rollup-android-arm-eabi": "4.53.3",
|
||||
"@rollup/rollup-android-arm64": "4.53.3",
|
||||
"@rollup/rollup-darwin-arm64": "4.53.3",
|
||||
"@rollup/rollup-darwin-x64": "4.53.3",
|
||||
"@rollup/rollup-freebsd-arm64": "4.53.3",
|
||||
"@rollup/rollup-freebsd-x64": "4.53.3",
|
||||
"@rollup/rollup-linux-arm-gnueabihf": "4.53.3",
|
||||
"@rollup/rollup-linux-arm-musleabihf": "4.53.3",
|
||||
"@rollup/rollup-linux-arm64-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-arm64-musl": "4.53.3",
|
||||
"@rollup/rollup-linux-loong64-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-ppc64-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-riscv64-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-riscv64-musl": "4.53.3",
|
||||
"@rollup/rollup-linux-s390x-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-x64-gnu": "4.53.3",
|
||||
"@rollup/rollup-linux-x64-musl": "4.53.3",
|
||||
"@rollup/rollup-openharmony-arm64": "4.53.3",
|
||||
"@rollup/rollup-win32-arm64-msvc": "4.53.3",
|
||||
"@rollup/rollup-win32-ia32-msvc": "4.53.3",
|
||||
"@rollup/rollup-win32-x64-gnu": "4.53.3",
|
||||
"@rollup/rollup-win32-x64-msvc": "4.53.3",
|
||||
"@rollup/rollup-android-arm-eabi": "4.59.0",
|
||||
"@rollup/rollup-android-arm64": "4.59.0",
|
||||
"@rollup/rollup-darwin-arm64": "4.59.0",
|
||||
"@rollup/rollup-darwin-x64": "4.59.0",
|
||||
"@rollup/rollup-freebsd-arm64": "4.59.0",
|
||||
"@rollup/rollup-freebsd-x64": "4.59.0",
|
||||
"@rollup/rollup-linux-arm-gnueabihf": "4.59.0",
|
||||
"@rollup/rollup-linux-arm-musleabihf": "4.59.0",
|
||||
"@rollup/rollup-linux-arm64-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-arm64-musl": "4.59.0",
|
||||
"@rollup/rollup-linux-loong64-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-loong64-musl": "4.59.0",
|
||||
"@rollup/rollup-linux-ppc64-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-ppc64-musl": "4.59.0",
|
||||
"@rollup/rollup-linux-riscv64-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-riscv64-musl": "4.59.0",
|
||||
"@rollup/rollup-linux-s390x-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-x64-gnu": "4.59.0",
|
||||
"@rollup/rollup-linux-x64-musl": "4.59.0",
|
||||
"@rollup/rollup-openbsd-x64": "4.59.0",
|
||||
"@rollup/rollup-openharmony-arm64": "4.59.0",
|
||||
"@rollup/rollup-win32-arm64-msvc": "4.59.0",
|
||||
"@rollup/rollup-win32-ia32-msvc": "4.59.0",
|
||||
"@rollup/rollup-win32-x64-gnu": "4.59.0",
|
||||
"@rollup/rollup-win32-x64-msvc": "4.59.0",
|
||||
"fsevents": "~2.3.2"
|
||||
}
|
||||
},
|
||||
@ -4173,11 +4218,13 @@
|
||||
}
|
||||
},
|
||||
"node_modules/serialize-javascript": {
|
||||
"version": "6.0.2",
|
||||
"version": "7.0.4",
|
||||
"resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-7.0.4.tgz",
|
||||
"integrity": "sha512-DuGdB+Po43Q5Jxwpzt1lhyFSYKryqoNjQSA9M92tyw0lyHIOur+XCalOUe0KTJpyqzT8+fQ5A0Jf7vCx/NKmIg==",
|
||||
"dev": true,
|
||||
"license": "BSD-3-Clause",
|
||||
"dependencies": {
|
||||
"randombytes": "^2.1.0"
|
||||
"engines": {
|
||||
"node": ">=20.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/serve-static": {
|
||||
|
||||
@ -70,7 +70,7 @@
|
||||
"@rollup/plugin-commonjs": "^28.0.0",
|
||||
"@rollup/plugin-json": "^6.1.0",
|
||||
"@rollup/plugin-node-resolve": "^15.3.0",
|
||||
"@rollup/plugin-terser": "^0.4.4",
|
||||
"@rollup/plugin-terser": "^1.0.0",
|
||||
"@rollup/plugin-typescript": "^12.1.0",
|
||||
"eslint": "^10.0.0",
|
||||
"eslint-plugin-compat": "^6.0.1",
|
||||
|
||||
@ -102,7 +102,7 @@ const factory = (UserObject, Util, Hash,
|
||||
// Folder is being deleted by its owner, don't deprecate it
|
||||
return;
|
||||
}
|
||||
if (Env.user.userObject.readOnly) {
|
||||
if (Env.user.userObject.readOnly || !reason) {
|
||||
// In a read-only team, we can't deprecate a shared folder
|
||||
// Use a empty object with a deprecated flag...
|
||||
var lm = { proxy: { deprecated: true } };
|
||||
@ -143,10 +143,10 @@ const factory = (UserObject, Util, Hash,
|
||||
var _ownedByMe = function (Env, owners) {
|
||||
return Array.isArray(owners) && owners.indexOf(Env.edPublic) !== -1;
|
||||
};
|
||||
var _ownedByOther = function (Env, owners) {
|
||||
return Array.isArray(owners) && owners.length &&
|
||||
(!Env.edPublic || owners.indexOf(Env.edPublic) === -1);
|
||||
};
|
||||
// var _ownedByOther = function (Env, owners) {
|
||||
// return Array.isArray(owners) && owners.length &&
|
||||
// (!Env.edPublic || owners.indexOf(Env.edPublic) === -1);
|
||||
// };
|
||||
|
||||
var _getUserObjects = function (Env) {
|
||||
var userObjects = [Env.user.userObject];
|
||||
@ -1307,37 +1307,30 @@ const factory = (UserObject, Util, Hash,
|
||||
*/
|
||||
|
||||
var excludeInvalidIdentifiers = function (result) {
|
||||
return result.filter(function (channel) {
|
||||
const filter = (channel) => {
|
||||
if (typeof(channel) !== 'string') { return; }
|
||||
return [32, 48].indexOf(channel.length) !== -1;
|
||||
});
|
||||
};
|
||||
|
||||
let newSet = new Set();
|
||||
for (var channel of result) {
|
||||
if(filter(channel)) { newSet.add(channel); }
|
||||
}
|
||||
return newSet;
|
||||
};
|
||||
|
||||
// Get the list of channels filtered by a type (expirable channels, owned channels, pin list)
|
||||
var getChannelsList = function (Env, type) {
|
||||
var result = [];
|
||||
//var result = [];
|
||||
let result = new Set();
|
||||
var addChannel = function (userObject) {
|
||||
if (type === 'expirable') {
|
||||
return function (fileId) {
|
||||
var data = userObject.getFileData(fileId);
|
||||
if (!data) { return; }
|
||||
// Don't push duplicates
|
||||
if (result.indexOf(data.channel) !== -1) { return; }
|
||||
// Return pads owned by someone else or expired by time
|
||||
if (_ownedByOther(Env, data.owners) || (data.expire && data.expire < (+new Date()))) {
|
||||
result.push(data.channel);
|
||||
}
|
||||
};
|
||||
}
|
||||
if (type === 'owned') {
|
||||
return function (fileId) {
|
||||
var data = userObject.getFileData(fileId);
|
||||
if (!data) { return; }
|
||||
// Don't push duplicates
|
||||
if (result.indexOf(data.channel) !== -1) { return; }
|
||||
// Return owned pads
|
||||
if (_ownedByMe(Env, data.owners)) {
|
||||
result.push(data.channel);
|
||||
result.add(data.channel);
|
||||
}
|
||||
};
|
||||
}
|
||||
@ -1345,37 +1338,31 @@ const factory = (UserObject, Util, Hash,
|
||||
return function (fileId) {
|
||||
var data = userObject.getFileData(fileId);
|
||||
if (!data) { return; }
|
||||
// Don't pin pads owned by someone else
|
||||
//if (_ownedByOther(Env, data.owners)) { return; }
|
||||
// Pin onlyoffice checkpoints
|
||||
if (data.lastVersion) {
|
||||
var otherChan = Hash.hrefToHexChannelId(data.lastVersion);
|
||||
if (result.indexOf(otherChan) === -1) {
|
||||
result.push(otherChan);
|
||||
}
|
||||
result.add(otherChan);
|
||||
}
|
||||
// Pin form answers channels
|
||||
if (data.answersChannel && result.indexOf(data.answersChannel) === -1) {
|
||||
result.push(data.answersChannel);
|
||||
if (data.answersChannel) {
|
||||
result.add(data.answersChannel);
|
||||
}
|
||||
// Pin onlyoffice realtime patches
|
||||
if (data.rtChannel && result.indexOf(data.rtChannel) === -1) {
|
||||
result.push(data.rtChannel);
|
||||
if (data.rtChannel) {
|
||||
result.add(data.rtChannel);
|
||||
}
|
||||
// Pin onlyoffice images
|
||||
if (data.ooImages && Array.isArray(data.ooImages)) {
|
||||
Array.prototype.push.apply(result, data.ooImages);
|
||||
data.ooImages.forEach(id => result.add(id));
|
||||
}
|
||||
// Pin the pad
|
||||
if (result.indexOf(data.channel) === -1) {
|
||||
result.push(data.channel);
|
||||
}
|
||||
result.add(data.channel);
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
if (type === 'owned' && !Env.edPublic) { return excludeInvalidIdentifiers(result); }
|
||||
if (type === 'pin' && !Env.edPublic) { return excludeInvalidIdentifiers(result); }
|
||||
if (type === 'owned' && !Env.edPublic) { return result; }
|
||||
if (type === 'pin' && !Env.edPublic) { return result; }
|
||||
|
||||
// Get the list of user objects
|
||||
var userObjects = _getUserObjects(Env);
|
||||
@ -1393,7 +1380,7 @@ const factory = (UserObject, Util, Hash,
|
||||
}).map(function (fId) {
|
||||
return Env.user.proxy[UserObject.SHARED_FOLDERS][fId].channel;
|
||||
});
|
||||
Array.prototype.push.apply(result, sfOwned);
|
||||
sfOwned.forEach(id => result.add(id));
|
||||
}
|
||||
if (type === "pin") {
|
||||
var sfChannels = Object.keys(Env.folders).map(function (fId) {
|
||||
@ -1403,7 +1390,7 @@ const factory = (UserObject, Util, Hash,
|
||||
console.error(err);
|
||||
}
|
||||
}).filter(Boolean);
|
||||
Array.prototype.push.apply(result, sfChannels);
|
||||
sfChannels.forEach(id => result.add(id));
|
||||
}
|
||||
|
||||
return excludeInvalidIdentifiers(result);
|
||||
|
||||
@ -5,7 +5,7 @@
|
||||
const factory = (Sortify, UserObject, ProxyManager,
|
||||
Migrate, Hash, Util, Constants, Feedback,
|
||||
Realtime, Messaging, Pinpad, Rpc, Cryptget, Cache,
|
||||
SF, AccountTS, DriveTS, PadTS, Cursor,
|
||||
SF, AccountTS, DriveTS, PadTS, Form, Cursor,
|
||||
Support, Integration, OnlyOffice,
|
||||
Mailbox, Profile, Team, Messenger, History,
|
||||
Calendar, BadgeTS, Block, NetConfig,
|
||||
@ -70,6 +70,9 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
Store.drive = Drive.initAPI({
|
||||
Store, store, postMessage, broadcast
|
||||
});
|
||||
Store.form = Form.init({
|
||||
Store, store, postMessage, broadcast
|
||||
});
|
||||
|
||||
// Drive clients
|
||||
var driveEventClients = [];
|
||||
@ -213,31 +216,36 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
});
|
||||
};
|
||||
|
||||
var getUserChannelList = function () {
|
||||
var userChannel = `${store.driveChannel}#drive`;
|
||||
var getUserChannelList = function (compareHash) {
|
||||
// If compareHash is true, we're going to compare our local
|
||||
// hash with the server one. We must remove the "#drive" tag
|
||||
// and the block (which isn't a channel)
|
||||
|
||||
var userChannel = compareHash ? store.driveChannel
|
||||
: `${store.driveChannel}#drive`;
|
||||
if (!userChannel) { return null; }
|
||||
|
||||
// Get the list of pads' channel ID in your drive
|
||||
// This list is filtered so that it doesn't include pad owned by other users
|
||||
// It now includes channels from shared folders
|
||||
var list = store.manager.getChannelsList('pin');
|
||||
var list = store.manager.getChannelsList('pin'); // "list" is a Set
|
||||
|
||||
// Get the avatar & profile
|
||||
var profile = store.proxy.profile;
|
||||
if (profile) {
|
||||
var profileChan = profile.edit ? Hash.hrefToHexChannelId('/profile/#' + profile.edit, null) : null;
|
||||
if (profileChan) { list.push(profileChan); }
|
||||
if (profileChan) { list.add(profileChan); }
|
||||
var avatarChan = profile.avatar ? Hash.hrefToHexChannelId(profile.avatar, null) : null;
|
||||
if (avatarChan) { list.push(avatarChan); }
|
||||
if (avatarChan) { list.add(avatarChan); }
|
||||
}
|
||||
|
||||
if (store.proxy.todo) {
|
||||
list.push(Hash.hrefToHexChannelId('/todo/#' + store.proxy.todo, null));
|
||||
list.add(Hash.hrefToHexChannelId('/todo/#' + store.proxy.todo, null));
|
||||
}
|
||||
|
||||
if (store.proxy.friends) {
|
||||
var fList = Messaging.getFriendChannelsList(store.proxy);
|
||||
list = list.concat(fList);
|
||||
fList.forEach(id => list.add(id));
|
||||
}
|
||||
|
||||
if (store.proxy.mailboxes) {
|
||||
@ -245,34 +253,23 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
if (m === "broadcast" && !store.isAdmin) { return; }
|
||||
return store.proxy.mailboxes[m].channel;
|
||||
}).filter(Boolean);
|
||||
list = list.concat(mList);
|
||||
mList.forEach(id => list.add(id));
|
||||
}
|
||||
|
||||
if (store.proxy.calendars) {
|
||||
var cList = Object.keys(store.proxy.calendars).map(function (c) {
|
||||
return store.proxy.calendars[c].channel;
|
||||
});
|
||||
list = list.concat(cList);
|
||||
cList.forEach(id => list.add(id));
|
||||
}
|
||||
|
||||
list.push(userChannel);
|
||||
list.add(userChannel);
|
||||
|
||||
if (store.data && store.data.blockId) {
|
||||
list.push(`${store.data.blockId}#block`);
|
||||
if (store.data && store.data.blockId && !compareHash) {
|
||||
list.add(`${store.data.blockId}#block`);
|
||||
}
|
||||
|
||||
list.sort();
|
||||
|
||||
return list;
|
||||
};
|
||||
|
||||
var getExpirableChannelList = function () {
|
||||
return store.manager.getChannelsList('expirable');
|
||||
};
|
||||
|
||||
var getCanonicalChannelList = function (expirable) {
|
||||
var list = expirable ? getExpirableChannelList() : getUserChannelList();
|
||||
return Util.deduplicateString(list).sort();
|
||||
return Array.from(list).sort();
|
||||
};
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
@ -352,7 +349,7 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
var arePinsSynced = function (cb) {
|
||||
if (!store.rpc) { return void cb({error: 'RPC_NOT_READY'}); }
|
||||
|
||||
var list = getCanonicalChannelList(false);
|
||||
var list = getUserChannelList(true);
|
||||
var local = Hash.hashChannelList(list);
|
||||
store.rpc.getServerHash(function (e, hash) {
|
||||
if (e) { return void cb(e); }
|
||||
@ -363,7 +360,7 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
var resetPins = function (cb) {
|
||||
if (!store.rpc) { return void cb({error: 'RPC_NOT_READY'}); }
|
||||
|
||||
var list = getCanonicalChannelList(false);
|
||||
var list = getUserChannelList();
|
||||
store.rpc.reset(list, function (e) {
|
||||
if (e) { return void cb(e); }
|
||||
cb(null);
|
||||
@ -524,7 +521,7 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
|
||||
Store.getDeletedPads = function (clientId, data, cb) {
|
||||
if (!store.anon_rpc) { return void cb({error: 'ANON_RPC_NOT_READY'}); }
|
||||
var list = (data && data.list) || getCanonicalChannelList(true);
|
||||
var list = data?.list;
|
||||
if (!Array.isArray(list)) {
|
||||
return void cb({error: 'INVALID_FILE_LIST'});
|
||||
}
|
||||
@ -705,8 +702,8 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
};
|
||||
|
||||
var getOwnedPads = function (account) {
|
||||
var list = [];
|
||||
if (account) {
|
||||
var list = [];
|
||||
if (store.proxy.todo) {
|
||||
// No password for todo
|
||||
list.push(Hash.hrefToHexChannelId('/todo/#' + store.proxy.todo, null));
|
||||
@ -718,29 +715,17 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
if (store.proxy.mailboxes) {
|
||||
Object.keys(store.proxy.mailboxes || {}).forEach(function (id) {
|
||||
if (id === 'supportadmin') { return; }
|
||||
if (id === 'supportteam') { return; }
|
||||
var m = store.proxy.mailboxes[id];
|
||||
list.push(m.channel);
|
||||
});
|
||||
}
|
||||
} else {
|
||||
list = store.manager.getChannelsList('owned');
|
||||
/*
|
||||
if (store.proxy.teams) {
|
||||
Object.keys(store.proxy.teams || {}).forEach(function (id) {
|
||||
var t = store.proxy.teams[id];
|
||||
if (t.owner) {
|
||||
list.push(t.channel);
|
||||
list.push(t.keys.roster.channel);
|
||||
list.push(t.keys.chat.channel);
|
||||
}
|
||||
});
|
||||
}
|
||||
*/
|
||||
return list.filter(function (channel) {
|
||||
if (typeof(channel) !== 'string') { return; }
|
||||
return [32, 48].indexOf(channel.length) !== -1;
|
||||
});
|
||||
}
|
||||
return list.filter(function (channel) {
|
||||
if (typeof(channel) !== 'string') { return; }
|
||||
return [32, 48].indexOf(channel.length) !== -1;
|
||||
});
|
||||
return Array.from(store.manager.getChannelsList('owned'));
|
||||
};
|
||||
var removeOwnedPads = function (account, waitFor) {
|
||||
// Delete owned pads
|
||||
@ -928,7 +913,7 @@ const factory = (Sortify, UserObject, ProxyManager,
|
||||
// Reset the drive part of the userObject (from settings)
|
||||
Store.resetDrive = function (clientId, data, cb) {
|
||||
nThen(function (waitFor) {
|
||||
removeOwnedPads(waitFor);
|
||||
removeOwnedPads(false, waitFor);
|
||||
}).nThen(function () {
|
||||
store.proxy.drive = store.userObject.getStructure();
|
||||
sendDriveEvent('DRIVE_CHANGE', {
|
||||
@ -3057,6 +3042,7 @@ module.exports = factory(
|
||||
require('./components/account'), // .ts
|
||||
require('./components/drive'), // .ts
|
||||
require('./components/pad'), // .ts
|
||||
require('./components/form'),
|
||||
require('./modules/cursor'),
|
||||
require('./modules/support'),
|
||||
require('./modules/integration'),
|
||||
|
||||
122
src/worker/components/form.js
Normal file
122
src/worker/components/form.js
Normal file
@ -0,0 +1,122 @@
|
||||
// SPDX-FileCopyrightText: 2026 XWiki CryptPad Team <contact@cryptpad.org> and contributors
|
||||
//
|
||||
// SPDX-License-Identifier: AGPL-3.0-or-later
|
||||
|
||||
const factory = (Util, Nacl, CPNetflux, Crypto) => {
|
||||
const Form = {};
|
||||
|
||||
const u8_slice = (A, start, end) => {
|
||||
return new Uint8Array(Array.prototype.slice.call(A, start, end));
|
||||
};
|
||||
const checkAnonProof = (proofObj, channel, curvePrivate) => {
|
||||
const pub = proofObj.key;
|
||||
const proofTxt = proofObj.proof;
|
||||
try {
|
||||
let u8_bundle = Util.decodeBase64(proofTxt);
|
||||
let u8_nonce = u8_slice(u8_bundle, 0, Nacl.box.nonceLength);
|
||||
let u8_cipher = u8_slice(u8_bundle, Nacl.box.nonceLength);
|
||||
let u8_plain = Nacl.box.open(
|
||||
u8_cipher,
|
||||
u8_nonce,
|
||||
Util.decodeBase64(pub),
|
||||
Util.decodeBase64(curvePrivate)
|
||||
);
|
||||
return channel === Util.encodeUTF8(u8_plain);
|
||||
} catch (e) {
|
||||
console.error(e);
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
const getResponses = (ctx, data, cb) => {
|
||||
const { store, Store } = ctx;
|
||||
const {
|
||||
cryptoKeys, // encryptor keys
|
||||
channel, // form responses channel id
|
||||
edPublic, // my edPublic
|
||||
validateKey, // form responses secondaryValidateKey
|
||||
deleteLines,
|
||||
cantEdit
|
||||
} = data;
|
||||
|
||||
const curvePrivate = cryptoKeys.curvePrivate;
|
||||
const crypto = Crypto.Mailbox.createEncryptor(cryptoKeys);
|
||||
|
||||
let config = {
|
||||
network: store.network,
|
||||
channel,
|
||||
noChainPad: true,
|
||||
validateKey,
|
||||
owners: [edPublic],
|
||||
crypto: crypto,
|
||||
metadata: {
|
||||
deleteLines: true
|
||||
}
|
||||
};
|
||||
|
||||
let cpNf;
|
||||
let results = {};
|
||||
|
||||
config.onError = (info) => {
|
||||
cb({ error: info.type });
|
||||
cpNf?.stop();
|
||||
};
|
||||
config.onRejected = Store.onRejected;
|
||||
|
||||
config.onReady = function () {
|
||||
cb({ results });
|
||||
cpNf?.stop();
|
||||
};
|
||||
|
||||
config.onMessage = (msg, peer, vKey, isCp, hash, senderCurve, cfg) => {
|
||||
let parsed = Util.tryParse(msg);
|
||||
if (!parsed) { return; }
|
||||
let uid = parsed._uid || '000';
|
||||
|
||||
// If we have a "non-anonymous" answer, it may be the edition of a
|
||||
// previous anonymous answer. Check if a previous anonymous answer exists
|
||||
// with the same uid and delete it.
|
||||
if (parsed._proof) {
|
||||
const check = checkAnonProof(parsed._proof, channel, curvePrivate);
|
||||
const theirAnonKey = parsed._proof.key;
|
||||
if (check && results[theirAnonKey] && results[theirAnonKey][uid]) {
|
||||
delete results[theirAnonKey][uid];
|
||||
}
|
||||
}
|
||||
|
||||
parsed._time = cfg && cfg.time;
|
||||
if (deleteLines) { parsed._hash = hash; }
|
||||
|
||||
if (cantEdit && results[senderCurve]
|
||||
&& results[senderCurve][uid]) { return; }
|
||||
results[senderCurve] = results[senderCurve] || {};
|
||||
results[senderCurve][uid] = {
|
||||
msg: parsed,
|
||||
hash: hash,
|
||||
time: cfg && cfg.time
|
||||
};
|
||||
};
|
||||
cpNf = CPNetflux.start(config);
|
||||
};
|
||||
|
||||
Form.init = (config) => {
|
||||
const { store, Store } = config;
|
||||
|
||||
const ctx = { store, Store };
|
||||
const form = {}
|
||||
|
||||
form.getResponses = (cId, data, cb) => {
|
||||
return getResponses(ctx, data, cb);
|
||||
};
|
||||
|
||||
return form;
|
||||
};
|
||||
|
||||
return Form;
|
||||
};
|
||||
module.exports = factory(
|
||||
require("../../common/common-util"),
|
||||
require('tweetnacl/nacl-fast'),
|
||||
require("chainpad-netflux"),
|
||||
require("chainpad-crypto")
|
||||
);
|
||||
@ -85,6 +85,8 @@ const factory = AStore => {
|
||||
CHANGE_PAD_PASSWORD_PIN: Store.changePadPasswordPin,
|
||||
GET_SNAPSHOT: Store.getSnapshot,
|
||||
DELETE_MAILBOX_MESSAGE: Store.deleteMailboxMessage,
|
||||
// Form
|
||||
FORM_GET_RESPONSES: Store.form?.getResponses,
|
||||
// Drive
|
||||
DRIVE_USEROBJECT: Store.userObjectCommand,
|
||||
GET_DRIVE: Store.drive.get,
|
||||
|
||||
@ -14,7 +14,7 @@ const factory = (Util, Hash,
|
||||
var TYPES = [
|
||||
'notifications',
|
||||
'supportteam',
|
||||
//'broadcast'
|
||||
'broadcast'
|
||||
];
|
||||
var BLOCKING_TYPES = [
|
||||
];
|
||||
|
||||
@ -123,41 +123,41 @@ const factory = (Util, Hash, Constants, Realtime, ProxyManager,
|
||||
}
|
||||
};
|
||||
|
||||
var getTeamChannelList = function (ctx, id) {
|
||||
var getTeamChannelList = function (ctx, compareHash, id) {
|
||||
// Get the list of pads' channel ID in your drive
|
||||
// This list is filtered so that it doesn't include pad owned by other users
|
||||
// It now includes channels from shared folders
|
||||
var store = ctx.teams[id];
|
||||
if (!store) { return null; }
|
||||
var list = store.manager.getChannelsList('pin');
|
||||
var list = store.manager.getChannelsList('pin'); // list is a Set
|
||||
|
||||
var team = ctx.store.proxy.teams[id];
|
||||
list.push(`${team.channel}#drive`);
|
||||
const teamChan = compareHash ? team.channel : `${team.channel}#drive`;
|
||||
list.add(teamChan);
|
||||
var chatChannel = Util.find(team, ['keys', 'chat', 'channel']);
|
||||
var membersChannel = Util.find(team, ['keys', 'roster', 'channel']);
|
||||
var mailboxChannel = Util.find(team, ['keys', 'mailbox', 'channel']);
|
||||
if (chatChannel) { list.push(chatChannel); }
|
||||
if (membersChannel) { list.push(membersChannel); }
|
||||
if (mailboxChannel) { list.push(mailboxChannel); }
|
||||
if (chatChannel) { list.add(chatChannel); }
|
||||
if (membersChannel) { list.add(membersChannel); }
|
||||
if (mailboxChannel) { list.add(mailboxChannel); }
|
||||
|
||||
if (store.proxy.calendars) {
|
||||
var cList = Object.keys(store.proxy.calendars).map(function (c) {
|
||||
return store.proxy.calendars[c].channel;
|
||||
});
|
||||
list = list.concat(cList);
|
||||
cList.forEach(id => list.add(id));
|
||||
}
|
||||
|
||||
var state = store.roster.getState();
|
||||
if (state.members) {
|
||||
Object.keys(state.members).forEach(function (curve) {
|
||||
var m = state.members[curve];
|
||||
if (m.inviteChannel && m.pending) { list.push(m.inviteChannel); }
|
||||
if (m.previewChannel && m.pending) { list.push(m.previewChannel); }
|
||||
if (m.inviteChannel && m.pending) { list.add(m.inviteChannel); }
|
||||
if (m.previewChannel && m.pending) { list.add(m.previewChannel); }
|
||||
});
|
||||
}
|
||||
|
||||
list.sort();
|
||||
return list;
|
||||
return Array.from(list).sort();
|
||||
};
|
||||
|
||||
var handleSharedFolder = function (ctx, id, sfId, rt) {
|
||||
@ -365,14 +365,15 @@ const factory = (Util, Hash, Constants, Realtime, ProxyManager,
|
||||
});
|
||||
}).nThen(function () {
|
||||
if (!team.rpc) { return; }
|
||||
var list = getTeamChannelList(ctx, id);
|
||||
var list = getTeamChannelList(ctx, true, id);
|
||||
var local = Hash.hashChannelList(list);
|
||||
// Check pin list
|
||||
team.rpc.getServerHash(function (e, hash) {
|
||||
if (e) { return void console.warn(e); }
|
||||
if (hash !== local) {
|
||||
// Reset pin list
|
||||
team.rpc.reset(list, function (e/*, hash*/) {
|
||||
var list2 = getTeamChannelList(ctx, false, id);
|
||||
team.rpc.reset(list2, function (e/*, hash*/) {
|
||||
if (e) { console.warn(e); }
|
||||
});
|
||||
}
|
||||
@ -853,7 +854,7 @@ const factory = (Util, Hash, Constants, Realtime, ProxyManager,
|
||||
// For each pad, check on the server if there are other owners.
|
||||
// If yes, then remove yourself as an owner
|
||||
// If no, delete the pad
|
||||
var ownedPads = team.manager.getChannelsList('owned');
|
||||
var ownedPads = Array.from(team.manager.getChannelsList('owned'));
|
||||
var sem = Util.Saferphore.create(10);
|
||||
ownedPads.forEach(function (c) {
|
||||
var w = waitFor();
|
||||
|
||||
@ -289,6 +289,10 @@ define([
|
||||
});
|
||||
});
|
||||
};
|
||||
common.getFormResponses = (data, cb) => {
|
||||
postMessage("FORM_GET_RESPONSES", data, cb);
|
||||
};
|
||||
|
||||
common.muteChannel = function (channel, state, cb) {
|
||||
var mutedChannels = [];
|
||||
nThen(function (waitFor) {
|
||||
|
||||
@ -1960,51 +1960,65 @@ define([
|
||||
// It seems we have performance issues when we open and close a lot of channels over
|
||||
// the same network, maybe a memory leak. To fix this, we kill and create a new
|
||||
// network every 30 cryptget calls (1 call = 1 channel)
|
||||
var cgNetwork;
|
||||
var whenCGReady = function (cb) {
|
||||
if (cgNetwork && cgNetwork !== true) { console.log(cgNetwork); return void cb(); }
|
||||
setTimeout(function () {
|
||||
whenCGReady(cb);
|
||||
}, 500);
|
||||
};
|
||||
var i = 0;
|
||||
const cgNetworkStatus = {};
|
||||
let cgNetworkId = 0;
|
||||
let cgNetworkIndex = 0;
|
||||
let cgNetwork;
|
||||
|
||||
sframeChan.on('Q_CRYPTGET', function (data, cb) {
|
||||
var keys;
|
||||
var todo = function () {
|
||||
data.opts.network = cgNetwork;
|
||||
var todo = function (network) {
|
||||
data.opts.network = network;
|
||||
data.opts.accessKeys = keys;
|
||||
Cryptget.get(data.hash, function (err, val) {
|
||||
cb({
|
||||
error: err,
|
||||
data: val
|
||||
|
||||
// Use promises to know when all the cryptget are done
|
||||
// so that we can disconnect the network
|
||||
cgNetworkStatus[cgNetworkId] ||= [];
|
||||
cgNetworkStatus.push(new Promise((res) => {
|
||||
Cryptget.get(data.hash, function (err, val) {
|
||||
res(network);
|
||||
cb({
|
||||
error: err,
|
||||
data: val
|
||||
});
|
||||
}, data.opts, function (progress) {
|
||||
sframeChan.event("EV_CRYPTGET_PROGRESS", {
|
||||
hash: data.hash,
|
||||
progress: progress,
|
||||
});
|
||||
});
|
||||
}, data.opts, function (progress) {
|
||||
sframeChan.event("EV_CRYPTGET_PROGRESS", {
|
||||
hash: data.hash,
|
||||
progress: progress,
|
||||
});
|
||||
});
|
||||
}));
|
||||
};
|
||||
//return void todo();
|
||||
if (i > 30) {
|
||||
i = 0;
|
||||
|
||||
// Every 30 cryptget, make a new network
|
||||
if (cgNetworkIndex > 30) {
|
||||
cgNetworkIndex = 0;
|
||||
// Make sure all previous command are done and disconnect
|
||||
const prom = cpNetworkStatus[cgNetworkId] || [];
|
||||
Promise.all(prom).then((nw) => {
|
||||
let network = nw[0];
|
||||
if (typeof(network?.disconnect) === "function") {
|
||||
network.disconnect();
|
||||
}
|
||||
});
|
||||
cgNetwork = undefined;
|
||||
cgNetworkId ++;
|
||||
}
|
||||
i++;
|
||||
cgNetworkIndex++;
|
||||
|
||||
Cryptpad.getAccessKeys(function (_keys) {
|
||||
keys = _keys;
|
||||
if (!cgNetwork) {
|
||||
cgNetwork = true;
|
||||
return void Cryptpad.makeNetwork(function (err, nw) {
|
||||
console.log(nw);
|
||||
cgNetwork = nw;
|
||||
todo();
|
||||
cgNetwork = new Promise((res) => {
|
||||
Cryptpad.makeNetwork(function (err, nw) {
|
||||
res(nw);
|
||||
//cgNetwork = nw;
|
||||
todo(nw);
|
||||
});
|
||||
});
|
||||
} else if (cgNetwork === true) {
|
||||
return void whenCGReady(todo);
|
||||
return;
|
||||
}
|
||||
todo();
|
||||
cgNetwork.then(todo);
|
||||
});
|
||||
});
|
||||
sframeChan.on('EV_CRYPTGET_DISCONNECT', function () {
|
||||
|
||||
2
www/common/worker.bundle.min.js
vendored
2
www/common/worker.bundle.min.js
vendored
File diff suppressed because one or more lines are too long
@ -135,28 +135,6 @@ define([
|
||||
});
|
||||
});
|
||||
});
|
||||
var u8_slice = function (A, start, end) {
|
||||
return new Uint8Array(Array.prototype.slice.call(A, start, end));
|
||||
};
|
||||
var checkAnonProof = function (proofObj, channel, curvePrivate) {
|
||||
var pub = proofObj.key;
|
||||
var proofTxt = proofObj.proof;
|
||||
try {
|
||||
var u8_bundle = Util.decodeBase64(proofTxt);
|
||||
var u8_nonce = u8_slice(u8_bundle, 0, Nacl.box.nonceLength);
|
||||
var u8_cipher = u8_slice(u8_bundle, Nacl.box.nonceLength);
|
||||
var u8_plain = Nacl.box.open(
|
||||
u8_cipher,
|
||||
u8_nonce,
|
||||
Util.decodeBase64(pub),
|
||||
Util.decodeBase64(curvePrivate)
|
||||
);
|
||||
return channel === Util.encodeUTF8(u8_plain);
|
||||
} catch (e) {
|
||||
console.error(e);
|
||||
return false;
|
||||
}
|
||||
};
|
||||
sframeChan.on('Q_FORM_FETCH_ANSWERS', function (data, _cb) {
|
||||
var formHref = data.href;
|
||||
var cb = Utils.Util.once(_cb);
|
||||
@ -178,7 +156,6 @@ define([
|
||||
Cryptpad.getAccessKeys(w(function (_keys) {
|
||||
if (!Array.isArray(_keys)) { return; }
|
||||
accessKeys = _keys;
|
||||
|
||||
_keys.some(function (_k) {
|
||||
if ((personalDrive && !_k.id) || Cryptpad.initialTeam === Number(_k.id)) {
|
||||
myKeys = _k;
|
||||
@ -194,14 +171,10 @@ define([
|
||||
}
|
||||
myFormKeys = keys;
|
||||
}));
|
||||
Cryptpad.makeNetwork(w(function (err, nw) {
|
||||
network = nw;
|
||||
}));
|
||||
Cryptpad.getPadMetadata({channel: data.channel}, w(function (md) {
|
||||
if (md && md.deleteLines) { deleteLines = true; }
|
||||
}));
|
||||
}).nThen(function () {
|
||||
if (!network) { return void cb({error: "E_CONNECT"}); }
|
||||
if (myFormKeys.formSeed) {
|
||||
myFormKeys = Cryptpad.getAnonymousKeys(myFormKeys.formSeed, data.channel, Utils);
|
||||
}
|
||||
@ -220,86 +193,33 @@ define([
|
||||
publicKey = formData?.form_public;
|
||||
var curvePrivate = privateKey || data.privateKey;
|
||||
if (!curvePrivate) { return void cb({error: 'EFORBIDDEN'}); }
|
||||
var crypto = Utils.Crypto.Mailbox.createEncryptor({
|
||||
var cryptoKeys = {
|
||||
curvePrivate: curvePrivate,
|
||||
curvePublic: publicKey || data.publicKey,
|
||||
validateKey: data.validateKey
|
||||
});
|
||||
};
|
||||
|
||||
var config = {
|
||||
network: network,
|
||||
Cryptpad.getFormResponses({
|
||||
cryptoKeys,
|
||||
channel: data.channel,
|
||||
noChainPad: true,
|
||||
edPublic: myKeys.edPublic,
|
||||
validateKey: keys.secondaryValidateKey,
|
||||
owners: [myKeys.edPublic],
|
||||
crypto: crypto,
|
||||
metadata: {
|
||||
deleteLines: true
|
||||
}
|
||||
//Cache: Utils.Cache // TODO enable cache for form responses when the cache stops evicting old answers
|
||||
};
|
||||
var results = {};
|
||||
config.onError = function (info) {
|
||||
cb({ error: info.type });
|
||||
};
|
||||
config.onRejected = function (data, cb) {
|
||||
if (!Array.isArray(data) || !data.length || data[0].length !== 16) {
|
||||
return void cb(true);
|
||||
}
|
||||
if (!Array.isArray(accessKeys)) { return void cb(true); }
|
||||
network.historyKeeper = data[0];
|
||||
nThen(function (waitFor) {
|
||||
accessKeys.forEach(function (obj) {
|
||||
Pinpad.create(network, obj, waitFor(function (e) {
|
||||
if (e) { console.error(e); }
|
||||
}));
|
||||
});
|
||||
}).nThen(function () {
|
||||
cb();
|
||||
});
|
||||
};
|
||||
config.onReady = function () {
|
||||
var myKey;
|
||||
cantEdit: data.cantEdit,
|
||||
deleteLines
|
||||
}, (obj) => {
|
||||
if (obj?.error) { return void cb(obj); }
|
||||
const results = obj.results;
|
||||
|
||||
// If we have submitted an anonymous answer, retrieve it
|
||||
let myKey;
|
||||
if (myFormKeys.curvePublic && results[myFormKeys.curvePublic]) {
|
||||
myKey = myFormKeys.curvePublic;
|
||||
}
|
||||
|
||||
cb({
|
||||
noDriveAnswered: noDriveAnswered,
|
||||
myKey: myKey,
|
||||
results: results
|
||||
noDriveAnswered, myKey, results
|
||||
});
|
||||
network.disconnect();
|
||||
};
|
||||
config.onMessage = function (msg, peer, vKey, isCp, hash, senderCurve, cfg) {
|
||||
var parsed = Utils.Util.tryParse(msg);
|
||||
if (!parsed) { return; }
|
||||
var uid = parsed._uid || '000';
|
||||
|
||||
// If we have a "non-anonymous" answer, it may be the edition of a
|
||||
// previous anonymous answer. Check if a previous anonymous answer exists
|
||||
// with the same uid and delete it.
|
||||
if (parsed._proof) {
|
||||
var check = checkAnonProof(parsed._proof, data.channel, curvePrivate);
|
||||
var theirAnonKey = parsed._proof.key;
|
||||
if (check && results[theirAnonKey] && results[theirAnonKey][uid]) {
|
||||
delete results[theirAnonKey][uid];
|
||||
}
|
||||
}
|
||||
|
||||
parsed._time = cfg && cfg.time;
|
||||
if (deleteLines) { parsed._hash = hash; }
|
||||
|
||||
if (data.cantEdit && results[senderCurve]
|
||||
&& results[senderCurve][uid]) { return; }
|
||||
results[senderCurve] = results[senderCurve] || {};
|
||||
results[senderCurve][uid] = {
|
||||
msg: parsed,
|
||||
hash: hash,
|
||||
time: cfg && cfg.time
|
||||
};
|
||||
};
|
||||
CPNetflux.start(config);
|
||||
});
|
||||
});
|
||||
});
|
||||
var noDriveSeed = Utils.Hash.createChannelId();
|
||||
|
||||
@ -25,6 +25,7 @@ define([
|
||||
'/common/diffMarked.js',
|
||||
'/common/sframe-common-codemirror.js',
|
||||
'/common/text-cursor.js',
|
||||
'/common/visible.js',
|
||||
'cm/lib/codemirror',
|
||||
'/components/chainpad/chainpad.dist.js',
|
||||
'tui-date-picker',
|
||||
@ -73,6 +74,7 @@ define([
|
||||
DiffMd,
|
||||
SFCodeMirror,
|
||||
TextCursor,
|
||||
Visible,
|
||||
CMeditor,
|
||||
ChainPad,
|
||||
DatePicker,
|
||||
@ -3280,6 +3282,8 @@ define([
|
||||
h('span.cp-button-name', Messages._getKey('form_results', [l])),
|
||||
]));
|
||||
var it = setInterval(function () {
|
||||
let visible = Visible.currently();
|
||||
if (!visible) { return; }
|
||||
sframeChan.query("Q_FORM_FETCH_ANSWERS", content.answers, function (err, obj) {
|
||||
var answers = obj && obj.results;
|
||||
var l = getAnswersLength(answers);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user