From 9b633251d578d80e1982048e261942a3d1793200 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Tue, 3 May 2022 21:52:44 +0100 Subject: [PATCH 01/38] Add README badges (#2335) --- README.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/README.md b/README.md index 5f60b5144cc..257337d2ca3 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,11 @@ +[![npm](https://img.shields.io/npm/v/matrix-js-sdk)](https://www.npmjs.com/package/matrix-js-sdk) +![Tests](https://github.com/matrix-org/matrix-js-sdk/actions/workflows/tests.yml/badge.svg) +![Static Analysis](https://github.com/matrix-org/matrix-js-sdk/actions/workflows/static_analysis.yml/badge.svg) +[![Quality Gate Status](https://sonarcloud.io/api/project_badges/measure?project=matrix-js-sdk&metric=alert_status)](https://sonarcloud.io/summary/new_code?id=matrix-js-sdk) +[![Coverage](https://sonarcloud.io/api/project_badges/measure?project=matrix-js-sdk&metric=coverage)](https://sonarcloud.io/summary/new_code?id=matrix-js-sdk) +[![Vulnerabilities](https://sonarcloud.io/api/project_badges/measure?project=matrix-js-sdk&metric=vulnerabilities)](https://sonarcloud.io/summary/new_code?id=matrix-js-sdk) +[![Bugs](https://sonarcloud.io/api/project_badges/measure?project=matrix-js-sdk&metric=bugs)](https://sonarcloud.io/summary/new_code?id=matrix-js-sdk) + Matrix Javascript SDK ===================== From 81c89f69c57f0fa3570b8d7e8ebbc3c544d13f22 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Tue, 3 May 2022 21:54:18 +0100 Subject: [PATCH 02/38] Create manual action for upgrading dependencies after rc cut (#2341) --- .github/workflows/upgrade_dependencies.yml | 24 ++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 .github/workflows/upgrade_dependencies.yml diff --git a/.github/workflows/upgrade_dependencies.yml b/.github/workflows/upgrade_dependencies.yml new file mode 100644 index 00000000000..37315444e7e --- /dev/null +++ b/.github/workflows/upgrade_dependencies.yml @@ -0,0 +1,24 @@ +name: Upgrade Dependencies +on: + workflow_dispatch: { } + workflow_call: { } +jobs: + upgrade: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + + - uses: actions/setup-node@v3 + with: + cache: 'yarn' + + - name: Upgrade + run: yarn upgrade && yarn install + + - name: Create Pull Request + uses: peter-evans/create-pull-request@v4 + with: + branch: actions/upgrade-deps + delete-branch: true + title: Upgrade dependencies + labels: T-Task From b86630f0e3733947caef6e7543c497be1e4e114f Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" <41898282+github-actions[bot]@users.noreply.github.com> Date: Tue, 3 May 2022 22:10:41 +0100 Subject: [PATCH 03/38] Upgrade dependencies (#2342) Co-authored-by: t3chguy --- package.json | 2 +- yarn.lock | 550 +++++++++++++++++++++++++-------------------------- 2 files changed, 266 insertions(+), 286 deletions(-) diff --git a/package.json b/package.json index f036645e320..0bc48f72721 100644 --- a/package.json +++ b/package.json @@ -3,7 +3,7 @@ "version": "17.1.0", "description": "Matrix Client-Server SDK for Javascript", "engines": { - "node": ">=12.9.0" + "node": ">=12.9.0" }, "scripts": { "prepublishOnly": "yarn build", diff --git a/yarn.lock b/yarn.lock index 84639c01de4..99d47e658b3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3,9 +3,9 @@ "@actions/core@^1.4.0": - version "1.6.0" - resolved "https://registry.yarnpkg.com/@actions/core/-/core-1.6.0.tgz#0568e47039bfb6a9170393a73f3b7eb3b22462cb" - integrity sha512-NB1UAZomZlCV/LmJqkLhNTqtKfFXJZAUPcfl/zqG7EfsQdeUJtaWO98SGbuQ3pydJ3fHl2CvI/51OKYlCYYcaw== + version "1.7.0" + resolved "https://registry.yarnpkg.com/@actions/core/-/core-1.7.0.tgz#f179a5a0bf5c1102d89b8cf1712825e763feaee4" + integrity sha512-7fPSS7yKOhTpgLMbw7lBLc1QJWvJBBAgyTX2PEhagWcKK8t0H8AKCoPMfnrHqIm5cRYH4QFPqD1/ruhuUE7YcQ== dependencies: "@actions/http-client" "^1.0.11" @@ -27,25 +27,25 @@ tunnel "0.0.6" "@ampproject/remapping@^2.1.0": - version "2.1.2" - resolved "https://registry.yarnpkg.com/@ampproject/remapping/-/remapping-2.1.2.tgz#4edca94973ded9630d20101cd8559cedb8d8bd34" - integrity sha512-hoyByceqwKirw7w3Z7gnIIZC3Wx3J484Y3L/cMpXFbr7d9ZQj2mODrirNzcJa+SM3UlpWXYvKV4RlRpFXlWgXg== + version "2.2.0" + resolved "https://registry.yarnpkg.com/@ampproject/remapping/-/remapping-2.2.0.tgz#56c133824780de3174aed5ab6834f3026790154d" + integrity sha512-qRmjj8nj9qmLTQXXmaR1cck3UXSRMPrbsLJAasZpF+t3riI71BXed5ebIOYwQntykeZuhjsdweEc9BxH5Jc26w== dependencies: - "@jridgewell/trace-mapping" "^0.3.0" + "@jridgewell/gen-mapping" "^0.1.0" + "@jridgewell/trace-mapping" "^0.3.9" "@babel/cli@^7.12.10": - version "7.17.6" - resolved "https://registry.yarnpkg.com/@babel/cli/-/cli-7.17.6.tgz#169e5935f1795f0b62ded5a2accafeedfe5c5363" - integrity sha512-l4w608nsDNlxZhiJ5tE3DbNmr61fIKMZ6fTBo171VEFuFMIYuJ3mHRhTLEkKKyvx2Mizkkv/0a8OJOnZqkKYNA== + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/cli/-/cli-7.17.10.tgz#5ea0bf6298bb78f3b59c7c06954f9bd1c79d5943" + integrity sha512-OygVO1M2J4yPMNOW9pb+I6kFGpQK77HmG44Oz3hg8xQIl5L/2zq+ZohwAdSaqYgVwM0SfmPHZHphH4wR8qzVYw== dependencies: - "@jridgewell/trace-mapping" "^0.3.4" + "@jridgewell/trace-mapping" "^0.3.8" commander "^4.0.1" convert-source-map "^1.1.0" fs-readdir-recursive "^1.1.0" glob "^7.0.0" make-dir "^2.1.0" slash "^2.0.0" - source-map "^0.5.0" optionalDependencies: "@nicolo-ribaudo/chokidar-2" "2.1.8-no-fsevents.3" chokidar "^3.4.0" @@ -57,26 +57,26 @@ dependencies: "@babel/highlight" "^7.16.7" -"@babel/compat-data@^7.13.11", "@babel/compat-data@^7.16.8", "@babel/compat-data@^7.17.0", "@babel/compat-data@^7.17.7": - version "7.17.7" - resolved "https://registry.yarnpkg.com/@babel/compat-data/-/compat-data-7.17.7.tgz#078d8b833fbbcc95286613be8c716cef2b519fa2" - integrity sha512-p8pdE6j0a29TNGebNm7NzYZWB3xVZJBZ7XGs42uAKzQo8VQ3F0By/cQCtUEABwIqw5zo6WA4NbmxsfzADzMKnQ== +"@babel/compat-data@^7.13.11", "@babel/compat-data@^7.17.0", "@babel/compat-data@^7.17.10": + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/compat-data/-/compat-data-7.17.10.tgz#711dc726a492dfc8be8220028b1b92482362baab" + integrity sha512-GZt/TCsG70Ms19gfZO1tM4CVnXsPgEPBCpJu+Qz3L0LUDsY5nZqFZglIoPC1kIYOtNBZlrnFT+klg12vFGZXrw== "@babel/core@^7.1.0", "@babel/core@^7.12.10", "@babel/core@^7.12.3", "@babel/core@^7.7.5": - version "7.17.9" - resolved "https://registry.yarnpkg.com/@babel/core/-/core-7.17.9.tgz#6bae81a06d95f4d0dec5bb9d74bbc1f58babdcfe" - integrity sha512-5ug+SfZCpDAkVp9SFIZAzlW18rlzsOcJGaetCjkySnrXXDUw9AR8cDUm1iByTmdWM6yxX6/zycaV76w3YTF2gw== + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/core/-/core-7.17.10.tgz#74ef0fbf56b7dfc3f198fc2d927f4f03e12f4b05" + integrity sha512-liKoppandF3ZcBnIYFjfSDHZLKdLHGJRkoWtG8zQyGJBQfIYobpnVGI5+pLBNtS6psFLDzyq8+h5HiVljW9PNA== dependencies: "@ampproject/remapping" "^2.1.0" "@babel/code-frame" "^7.16.7" - "@babel/generator" "^7.17.9" - "@babel/helper-compilation-targets" "^7.17.7" + "@babel/generator" "^7.17.10" + "@babel/helper-compilation-targets" "^7.17.10" "@babel/helper-module-transforms" "^7.17.7" "@babel/helpers" "^7.17.9" - "@babel/parser" "^7.17.9" + "@babel/parser" "^7.17.10" "@babel/template" "^7.16.7" - "@babel/traverse" "^7.17.9" - "@babel/types" "^7.17.0" + "@babel/traverse" "^7.17.10" + "@babel/types" "^7.17.10" convert-source-map "^1.7.0" debug "^4.1.0" gensync "^1.0.0-beta.2" @@ -99,16 +99,7 @@ dependencies: eslint-rule-composer "^0.3.0" -"@babel/generator@^7.12.11", "@babel/generator@^7.17.9": - version "7.17.9" - resolved "https://registry.yarnpkg.com/@babel/generator/-/generator-7.17.9.tgz#f4af9fd38fa8de143c29fce3f71852406fc1e2fc" - integrity sha512-rAdDousTwxbIxbz5I7GEQ3lUip+xVCXooZNbsydCWs3xA7ZsYOv+CFRdzGxRX78BmQHu9B1Eso59AOZQOJDEdQ== - dependencies: - "@babel/types" "^7.17.0" - jsesc "^2.5.1" - source-map "^0.5.0" - -"@babel/generator@^7.17.10": +"@babel/generator@^7.12.11", "@babel/generator@^7.17.10": version "7.17.10" resolved "https://registry.yarnpkg.com/@babel/generator/-/generator-7.17.10.tgz#c281fa35b0c349bbe9d02916f4ae08fc85ed7189" integrity sha512-46MJZZo9y3o4kmhBVc7zW7i8dtR1oIK/sdO5NcfcZRhTGYi+KKJRtHNgsU6c4VUcJmUNV/LQdebD/9Dlv4K+Tg== @@ -132,14 +123,14 @@ "@babel/helper-explode-assignable-expression" "^7.16.7" "@babel/types" "^7.16.7" -"@babel/helper-compilation-targets@^7.13.0", "@babel/helper-compilation-targets@^7.16.7", "@babel/helper-compilation-targets@^7.17.7": - version "7.17.7" - resolved "https://registry.yarnpkg.com/@babel/helper-compilation-targets/-/helper-compilation-targets-7.17.7.tgz#a3c2924f5e5f0379b356d4cfb313d1414dc30e46" - integrity sha512-UFzlz2jjd8kroj0hmCFV5zr+tQPi1dpC2cRsDV/3IEW8bJfCPrPpmcSN6ZS8RqIq4LXcmpipCQFPddyFA5Yc7w== +"@babel/helper-compilation-targets@^7.13.0", "@babel/helper-compilation-targets@^7.16.7", "@babel/helper-compilation-targets@^7.17.10": + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/helper-compilation-targets/-/helper-compilation-targets-7.17.10.tgz#09c63106d47af93cf31803db6bc49fef354e2ebe" + integrity sha512-gh3RxjWbauw/dFiU/7whjd0qN9K6nPJMqe6+Er7rOavFh0CQUSwhAE3IcTho2rywPJFxej6TUUHDkWcYI6gGqQ== dependencies: - "@babel/compat-data" "^7.17.7" + "@babel/compat-data" "^7.17.10" "@babel/helper-validator-option" "^7.16.7" - browserslist "^4.17.5" + browserslist "^4.20.2" semver "^6.3.0" "@babel/helper-create-class-features-plugin@^7.16.10", "@babel/helper-create-class-features-plugin@^7.16.7", "@babel/helper-create-class-features-plugin@^7.17.6": @@ -155,7 +146,7 @@ "@babel/helper-replace-supers" "^7.16.7" "@babel/helper-split-export-declaration" "^7.16.7" -"@babel/helper-create-regexp-features-plugin@^7.16.7": +"@babel/helper-create-regexp-features-plugin@^7.16.7", "@babel/helper-create-regexp-features-plugin@^7.17.0": version "7.17.0" resolved "https://registry.yarnpkg.com/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.17.0.tgz#1dcc7d40ba0c6b6b25618997c5dbfd310f186fe1" integrity sha512-awO2So99wG6KnlE+TPs6rn83gCz5WlEePJDTnLEqbchMVrBeAujURVphRdigsk094VhvZehFoNOihSlcBjwsXA== @@ -325,12 +316,7 @@ chalk "^2.0.0" js-tokens "^4.0.0" -"@babel/parser@^7.1.0", "@babel/parser@^7.14.7", "@babel/parser@^7.16.7", "@babel/parser@^7.17.9", "@babel/parser@^7.2.3", "@babel/parser@^7.9.4": - version "7.17.9" - resolved "https://registry.yarnpkg.com/@babel/parser/-/parser-7.17.9.tgz#9c94189a6062f0291418ca021077983058e171ef" - integrity sha512-vqUSBLP8dQHFPdPi9bc5GK9vRkYHJ49fsZdtoJ8EQ8ibpwk5rPKfvNIwChB0KVXcIjcepEBBd2VHC5r9Gy8ueg== - -"@babel/parser@^7.17.10": +"@babel/parser@^7.1.0", "@babel/parser@^7.14.7", "@babel/parser@^7.16.7", "@babel/parser@^7.17.10", "@babel/parser@^7.2.3", "@babel/parser@^7.9.4": version "7.17.10" resolved "https://registry.yarnpkg.com/@babel/parser/-/parser-7.17.10.tgz#873b16db82a8909e0fbd7f115772f4b739f6ce78" integrity sha512-n2Q6i+fnJqzOaq2VkdXxy2TCPCWQZHiCo0XqmrCvDWcZQKRyZzYi4Z0yxlBuN0w+r2ZHmre+Q087DSrw3pbJDQ== @@ -368,7 +354,7 @@ "@babel/helper-create-class-features-plugin" "^7.16.7" "@babel/helper-plugin-utils" "^7.16.7" -"@babel/plugin-proposal-class-static-block@^7.16.7": +"@babel/plugin-proposal-class-static-block@^7.17.6": version "7.17.6" resolved "https://registry.yarnpkg.com/@babel/plugin-proposal-class-static-block/-/plugin-proposal-class-static-block-7.17.6.tgz#164e8fd25f0d80fa48c5a4d1438a6629325ad83c" integrity sha512-X/tididvL2zbs7jZCeeRJ8167U/+Ac135AM6jCAx6gYXDUviZV5Ku9UDvWS2NCuWlFjIRXklYhwo6HhAC7ETnA== @@ -425,7 +411,7 @@ "@babel/helper-plugin-utils" "^7.16.7" "@babel/plugin-syntax-numeric-separator" "^7.10.4" -"@babel/plugin-proposal-object-rest-spread@^7.12.1", "@babel/plugin-proposal-object-rest-spread@^7.16.7": +"@babel/plugin-proposal-object-rest-spread@^7.12.1", "@babel/plugin-proposal-object-rest-spread@^7.17.3": version "7.17.3" resolved "https://registry.yarnpkg.com/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.17.3.tgz#d9eb649a54628a51701aef7e0ea3d17e2b9dd390" integrity sha512-yuL5iQA/TbZn+RGAfxQXfi7CNLmKi1f8zInn4IgobuCWcAb7i+zj4TYzQ9l8cEzVyJ89PDGuqxK1xZpUDISesw== @@ -592,9 +578,9 @@ "@babel/helper-plugin-utils" "^7.14.5" "@babel/plugin-syntax-typescript@^7.16.7": - version "7.16.7" - resolved "https://registry.yarnpkg.com/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.16.7.tgz#39c9b55ee153151990fb038651d58d3fd03f98f8" - integrity sha512-YhUIJHHGkqPgEcMYkPCKTyGUdoGKWtopIycQyjJH8OjvRgOYsXsaKehLVPScKJWAULPxMa4N1vCe6szREFlZ7A== + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.17.10.tgz#80031e6042cad6a95ed753f672ebd23c30933195" + integrity sha512-xJefea1DWXW09pW4Tm9bjwVlPDyYA2it3fWlmEjpYz6alPvTUjL0EOzNzI/FEOyI3r4/J7uVH5UqKgl1TQ5hqQ== dependencies: "@babel/helper-plugin-utils" "^7.16.7" @@ -649,7 +635,7 @@ dependencies: "@babel/helper-plugin-utils" "^7.16.7" -"@babel/plugin-transform-destructuring@^7.16.7": +"@babel/plugin-transform-destructuring@^7.17.7": version "7.17.7" resolved "https://registry.yarnpkg.com/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.17.7.tgz#49dc2675a7afa9a5e4c6bdee636061136c3408d1" integrity sha512-XVh0r5yq9sLR4vZ6eVZe8FKfIcSgaTBxVBRSYokRj2qksf6QerYnTxz9/GTuKTH/n/HwLP7t6gtlybHetJ/6hQ== @@ -718,7 +704,7 @@ "@babel/helper-plugin-utils" "^7.16.7" babel-plugin-dynamic-import-node "^2.3.3" -"@babel/plugin-transform-modules-commonjs@^7.16.8": +"@babel/plugin-transform-modules-commonjs@^7.17.9": version "7.17.9" resolved "https://registry.yarnpkg.com/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.17.9.tgz#274be1a2087beec0254d4abd4d86e52442e1e5b6" integrity sha512-2TBFd/r2I6VlYn0YRTz2JdazS+FoUuQ2rIFHoAxtyP/0G3D82SBLaRq9rnUkpqlLg03Byfl/+M32mpxjO6KaPw== @@ -728,7 +714,7 @@ "@babel/helper-simple-access" "^7.17.7" babel-plugin-dynamic-import-node "^2.3.3" -"@babel/plugin-transform-modules-systemjs@^7.16.7": +"@babel/plugin-transform-modules-systemjs@^7.17.8": version "7.17.8" resolved "https://registry.yarnpkg.com/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.17.8.tgz#81fd834024fae14ea78fbe34168b042f38703859" integrity sha512-39reIkMTUVagzgA5x88zDYXPCMT6lcaRKs1+S9K6NKBPErbgO/w/kP8GlNQTC87b412ZTlmNgr3k2JrWgHH+Bw== @@ -747,12 +733,12 @@ "@babel/helper-module-transforms" "^7.16.7" "@babel/helper-plugin-utils" "^7.16.7" -"@babel/plugin-transform-named-capturing-groups-regex@^7.16.8": - version "7.16.8" - resolved "https://registry.yarnpkg.com/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.16.8.tgz#7f860e0e40d844a02c9dcf9d84965e7dfd666252" - integrity sha512-j3Jw+n5PvpmhRR+mrgIh04puSANCk/T/UA3m3P1MjJkhlK906+ApHhDIqBQDdOgL/r1UYpz4GNclTXxyZrYGSw== +"@babel/plugin-transform-named-capturing-groups-regex@^7.17.10": + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.17.10.tgz#715dbcfafdb54ce8bccd3d12e8917296a4ba66a4" + integrity sha512-v54O6yLaJySCs6mGzaVOUw9T967GnH38T6CQSAtnzdNPwu84l2qAjssKzo/WSO8Yi7NF+7ekm5cVbF/5qiIgNA== dependencies: - "@babel/helper-create-regexp-features-plugin" "^7.16.7" + "@babel/helper-create-regexp-features-plugin" "^7.17.0" "@babel/plugin-transform-new-target@^7.16.7": version "7.16.7" @@ -783,7 +769,7 @@ dependencies: "@babel/helper-plugin-utils" "^7.16.7" -"@babel/plugin-transform-regenerator@^7.16.7": +"@babel/plugin-transform-regenerator@^7.17.9": version "7.17.9" resolved "https://registry.yarnpkg.com/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.17.9.tgz#0a33c3a61cf47f45ed3232903683a0afd2d3460c" integrity sha512-Lc2TfbxR1HOyn/c6b4Y/b6NHoTb67n/IoWLxTu4kC7h4KQnWlhCq2S8Tx0t2SVvv5Uu87Hs+6JEJ5kt2tYGylQ== @@ -798,9 +784,9 @@ "@babel/helper-plugin-utils" "^7.16.7" "@babel/plugin-transform-runtime@^7.12.10": - version "7.17.0" - resolved "https://registry.yarnpkg.com/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.17.0.tgz#0a2e08b5e2b2d95c4b1d3b3371a2180617455b70" - integrity sha512-fr7zPWnKXNc1xoHfrIU9mN/4XKX4VLZ45Q+oMhfsYIaHvg7mHgmhfOy/ckRWqDK7XF3QDigRpkh5DKq6+clE8A== + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.17.10.tgz#b89d821c55d61b5e3d3c3d1d636d8d5a81040ae1" + integrity sha512-6jrMilUAJhktTr56kACL8LnWC5hx3Lf27BS0R0DSyW/OoJfb/iTHeE96V3b1dgKG3FSFdd/0culnYWMkjcKCig== dependencies: "@babel/helper-module-imports" "^7.16.7" "@babel/helper-plugin-utils" "^7.16.7" @@ -870,26 +856,26 @@ "@babel/helper-plugin-utils" "^7.16.7" "@babel/preset-env@^7.12.11": - version "7.16.11" - resolved "https://registry.yarnpkg.com/@babel/preset-env/-/preset-env-7.16.11.tgz#5dd88fd885fae36f88fd7c8342475c9f0abe2982" - integrity sha512-qcmWG8R7ZW6WBRPZK//y+E3Cli151B20W1Rv7ln27vuPaXU/8TKms6jFdiJtF7UDTxcrb7mZd88tAeK9LjdT8g== + version "7.17.10" + resolved "https://registry.yarnpkg.com/@babel/preset-env/-/preset-env-7.17.10.tgz#a81b093669e3eb6541bb81a23173c5963c5de69c" + integrity sha512-YNgyBHZQpeoBSRBg0xixsZzfT58Ze1iZrajvv0lJc70qDDGuGfonEnMGfWeSY0mQ3JTuCWFbMkzFRVafOyJx4g== dependencies: - "@babel/compat-data" "^7.16.8" - "@babel/helper-compilation-targets" "^7.16.7" + "@babel/compat-data" "^7.17.10" + "@babel/helper-compilation-targets" "^7.17.10" "@babel/helper-plugin-utils" "^7.16.7" "@babel/helper-validator-option" "^7.16.7" "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression" "^7.16.7" "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining" "^7.16.7" "@babel/plugin-proposal-async-generator-functions" "^7.16.8" "@babel/plugin-proposal-class-properties" "^7.16.7" - "@babel/plugin-proposal-class-static-block" "^7.16.7" + "@babel/plugin-proposal-class-static-block" "^7.17.6" "@babel/plugin-proposal-dynamic-import" "^7.16.7" "@babel/plugin-proposal-export-namespace-from" "^7.16.7" "@babel/plugin-proposal-json-strings" "^7.16.7" "@babel/plugin-proposal-logical-assignment-operators" "^7.16.7" "@babel/plugin-proposal-nullish-coalescing-operator" "^7.16.7" "@babel/plugin-proposal-numeric-separator" "^7.16.7" - "@babel/plugin-proposal-object-rest-spread" "^7.16.7" + "@babel/plugin-proposal-object-rest-spread" "^7.17.3" "@babel/plugin-proposal-optional-catch-binding" "^7.16.7" "@babel/plugin-proposal-optional-chaining" "^7.16.7" "@babel/plugin-proposal-private-methods" "^7.16.11" @@ -915,7 +901,7 @@ "@babel/plugin-transform-block-scoping" "^7.16.7" "@babel/plugin-transform-classes" "^7.16.7" "@babel/plugin-transform-computed-properties" "^7.16.7" - "@babel/plugin-transform-destructuring" "^7.16.7" + "@babel/plugin-transform-destructuring" "^7.17.7" "@babel/plugin-transform-dotall-regex" "^7.16.7" "@babel/plugin-transform-duplicate-keys" "^7.16.7" "@babel/plugin-transform-exponentiation-operator" "^7.16.7" @@ -924,15 +910,15 @@ "@babel/plugin-transform-literals" "^7.16.7" "@babel/plugin-transform-member-expression-literals" "^7.16.7" "@babel/plugin-transform-modules-amd" "^7.16.7" - "@babel/plugin-transform-modules-commonjs" "^7.16.8" - "@babel/plugin-transform-modules-systemjs" "^7.16.7" + "@babel/plugin-transform-modules-commonjs" "^7.17.9" + "@babel/plugin-transform-modules-systemjs" "^7.17.8" "@babel/plugin-transform-modules-umd" "^7.16.7" - "@babel/plugin-transform-named-capturing-groups-regex" "^7.16.8" + "@babel/plugin-transform-named-capturing-groups-regex" "^7.17.10" "@babel/plugin-transform-new-target" "^7.16.7" "@babel/plugin-transform-object-super" "^7.16.7" "@babel/plugin-transform-parameters" "^7.16.7" "@babel/plugin-transform-property-literals" "^7.16.7" - "@babel/plugin-transform-regenerator" "^7.16.7" + "@babel/plugin-transform-regenerator" "^7.17.9" "@babel/plugin-transform-reserved-words" "^7.16.7" "@babel/plugin-transform-shorthand-properties" "^7.16.7" "@babel/plugin-transform-spread" "^7.16.7" @@ -942,11 +928,11 @@ "@babel/plugin-transform-unicode-escapes" "^7.16.7" "@babel/plugin-transform-unicode-regex" "^7.16.7" "@babel/preset-modules" "^0.1.5" - "@babel/types" "^7.16.8" + "@babel/types" "^7.17.10" babel-plugin-polyfill-corejs2 "^0.3.0" babel-plugin-polyfill-corejs3 "^0.5.0" babel-plugin-polyfill-regenerator "^0.3.0" - core-js-compat "^3.20.2" + core-js-compat "^3.22.1" semver "^6.3.0" "@babel/preset-modules@^0.1.5": @@ -996,7 +982,7 @@ "@babel/parser" "^7.16.7" "@babel/types" "^7.16.7" -"@babel/traverse@^7.1.0": +"@babel/traverse@^7.1.0", "@babel/traverse@^7.1.6", "@babel/traverse@^7.13.0", "@babel/traverse@^7.16.7", "@babel/traverse@^7.16.8", "@babel/traverse@^7.17.10", "@babel/traverse@^7.17.3", "@babel/traverse@^7.17.9": version "7.17.10" resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.17.10.tgz#1ee1a5ac39f4eac844e6cf855b35520e5eb6f8b5" integrity sha512-VmbrTHQteIdUUQNTb+zE12SHS/xQVIShmBPhlNP12hD5poF2pbITW1Z4172d03HegaQWhLffdkRJYtAzp0AGcw== @@ -1012,31 +998,7 @@ debug "^4.1.0" globals "^11.1.0" -"@babel/traverse@^7.1.6", "@babel/traverse@^7.13.0", "@babel/traverse@^7.16.7", "@babel/traverse@^7.16.8", "@babel/traverse@^7.17.3", "@babel/traverse@^7.17.9": - version "7.17.9" - resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.17.9.tgz#1f9b207435d9ae4a8ed6998b2b82300d83c37a0d" - integrity sha512-PQO8sDIJ8SIwipTPiR71kJQCKQYB5NGImbOviK8K+kg5xkNSYXLBupuX9QhatFowrsvo9Hj8WgArg3W7ijNAQw== - dependencies: - "@babel/code-frame" "^7.16.7" - "@babel/generator" "^7.17.9" - "@babel/helper-environment-visitor" "^7.16.7" - "@babel/helper-function-name" "^7.17.9" - "@babel/helper-hoist-variables" "^7.16.7" - "@babel/helper-split-export-declaration" "^7.16.7" - "@babel/parser" "^7.17.9" - "@babel/types" "^7.17.0" - debug "^4.1.0" - globals "^11.1.0" - -"@babel/types@^7.0.0", "@babel/types@^7.16.0", "@babel/types@^7.16.7", "@babel/types@^7.16.8", "@babel/types@^7.17.0", "@babel/types@^7.2.0", "@babel/types@^7.3.0", "@babel/types@^7.3.3", "@babel/types@^7.4.4": - version "7.17.0" - resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.17.0.tgz#a826e368bccb6b3d84acd76acad5c0d87342390b" - integrity sha512-TmKSNO4D5rzhL5bjWFcVHHLETzfQ/AmbKpKPOSjlP0WoHZ6L911fgoOKY4Alp/emzG4cHJdyN49zpgkbXFEHHw== - dependencies: - "@babel/helper-validator-identifier" "^7.16.7" - to-fast-properties "^2.0.0" - -"@babel/types@^7.17.10": +"@babel/types@^7.0.0", "@babel/types@^7.16.0", "@babel/types@^7.16.7", "@babel/types@^7.16.8", "@babel/types@^7.17.0", "@babel/types@^7.17.10", "@babel/types@^7.2.0", "@babel/types@^7.3.0", "@babel/types@^7.3.3", "@babel/types@^7.4.4": version "7.17.10" resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.17.10.tgz#d35d7b4467e439fcf06d195f8100e0fea7fc82c4" integrity sha512-9O26jG0mBYfGkUYCYZRnBwbVLd1UZOICEr2Em6InB6jVfsAv1GKgwXHmrSg+WFWDmeKTA6vyTZiN8tCSM5Oo3A== @@ -1058,9 +1020,9 @@ minimist "^1.2.0" "@eslint/eslintrc@^1.1.0": - version "1.2.1" - resolved "https://registry.yarnpkg.com/@eslint/eslintrc/-/eslintrc-1.2.1.tgz#8b5e1c49f4077235516bc9ec7d41378c0f69b8c6" - integrity sha512-bxvbYnBPN1Gibwyp6NrpnFzA3YtRL3BBAyEAFVIpNTm2Rn4Vy87GA5M4aSn3InRrlsbX5N0GW7XIx+U4SAEKdQ== + version "1.2.2" + resolved "https://registry.yarnpkg.com/@eslint/eslintrc/-/eslintrc-1.2.2.tgz#4989b9e8c0216747ee7cca314ae73791bb281aae" + integrity sha512-lTVWHs7O2hjBFZunXTZYnYqtB9GakA1lnxIf+gKq2nY5gxkkNi/lQvveW6t8gFdOHTg6nG50Xs95PrLqVpcaLg== dependencies: ajv "^6.12.4" debug "^4.3.2" @@ -1097,7 +1059,7 @@ js-yaml "^3.13.1" resolve-from "^5.0.0" -"@istanbuljs/schema@^0.1.2": +"@istanbuljs/schema@^0.1.2", "@istanbuljs/schema@^0.1.3": version "0.1.3" resolved "https://registry.yarnpkg.com/@istanbuljs/schema/-/schema-0.1.3.tgz#e45e384e4b8ec16bce2fd903af78450f6bf7ec98" integrity sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA== @@ -1282,9 +1244,9 @@ "@jridgewell/sourcemap-codec" "^1.4.10" "@jridgewell/resolve-uri@^3.0.3": - version "3.0.5" - resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.0.5.tgz#68eb521368db76d040a6315cdb24bf2483037b9c" - integrity sha512-VPeQ7+wH0itvQxnG+lIzWgkysKIr3L9sslimFW55rHMdGu/qCQ5z5h9zq4gI8uBtqkpHhsF4Z/OwExufUCThew== + version "3.0.6" + resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.0.6.tgz#4ac237f4dabc8dd93330386907b97591801f7352" + integrity sha512-R7xHtBSNm+9SyvpJkdQl+qrM3Hm2fea3Ef197M3mUug+v+yR+Rhfbs7PBtcBUVnIWJ4JcAdjvij+c8hXS9p5aw== "@jridgewell/set-array@^1.0.0": version "1.1.0" @@ -1292,14 +1254,14 @@ integrity sha512-SfJxIxNVYLTsKwzB3MoOQ1yxf4w/E6MdkvTgrgAt1bfxjSrLUoHMKrDOykwN14q65waezZIdqDneUIPh4/sKxg== "@jridgewell/sourcemap-codec@^1.4.10": - version "1.4.11" - resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.11.tgz#771a1d8d744eeb71b6adb35808e1a6c7b9b8c8ec" - integrity sha512-Fg32GrJo61m+VqYSdRSjRXMjQ06j8YIYfcTqndLYVAaHmroZHLJZCydsWBOTDqXS2v+mjxohBWEMfg97GXmYQg== + version "1.4.12" + resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.12.tgz#7ed98f6fa525ffb7c56a2cbecb5f7bb91abd2baf" + integrity sha512-az/NhpIwP3K33ILr0T2bso+k2E/SLf8Yidd8mHl0n6sCQ4YdyC8qDhZA6kOPDNDBA56ZnIjngVl0U3jREA0BUA== -"@jridgewell/trace-mapping@^0.3.0", "@jridgewell/trace-mapping@^0.3.4": - version "0.3.4" - resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.4.tgz#f6a0832dffd5b8a6aaa633b7d9f8e8e94c83a0c3" - integrity sha512-vFv9ttIedivx0ux3QSjhgtCVjPZd5l46ZOMDSCwnH1yUO2e964gO8LZGyv2QkqcgR6TnBU1v+1IFqmeoG+0UJQ== +"@jridgewell/trace-mapping@^0.3.7", "@jridgewell/trace-mapping@^0.3.8", "@jridgewell/trace-mapping@^0.3.9": + version "0.3.9" + resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9" + integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ== dependencies: "@jridgewell/resolve-uri" "^3.0.3" "@jridgewell/sourcemap-codec" "^1.4.10" @@ -1485,14 +1447,7 @@ "@babel/parser" "^7.1.0" "@babel/types" "^7.0.0" -"@types/babel__traverse@*", "@types/babel__traverse@^7.0.6": - version "7.17.0" - resolved "https://registry.yarnpkg.com/@types/babel__traverse/-/babel__traverse-7.17.0.tgz#7a9b80f712fe2052bc20da153ff1e552404d8e4b" - integrity sha512-r8aveDbd+rzGP+ykSdF3oPuTVRWRfbBiHl0rVDM2yNEmSMXfkObQLV46b4RnCv3Lra51OlfnZhkkFaDl2MIRaA== - dependencies: - "@babel/types" "^7.3.0" - -"@types/babel__traverse@^7.0.4": +"@types/babel__traverse@*", "@types/babel__traverse@^7.0.4", "@types/babel__traverse@^7.0.6": version "7.17.1" resolved "https://registry.yarnpkg.com/@types/babel__traverse/-/babel__traverse-7.17.1.tgz#1a0e73e8c28c7e832656db372b779bfd2ef37314" integrity sha512-kVzjari1s2YVi77D3w1yuvohV2idweYXMCDzqBiVNN63TcDWrIlTVOYpqVrvbbyOE/IyzBoTKF0fdnLPEORFxA== @@ -1586,14 +1541,14 @@ integrity sha512-eC4U9MlIcu2q0KQmXszyn5Akca/0jrQmwDRgpAMJai7qBWq4amIQhZyNau4VYGtCeALvW1/NtjzJJ567aZxfKA== "@types/node@*": - version "17.0.25" - resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.25.tgz#527051f3c2f77aa52e5dc74e45a3da5fb2301448" - integrity sha512-wANk6fBrUwdpY4isjWrKTufkrXdu1D2YHCot2fD/DfWxF5sMrVSA+KN7ydckvaTCh0HiqX9IVl0L5/ZoXg5M7w== + version "17.0.31" + resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.31.tgz#a5bb84ecfa27eec5e1c802c6bbf8139bdb163a5d" + integrity sha512-AR0x5HbXGqkEx9CadRH3EBYx/VkiUgZIhP4wvPn/+5KIsgpNoyFaRlVe0Zlx9gRtg8fA06a9tskE2MSN7TcG4Q== "@types/node@12": - version "12.20.48" - resolved "https://registry.yarnpkg.com/@types/node/-/node-12.20.48.tgz#55f70bd432b6515828c0298689776861b90ca4fa" - integrity sha512-4kxzqkrpwYtn6okJUcb2lfUu9ilnb3yhUOH6qX3nug8D2DupZ2drIkff2yJzYcNJVl3begnlcaBJ7tqiTTzjnQ== + version "12.20.50" + resolved "https://registry.yarnpkg.com/@types/node/-/node-12.20.50.tgz#14ba5198f1754ffd0472a2f84ab433b45ee0b65e" + integrity sha512-+9axpWx2b2JCVovr7Ilgt96uc6C1zBKOQMpGtRbWT9IoR/8ue32GGMfGA4woP8QyP2gBs6GQWEVM3tCybGCxDA== "@types/normalize-package-data@^2.4.0": version "2.4.1" @@ -1615,10 +1570,10 @@ "@types/tough-cookie" "*" form-data "^2.5.0" -"@types/retry@^0.12.0": - version "0.12.1" - resolved "https://registry.yarnpkg.com/@types/retry/-/retry-0.12.1.tgz#d8f1c0d0dc23afad6dc16a9e993a0865774b4065" - integrity sha512-xoDlM2S4ortawSWORYqsdU+2rxdh4LRW9ytc3zmT37RIKQh6IHyKwwtKhKis9ah8ol07DCkZxPt8BBvPjC6v4g== +"@types/retry@0.12.0": + version "0.12.0" + resolved "https://registry.yarnpkg.com/@types/retry/-/retry-0.12.0.tgz#2b35eccfcee7d38cd72ad99232fbd58bffb3c84d" + integrity sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA== "@types/stack-utils@^2.0.0": version "2.0.1" @@ -1643,13 +1598,13 @@ "@types/yargs-parser" "*" "@typescript-eslint/eslint-plugin@^5.6.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.20.0.tgz#022531a639640ff3faafaf251d1ce00a2ef000a1" - integrity sha512-fapGzoxilCn3sBtC6NtXZX6+P/Hef7VDbyfGqTTpzYydwhlkevB+0vE0EnmHPVTVSy68GUncyJ/2PcrFBeCo5Q== + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.22.0.tgz#7b52a0de2e664044f28b36419210aea4ab619e2a" + integrity sha512-YCiy5PUzpAeOPGQ7VSGDEY2NeYUV1B0swde2e0HzokRsHBYjSdF6DZ51OuRZxVPHx0032lXGLvOMls91D8FXlg== dependencies: - "@typescript-eslint/scope-manager" "5.20.0" - "@typescript-eslint/type-utils" "5.20.0" - "@typescript-eslint/utils" "5.20.0" + "@typescript-eslint/scope-manager" "5.22.0" + "@typescript-eslint/type-utils" "5.22.0" + "@typescript-eslint/utils" "5.22.0" debug "^4.3.2" functional-red-black-tree "^1.0.1" ignore "^5.1.8" @@ -1658,68 +1613,68 @@ tsutils "^3.21.0" "@typescript-eslint/parser@^5.6.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-5.20.0.tgz#4991c4ee0344315c2afc2a62f156565f689c8d0b" - integrity sha512-UWKibrCZQCYvobmu3/N8TWbEeo/EPQbS41Ux1F9XqPzGuV7pfg6n50ZrFo6hryynD8qOTTfLHtHjjdQtxJ0h/w== + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-5.22.0.tgz#7bedf8784ef0d5d60567c5ba4ce162460e70c178" + integrity sha512-piwC4krUpRDqPaPbFaycN70KCP87+PC5WZmrWs+DlVOxxmF+zI6b6hETv7Quy4s9wbkV16ikMeZgXsvzwI3icQ== dependencies: - "@typescript-eslint/scope-manager" "5.20.0" - "@typescript-eslint/types" "5.20.0" - "@typescript-eslint/typescript-estree" "5.20.0" + "@typescript-eslint/scope-manager" "5.22.0" + "@typescript-eslint/types" "5.22.0" + "@typescript-eslint/typescript-estree" "5.22.0" debug "^4.3.2" -"@typescript-eslint/scope-manager@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-5.20.0.tgz#79c7fb8598d2942e45b3c881ced95319818c7980" - integrity sha512-h9KtuPZ4D/JuX7rpp1iKg3zOH0WNEa+ZIXwpW/KWmEFDxlA/HSfCMhiyF1HS/drTICjIbpA6OqkAhrP/zkCStg== +"@typescript-eslint/scope-manager@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-5.22.0.tgz#590865f244ebe6e46dc3e9cab7976fc2afa8af24" + integrity sha512-yA9G5NJgV5esANJCO0oF15MkBO20mIskbZ8ijfmlKIvQKg0ynVKfHZ15/nhAJN5m8Jn3X5qkwriQCiUntC9AbA== dependencies: - "@typescript-eslint/types" "5.20.0" - "@typescript-eslint/visitor-keys" "5.20.0" + "@typescript-eslint/types" "5.22.0" + "@typescript-eslint/visitor-keys" "5.22.0" -"@typescript-eslint/type-utils@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-5.20.0.tgz#151c21cbe9a378a34685735036e5ddfc00223be3" - integrity sha512-WxNrCwYB3N/m8ceyoGCgbLmuZwupvzN0rE8NBuwnl7APgjv24ZJIjkNzoFBXPRCGzLNkoU/WfanW0exvp/+3Iw== +"@typescript-eslint/type-utils@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-5.22.0.tgz#0c0e93b34210e334fbe1bcb7250c470f4a537c19" + integrity sha512-iqfLZIsZhK2OEJ4cQ01xOq3NaCuG5FQRKyHicA3xhZxMgaxQazLUHbH/B2k9y5i7l3+o+B5ND9Mf1AWETeMISA== dependencies: - "@typescript-eslint/utils" "5.20.0" + "@typescript-eslint/utils" "5.22.0" debug "^4.3.2" tsutils "^3.21.0" -"@typescript-eslint/types@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-5.20.0.tgz#fa39c3c2aa786568302318f1cb51fcf64258c20c" - integrity sha512-+d8wprF9GyvPwtoB4CxBAR/s0rpP25XKgnOvMf/gMXYDvlUC3rPFHupdTQ/ow9vn7UDe5rX02ovGYQbv/IUCbg== +"@typescript-eslint/types@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-5.22.0.tgz#50a4266e457a5d4c4b87ac31903b28b06b2c3ed0" + integrity sha512-T7owcXW4l0v7NTijmjGWwWf/1JqdlWiBzPqzAWhobxft0SiEvMJB56QXmeCQjrPuM8zEfGUKyPQr/L8+cFUBLw== -"@typescript-eslint/typescript-estree@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-5.20.0.tgz#ab73686ab18c8781bbf249c9459a55dc9417d6b0" - integrity sha512-36xLjP/+bXusLMrT9fMMYy1KJAGgHhlER2TqpUVDYUQg4w0q/NW/sg4UGAgVwAqb8V4zYg43KMUpM8vV2lve6w== +"@typescript-eslint/typescript-estree@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-5.22.0.tgz#e2116fd644c3e2fda7f4395158cddd38c0c6df97" + integrity sha512-EyBEQxvNjg80yinGE2xdhpDYm41so/1kOItl0qrjIiJ1kX/L/L8WWGmJg8ni6eG3DwqmOzDqOhe6763bF92nOw== dependencies: - "@typescript-eslint/types" "5.20.0" - "@typescript-eslint/visitor-keys" "5.20.0" + "@typescript-eslint/types" "5.22.0" + "@typescript-eslint/visitor-keys" "5.22.0" debug "^4.3.2" globby "^11.0.4" is-glob "^4.0.3" semver "^7.3.5" tsutils "^3.21.0" -"@typescript-eslint/utils@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-5.20.0.tgz#b8e959ed11eca1b2d5414e12417fd94cae3517a5" - integrity sha512-lHONGJL1LIO12Ujyx8L8xKbwWSkoUKFSO+0wDAqGXiudWB2EO7WEUT+YZLtVbmOmSllAjLb9tpoIPwpRe5Tn6w== +"@typescript-eslint/utils@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-5.22.0.tgz#1f2c4897e2cf7e44443c848a13c60407861babd8" + integrity sha512-HodsGb037iobrWSUMS7QH6Hl1kppikjA1ELiJlNSTYf/UdMEwzgj0WIp+lBNb6WZ3zTwb0tEz51j0Wee3iJ3wQ== dependencies: "@types/json-schema" "^7.0.9" - "@typescript-eslint/scope-manager" "5.20.0" - "@typescript-eslint/types" "5.20.0" - "@typescript-eslint/typescript-estree" "5.20.0" + "@typescript-eslint/scope-manager" "5.22.0" + "@typescript-eslint/types" "5.22.0" + "@typescript-eslint/typescript-estree" "5.22.0" eslint-scope "^5.1.1" eslint-utils "^3.0.0" -"@typescript-eslint/visitor-keys@5.20.0": - version "5.20.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-5.20.0.tgz#70236b5c6b67fbaf8b2f58bf3414b76c1e826c2a" - integrity sha512-1flRpNF+0CAQkMNlTJ6L/Z5jiODG/e5+7mk6XwtPOUS3UrTz3UOiAg9jG2VtKsWI6rZQfy4C6a232QNRZTRGlg== +"@typescript-eslint/visitor-keys@5.22.0": + version "5.22.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-5.22.0.tgz#f49c0ce406944ffa331a1cfabeed451ea4d0909c" + integrity sha512-DbgTqn2Dv5RFWluG88tn0pP6Ex0ROF+dpDO1TNNZdRtLjUr6bdznjA6f/qNqJLjd2PgguAES2Zgxh/JzwzETDg== dependencies: - "@typescript-eslint/types" "5.20.0" + "@typescript-eslint/types" "5.22.0" eslint-visitor-keys "^3.0.0" JSONStream@^1.0.3: @@ -1789,16 +1744,11 @@ acorn@^7.0.0, acorn@^7.1.1: resolved "https://registry.yarnpkg.com/acorn/-/acorn-7.4.1.tgz#feaed255973d2e77555b83dbc08851a6c63520fa" integrity sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A== -acorn@^8.2.4: +acorn@^8.2.4, acorn@^8.5.0, acorn@^8.7.0: version "8.7.1" resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.7.1.tgz#0197122c843d1bf6d0a5e83220a788f278f63c30" integrity sha512-Xx54uLJQZ19lKygFXOWsscKUbsBZW0CPykPhVQdhIeIwrbPmJzqeASDInc8nKBnp/JT6igTs82qPXz069H8I/A== -acorn@^8.5.0, acorn@^8.7.0: - version "8.7.0" - resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.7.0.tgz#90951fde0f8f09df93549481e5fc141445b791cf" - integrity sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ== - agent-base@6: version "6.0.2" resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" @@ -2412,15 +2362,15 @@ browserify@^17.0.0: vm-browserify "^1.0.0" xtend "^4.0.0" -browserslist@^4.17.5, browserslist@^4.20.2: - version "4.20.2" - resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.20.2.tgz#567b41508757ecd904dab4d1c646c612cd3d4f88" - integrity sha512-CQOBCqp/9pDvDbx3xfMi+86pr4KXIf2FDkTTdeuYw8OxS9t898LA1Khq57gtufFILXpfgsSx5woNgsBgvGjpsA== +browserslist@^4.20.2, browserslist@^4.20.3: + version "4.20.3" + resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.20.3.tgz#eb7572f49ec430e054f56d52ff0ebe9be915f8bf" + integrity sha512-NBhymBQl1zM0Y5dQT/O+xiLP9/rzOIQdKM/eMJBAq7yBgaB6krIYLGejrwVYnSHZdqjscB1SPuAjHwxjvN6Wdg== dependencies: - caniuse-lite "^1.0.30001317" - electron-to-chromium "^1.4.84" + caniuse-lite "^1.0.30001332" + electron-to-chromium "^1.4.118" escalade "^3.1.1" - node-releases "^2.0.2" + node-releases "^2.0.3" picocolors "^1.0.0" bs58@^4.0.1: @@ -2461,22 +2411,22 @@ builtin-status-codes@^3.0.0: integrity sha1-hZgoeOIbmOHGZCXgPQF0eI9Wnug= c8@^7.6.0: - version "7.11.0" - resolved "https://registry.yarnpkg.com/c8/-/c8-7.11.0.tgz#b3ab4e9e03295a102c47ce11d4ef6d735d9a9ac9" - integrity sha512-XqPyj1uvlHMr+Y1IeRndC2X5P7iJzJlEJwBpCdBbq2JocXOgJfr+JVfJkyNMGROke5LfKrhSFXGFXnwnRJAUJw== + version "7.11.2" + resolved "https://registry.yarnpkg.com/c8/-/c8-7.11.2.tgz#2f2103e39079899041e612999a16b31d7ea6d463" + integrity sha512-6ahJSrhS6TqSghHm+HnWt/8Y2+z0hM/FQyB1ybKhAR30+NYL9CTQ1uwHxuWw6U7BHlHv6wvhgOrH81I+lfCkxg== dependencies: "@bcoe/v8-coverage" "^0.2.3" - "@istanbuljs/schema" "^0.1.2" + "@istanbuljs/schema" "^0.1.3" find-up "^5.0.0" foreground-child "^2.0.0" - istanbul-lib-coverage "^3.0.1" + istanbul-lib-coverage "^3.2.0" istanbul-lib-report "^3.0.0" - istanbul-reports "^3.0.2" - rimraf "^3.0.0" + istanbul-reports "^3.1.4" + rimraf "^3.0.2" test-exclude "^6.0.0" - v8-to-istanbul "^8.0.0" + v8-to-istanbul "^9.0.0" yargs "^16.2.0" - yargs-parser "^20.2.7" + yargs-parser "^20.2.9" cache-base@^1.0.1: version "1.0.1" @@ -2526,10 +2476,10 @@ camelcase@^6.0.0: resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== -caniuse-lite@^1.0.30001317: - version "1.0.30001332" - resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001332.tgz#39476d3aa8d83ea76359c70302eafdd4a1d727dd" - integrity sha512-10T30NYOEQtN6C11YGg411yebhvpnC6Z102+B95eAsN0oB6KUs01ivE8u+G6FMIRtIrVlYXhL+LUwQ3/hXwDWw== +caniuse-lite@^1.0.30001332: + version "1.0.30001335" + resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001335.tgz#899254a0b70579e5a957c32dced79f0727c61f2a" + integrity sha512-ddP1Tgm7z2iIxu6QTtbZUv6HJxSaV/PZeSrWFZtbY4JZ69tOeNhBCl3HyRQgeNZKE5AOn1kpV7fhljigy0Ty3w== capture-exit@^2.0.0: version "2.0.0" @@ -2820,12 +2770,12 @@ copy-descriptor@^0.1.0: resolved "https://registry.yarnpkg.com/copy-descriptor/-/copy-descriptor-0.1.1.tgz#676f6eb3c39997c2ee1ac3a924fd6124748f578d" integrity sha1-Z29us8OZl8LuGsOpJP1hJHSPV40= -core-js-compat@^3.20.2, core-js-compat@^3.21.0: - version "3.22.0" - resolved "https://registry.yarnpkg.com/core-js-compat/-/core-js-compat-3.22.0.tgz#7ce17ab57c378be2c717c7c8ed8f82a50a25b3e4" - integrity sha512-WwA7xbfRGrk8BGaaHlakauVXrlYmAIkk8PNGb1FDQS+Rbrewc3pgFfwJFRw6psmJVAll7Px9UHRYE16oRQnwAQ== +core-js-compat@^3.21.0, core-js-compat@^3.22.1: + version "3.22.4" + resolved "https://registry.yarnpkg.com/core-js-compat/-/core-js-compat-3.22.4.tgz#d700f451e50f1d7672dcad0ac85d910e6691e579" + integrity sha512-dIWcsszDezkFZrfm1cnB4f/J85gyhiCpxbgBdohWCDtSVuAaChTSpPV7ldOQf/Xds2U5xCIJZOK82G4ZPAIswA== dependencies: - browserslist "^4.20.2" + browserslist "^4.20.3" semver "7.0.0" core-js@^2.4.0: @@ -2834,9 +2784,9 @@ core-js@^2.4.0: integrity sha512-Kb2wC0fvsWfQrgk8HU5lW6U/Lcs8+9aaYcy4ZFc6DDlo4nZ7n70dEgE5rtR0oG6ufKDUnrwfWL1mXR5ljDatrQ== core-js@^3.4: - version "3.22.0" - resolved "https://registry.yarnpkg.com/core-js/-/core-js-3.22.0.tgz#b52007870c5e091517352e833b77f0b2d2b259f3" - integrity sha512-8h9jBweRjMiY+ORO7bdWSeWfHhLPO7whobj7Z2Bl0IDo00C228EdGgH7FE4jGumbEjzcFfkfW8bXgdkEDhnwHQ== + version "3.22.4" + resolved "https://registry.yarnpkg.com/core-js/-/core-js-3.22.4.tgz#f4b3f108d45736935aa028444a69397e40d8c531" + integrity sha512-1uLykR+iOfYja+6Jn/57743gc9n73EWiOnSJJ4ba3B4fOEYDBv25MagmEZBxTp5cWq4b/KPx/l77zgsp28ju4w== core-util-is@1.0.2: version "1.0.2" @@ -3013,7 +2963,7 @@ deepmerge@^4.2.2: resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955" integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg== -define-properties@^1.1.3, define-properties@~1.1.2: +define-properties@^1.1.3, define-properties@^1.1.4, define-properties@~1.1.2: version "1.1.4" resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.1.4.tgz#0b14d7bd7fbeb2f3572c3a7eda80ea5d57fb05b1" integrity sha512-uckOqKcfaVvtBdsVkdPv3XjveQJsNQqmhXgRi8uhvWWuPYZCNlzT8qAyblUgNoXdHdjMTzAqeGjAoli8f+bzPA== @@ -3174,10 +3124,10 @@ ecc-jsbn@~0.1.1: jsbn "~0.1.0" safer-buffer "^2.1.0" -electron-to-chromium@^1.4.84: - version "1.4.113" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.113.tgz#b3425c086e2f4fc31e9e53a724c6f239e3adb8b9" - integrity sha512-s30WKxp27F3bBH6fA07FYL2Xm/FYnYrKpMjHr3XVCTUb9anAyZn/BeZfPWgTZGAbJeT4NxNwISSbLcYZvggPMA== +electron-to-chromium@^1.4.118: + version "1.4.131" + resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.131.tgz#ca42d22eac0fe545860fbc636a6f4a7190ba70a9" + integrity sha512-oi3YPmaP87hiHn0c4ePB67tXaF+ldGhxvZnT19tW9zX6/Ej+pLN0Afja5rQ6S+TND7I9EuwQTT8JYn1k7R7rrw== elliptic@^6.5.3: version "6.5.4" @@ -3221,7 +3171,7 @@ error-ex@^1.2.0, error-ex@^1.3.1: dependencies: is-arrayish "^0.2.1" -es-abstract@^1.18.5, es-abstract@^1.19.0, es-abstract@^1.19.1, es-abstract@^1.19.2: +es-abstract@^1.18.5, es-abstract@^1.19.0, es-abstract@^1.19.1, es-abstract@^1.19.2, es-abstract@^1.19.5: version "1.19.5" resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.19.5.tgz#a2cb01eb87f724e815b278b0dd0d00f36ca9a7f1" integrity sha512-Aa2G2+Rd3b6kxEUKTF4TaW67czBLyAv3z7VOhYRU50YBx+bbsYZ9xQP4lMNazePuFlybXI0V4MruPos7qUo5fA== @@ -3278,9 +3228,9 @@ es-to-primitive@^1.2.1: is-symbol "^1.0.2" es5-ext@^0.10.35, es5-ext@^0.10.46, es5-ext@^0.10.50, es5-ext@^0.10.53, es5-ext@^0.10.59, es5-ext@~0.10.14, es5-ext@~0.10.2, es5-ext@~0.10.46: - version "0.10.60" - resolved "https://registry.yarnpkg.com/es5-ext/-/es5-ext-0.10.60.tgz#e8060a86472842b93019c31c34865012449883f4" - integrity sha512-jpKNXIt60htYG59/9FGf2PYT3pwMpnEbNKysU+k/4FGwyGtMotOvcZOuW+EmXXYASRqYSXQfGL5cVIthOTgbkg== + version "0.10.61" + resolved "https://registry.yarnpkg.com/es5-ext/-/es5-ext-0.10.61.tgz#311de37949ef86b6b0dcea894d1ffedb909d3269" + integrity sha512-yFhIqQAzu2Ca2I4SE2Au3rxVfmohU9Y7wqGR+s7+H7krk26NXhIRAZDgqd6xqjCEFUomDEA3/Bo/7fKmIkW1kA== dependencies: es6-iterator "^2.0.3" es6-symbol "^3.1.3" @@ -3900,9 +3850,9 @@ functional-red-black-tree@^1.0.1: integrity sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc= functions-have-names@^1.2.2: - version "1.2.2" - resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.2.tgz#98d93991c39da9361f8e50b337c4f6e41f120e21" - integrity sha512-bLgc3asbWdwPbx2mNk2S49kmJCuQeu0nfmaOgbs8WIyzzkw3r4htszdIi9Q9EMezDPTYuJx2wvjZ/EwgAthpnA== + version "1.2.3" + resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834" + integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ== gensync@^1.0.0-beta.2: version "1.0.0-beta.2" @@ -4040,10 +3990,10 @@ har-validator@~5.1.3: ajv "^6.12.3" har-schema "^2.0.0" -has-bigints@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.1.tgz#64fe6acb020673e3b78db035a5af69aa9d07b113" - integrity sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA== +has-bigints@^1.0.1, has-bigints@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.2.tgz#0871bd3e3d51626f6ca0966668ba35d5602d6eaa" + integrity sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ== has-flag@^3.0.0: version "3.0.0" @@ -4375,9 +4325,9 @@ is-ci@^2.0.0: ci-info "^2.0.0" is-core-module@^2.8.1: - version "2.8.1" - resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.8.1.tgz#f59fdfca701d5879d0a6b100a40aa1560ce27211" - integrity sha512-SdNCUs284hr40hFTFP6l0IfZ/RSrMXF3qgoRHd3/79unUTvrFO/JoXwkGm+5J/Oe3E/b5GsnG330uUNgRpu1PA== + version "2.9.0" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.9.0.tgz#e1c34429cd51c6dd9e09e0799e396e27b19a9c69" + integrity sha512-+5FPy5PnwmO3lvfMb0AsoPaBG+5KHUI0wYFXOtYPnVVVspTFUuMZNfNaNVRt3FZadstu2c8x23vykRW/NBoU6A== dependencies: has "^1.0.3" @@ -4688,7 +4638,7 @@ isstream@~0.1.2: resolved "https://registry.yarnpkg.com/isstream/-/isstream-0.1.2.tgz#47e63f7af55afa6f92e1500e690eb8b8529c099a" integrity sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo= -istanbul-lib-coverage@^3.0.0, istanbul-lib-coverage@^3.0.1, istanbul-lib-coverage@^3.2.0: +istanbul-lib-coverage@^3.0.0, istanbul-lib-coverage@^3.2.0: version "3.2.0" resolved "https://registry.yarnpkg.com/istanbul-lib-coverage/-/istanbul-lib-coverage-3.2.0.tgz#189e7909d0a39fa5a3dfad5b03f71947770191d3" integrity sha512-eOeJ5BHCmHYvQK7xt9GkdHuzuCGS1Y6g9Gvnx3Ym33fz/HpLRYxiS0wHNr+m/MBC8B647Xt608vCDEvhl9c6Mw== @@ -4704,9 +4654,9 @@ istanbul-lib-instrument@^4.0.3: semver "^6.3.0" istanbul-lib-instrument@^5.0.4: - version "5.1.0" - resolved "https://registry.yarnpkg.com/istanbul-lib-instrument/-/istanbul-lib-instrument-5.1.0.tgz#7b49198b657b27a730b8e9cb601f1e1bff24c59a" - integrity sha512-czwUz525rkOFDJxfKK6mYfIs9zBKILyrZQxjz3ABhjQXhbhFsSbo1HW/BFcsDnfJYJWA6thRR5/TUY2qs5W99Q== + version "5.2.0" + resolved "https://registry.yarnpkg.com/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.0.tgz#31d18bdd127f825dd02ea7bfdfd906f8ab840e9f" + integrity sha512-6Lthe1hqXHBNsqvgDzGO6l03XNeu3CrG4RqQ1KM9+l5+jNGpEJfIELx1NS3SEHmJQA8np/u+E4EPRKRiu6m19A== dependencies: "@babel/core" "^7.12.3" "@babel/parser" "^7.14.7" @@ -4732,7 +4682,7 @@ istanbul-lib-source-maps@^4.0.0: istanbul-lib-coverage "^3.0.0" source-map "^0.6.1" -istanbul-reports@^3.0.2: +istanbul-reports@^3.0.2, istanbul-reports@^3.1.4: version "3.1.4" resolved "https://registry.yarnpkg.com/istanbul-reports/-/istanbul-reports-3.1.4.tgz#1b6f068ecbc6c331040aab5741991273e609e40c" integrity sha512-r1/DshN4KSE7xWEknZLLLLDn5CJybV3nw01VTkp6D5jzLuELlcbudfj/eSQFvrKsJuTVCGnePO7ho82Nw9zzfw== @@ -5421,6 +5371,11 @@ lodash.merge@^4.6.2: resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== +lodash.sortby@^4.7.0: + version "4.7.0" + resolved "https://registry.yarnpkg.com/lodash.sortby/-/lodash.sortby-4.7.0.tgz#edd14c824e2cc9c1e0b0a1b42bb5210516a42438" + integrity sha1-7dFMgk4sycHgsKG0K7UhBRakJDg= + lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.4, lodash@^4.7.0: version "4.17.21" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" @@ -5516,9 +5471,9 @@ markdown-it@^12.3.2: uc.micro "^1.0.5" marked@^4.0.10: - version "4.0.14" - resolved "https://registry.yarnpkg.com/marked/-/marked-4.0.14.tgz#7a3a5fa5c80580bac78c1ed2e3b84d7bd6fc3870" - integrity sha512-HL5sSPE/LP6U9qKgngIIPTthuxC0jrfxpYMZ3LdGDD3vTnLs59m2Z7r6+LNDR3ToqEQdkKd6YaaEfJhodJmijQ== + version "4.0.15" + resolved "https://registry.yarnpkg.com/marked/-/marked-4.0.15.tgz#0216b7c9d5fcf6ac5042343c41d81a8b1b5e1b4a" + integrity sha512-esX5lPdTfG4p8LDkv+obbRCyOKzB+820ZZyMOXJZygZBHrH9b3xXR64X4kT3sPe9Nx8qQXbmcz6kFSMt4Nfk6Q== matrix-events-sdk@^0.0.1-beta.7: version "0.0.1-beta.7" @@ -5792,10 +5747,10 @@ node-notifier@^8.0.0: uuid "^8.3.0" which "^2.0.2" -node-releases@^2.0.2: - version "2.0.3" - resolved "https://registry.yarnpkg.com/node-releases/-/node-releases-2.0.3.tgz#225ee7488e4a5e636da8da52854844f9d716ca96" - integrity sha512-maHFz6OLqYxz+VQyCAtA3PTX4UP/53pa05fyDNc9CwjvJ0yEh6+xBwKsgCxMNhS8taUKBFYxfuiaD9U/55iFaw== +node-releases@^2.0.3: + version "2.0.4" + resolved "https://registry.yarnpkg.com/node-releases/-/node-releases-2.0.4.tgz#f38252370c43854dc48aa431c766c6c398f40476" + integrity sha512-gbMzqQtTtDz/00jQzZ21PQzdI9PyLYqUSvD0p3naOhX4odFji0ZxYdnVwPTxmSwkmxhcFImpozceidSG+AgoPQ== normalize-package-data@^2.5.0: version "2.5.0" @@ -6022,11 +5977,11 @@ p-locate@^5.0.0: p-limit "^3.0.2" p-retry@^4.5.0: - version "4.6.1" - resolved "https://registry.yarnpkg.com/p-retry/-/p-retry-4.6.1.tgz#8fcddd5cdf7a67a0911a9cf2ef0e5df7f602316c" - integrity sha512-e2xXGNhZOZ0lfgR9kL34iGlU8N/KO0xZnQxVEwdeOvpqNDQfdnxIYizvWtK8RglUa3bGqI8g0R/BdfzLMxRkiA== + version "4.6.2" + resolved "https://registry.yarnpkg.com/p-retry/-/p-retry-4.6.2.tgz#9baae7184057edd4e17231cee04264106e092a16" + integrity sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ== dependencies: - "@types/retry" "^0.12.0" + "@types/retry" "0.12.0" retry "^0.13.1" p-try@^1.0.0: @@ -7004,7 +6959,7 @@ source-map-url@^0.4.0: resolved "https://registry.yarnpkg.com/source-map-url/-/source-map-url-0.4.1.tgz#0af66605a745a5a2f91cf1bbf8a7afbc283dec56" integrity sha512-cPiFOTLUKvJFIg4SKVScy4ilPPW6rFgMgfuZJPNoDuMs3nC1HbMUycBoJw77xFIp6z1UJQJOfx6C9GMH80DiTw== -source-map@^0.5.0, source-map@^0.5.6, source-map@~0.5.1, source-map@~0.5.3: +source-map@^0.5.6, source-map@~0.5.1, source-map@~0.5.3: version "0.5.7" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.7.tgz#8a039d2d1021d22d1ea14c80d8ea468ba2ef3fcc" integrity sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w= @@ -7014,11 +6969,18 @@ source-map@^0.6.0, source-map@^0.6.1, source-map@~0.6.0, source-map@~0.6.1: resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== -source-map@^0.7.3, source-map@~0.7.2: +source-map@^0.7.3: version "0.7.3" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.7.3.tgz#5302f8169031735226544092e64981f751750383" integrity sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ== +source-map@~0.8.0-beta.0: + version "0.8.0-beta.0" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.8.0-beta.0.tgz#d4c1bb42c3f7ee925f005927ba10709e0d1d1f11" + integrity sha512-2ymg6oRBpebeZi9UUNsgQ89bhx01TcTkmNTGnNO88imTmbSgy4nfujrgVEFKWpMTEGA11EDkTt7mqObTPdigIA== + dependencies: + whatwg-url "^7.0.0" + spdx-correct@^3.0.0: version "3.1.1" resolved "https://registry.yarnpkg.com/spdx-correct/-/spdx-correct-3.1.1.tgz#dece81ac9c1e6713e5f7d1b6f17d468fa53d89a9" @@ -7139,20 +7101,22 @@ string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3: strip-ansi "^6.0.1" string.prototype.trimend@^1.0.4: - version "1.0.4" - resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.4.tgz#e75ae90c2942c63504686c18b287b4a0b1a45f80" - integrity sha512-y9xCjw1P23Awk8EvTpcyL2NIr1j7wJ39f+k6lvRnSMz+mz9CGz9NYPelDk42kOz6+ql8xjfK8oYzy3jAP5QU5A== + version "1.0.5" + resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.5.tgz#914a65baaab25fbdd4ee291ca7dde57e869cb8d0" + integrity sha512-I7RGvmjV4pJ7O3kdf+LXFpVfdNOxtCW/2C8f6jNiW4+PQchwxkCDzlk1/7p+Wl4bqFIZeF47qAHXLuHHWKAxog== dependencies: call-bind "^1.0.2" - define-properties "^1.1.3" + define-properties "^1.1.4" + es-abstract "^1.19.5" string.prototype.trimstart@^1.0.4: - version "1.0.4" - resolved "https://registry.yarnpkg.com/string.prototype.trimstart/-/string.prototype.trimstart-1.0.4.tgz#b36399af4ab2999b4c9c648bd7a3fb2bb26feeed" - integrity sha512-jh6e984OBfvxS50tdY2nRZnoC5/mLFKOREQfw8t5yytkoUsJRNxvI/E39qu1sD0OtWI3OC0XgKSmcWwziwYuZw== + version "1.0.5" + resolved "https://registry.yarnpkg.com/string.prototype.trimstart/-/string.prototype.trimstart-1.0.5.tgz#5466d93ba58cfa2134839f81d7f42437e8c01fef" + integrity sha512-THx16TJCGlsN0o6dl2o6ncWUsdgnLRSA23rRE5pyGBw/mLr3Ej/R2LaqCtgP8VNMGZsvMWnf9ooZPyY2bHvUFg== dependencies: call-bind "^1.0.2" - define-properties "^1.1.3" + define-properties "^1.1.4" + es-abstract "^1.19.5" string_decoder@^1.1.1: version "1.3.0" @@ -7279,13 +7243,13 @@ terminal-link@^2.0.0: supports-hyperlinks "^2.0.0" terser@^5.5.1: - version "5.12.1" - resolved "https://registry.yarnpkg.com/terser/-/terser-5.12.1.tgz#4cf2ebed1f5bceef5c83b9f60104ac4a78b49e9c" - integrity sha512-NXbs+7nisos5E+yXwAD+y7zrcTkMqb0dEJxIGtSKPdCBzopf7ni4odPul2aechpV7EXNvOudYOX2bb5tln1jbQ== + version "5.13.1" + resolved "https://registry.yarnpkg.com/terser/-/terser-5.13.1.tgz#66332cdc5a01b04a224c9fad449fc1a18eaa1799" + integrity sha512-hn4WKOfwnwbYfe48NgrQjqNOH9jzLqRcIfbYytOXCOv46LBfWr9bDS17MQqOi+BWGD0sJK3Sj5NC/gJjiojaoA== dependencies: acorn "^8.5.0" commander "^2.20.0" - source-map "~0.7.2" + source-map "~0.8.0-beta.0" source-map-support "~0.5.20" test-exclude@^6.0.0: @@ -7414,6 +7378,13 @@ tough-cookie@~2.5.0: psl "^1.1.28" punycode "^2.1.1" +tr46@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/tr46/-/tr46-1.0.1.tgz#a8b13fd6bfd2489519674ccde55ba3693b706d09" + integrity sha1-qLE/1r/SSJUZZ0zN5VujaTtwbQk= + dependencies: + punycode "^2.1.0" + tr46@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/tr46/-/tr46-2.1.0.tgz#fa87aa81ca5d5941da8cbf1f9b749dc969a4e240" @@ -7469,9 +7440,9 @@ tslib@^1.8.1: integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== tslib@^2.0.1: - version "2.3.1" - resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" - integrity sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw== + version "2.4.0" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.0.tgz#7cecaa7f073ce680a05847aa77be941098f36dc3" + integrity sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ== tsutils@^3.21.0: version "3.21.0" @@ -7569,9 +7540,9 @@ typescript@^3.2.2: integrity sha512-w6fIxVE/H1PkLKcCPsFqKE7Kv7QUwhU8qQY2MueZXWx5cPZdwFupLgKK3vntcK98BtNHZtAF4LA/yl2a7k8R6Q== typescript@^4.5.3, typescript@^4.5.4: - version "4.6.3" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.6.3.tgz#eefeafa6afdd31d725584c67a0eaba80f6fc6c6c" - integrity sha512-yNIatDa5iaofVozS/uQJEl3JRWLKKGJKh6Yaiv0GLGSuhpFJe7P3SbHZ8/yjAHRQwKRoA6YZqlfjXWmVzoVSMw== + version "4.6.4" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.6.4.tgz#caa78bbc3a59e6a5c510d35703f6a09877ce45e9" + integrity sha512-9ia/jWHIEbo49HfjrLGfKbZSuWo9iTMwXO+Ca3pRsSpbsMbc7/IU8NKdCZVRRBafVPGnoJeFL76ZOAA84I9fEg== typeson-registry@^1.0.0-alpha.20: version "1.0.0-alpha.39" @@ -7613,13 +7584,13 @@ umd@^3.0.0: integrity sha512-4IcGSufhFshvLNcMCV80UnQVlZ5pMOC8mvNPForqwA4+lzYQuetTESLDQkeLmihq8bRcnpbQa48Wb8Lh16/xow== unbox-primitive@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/unbox-primitive/-/unbox-primitive-1.0.1.tgz#085e215625ec3162574dc8859abee78a59b14471" - integrity sha512-tZU/3NqK3dA5gpE1KtyiJUrEB0lxnGkMFHptJ7q6ewdZ8s12QrODwNbhIJStmJkd1QDXa1NRA8aF2A1zk/Ypyw== + version "1.0.2" + resolved "https://registry.yarnpkg.com/unbox-primitive/-/unbox-primitive-1.0.2.tgz#29032021057d5e6cdbd08c5129c226dff8ed6f9e" + integrity sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw== dependencies: - function-bind "^1.1.1" - has-bigints "^1.0.1" - has-symbols "^1.0.2" + call-bind "^1.0.2" + has-bigints "^1.0.2" + has-symbols "^1.0.3" which-boxed-primitive "^1.0.2" undeclared-identifiers@^1.1.2: @@ -7634,9 +7605,9 @@ undeclared-identifiers@^1.1.2: xtend "^4.0.1" underscore@^1.13.2, underscore@~1.13.2: - version "1.13.2" - resolved "https://registry.yarnpkg.com/underscore/-/underscore-1.13.2.tgz#276cea1e8b9722a8dbed0100a407dda572125881" - integrity sha512-ekY1NhRzq0B08g4bGuX4wd2jZx5GnKz6mKSqFL4nqBlfyMGiG10gDFhDTMEfYmDL6Jy0FUIZp7wiRB+0BP7J2g== + version "1.13.3" + resolved "https://registry.yarnpkg.com/underscore/-/underscore-1.13.3.tgz#54bc95f7648c5557897e5e968d0f76bc062c34ee" + integrity sha512-QvjkYpiD+dJJraRA8+dGAU4i7aBbb2s0S3jA45TFOvg2VgqvdCDd/3N6CqA8gluk1W91GLoXg5enMUx560QzuA== unhomoglyph@^1.0.6: version "1.0.6" @@ -7767,14 +7738,14 @@ v8-to-istanbul@^7.0.0: convert-source-map "^1.6.0" source-map "^0.7.3" -v8-to-istanbul@^8.0.0: - version "8.1.1" - resolved "https://registry.yarnpkg.com/v8-to-istanbul/-/v8-to-istanbul-8.1.1.tgz#77b752fd3975e31bbcef938f85e9bd1c7a8d60ed" - integrity sha512-FGtKtv3xIpR6BYhvgH8MI/y78oT7d8Au3ww4QIxymrCtZEh5b8gCw2siywE+puhEmuWKDtmfrvF5UlB298ut3w== +v8-to-istanbul@^9.0.0: + version "9.0.0" + resolved "https://registry.yarnpkg.com/v8-to-istanbul/-/v8-to-istanbul-9.0.0.tgz#be0dae58719fc53cb97e5c7ac1d7e6d4f5b19511" + integrity sha512-HcvgY/xaRm7isYmyx+lFKA4uQmfUbN0J4M0nNItvzTvH/iQ9kW5j/t4YSR+Ge323/lrgDAWJoF46tzGQHwBHFw== dependencies: + "@jridgewell/trace-mapping" "^0.3.7" "@types/istanbul-lib-coverage" "^2.0.1" convert-source-map "^1.6.0" - source-map "^0.7.3" validate-npm-package-license@^3.0.1: version "3.0.4" @@ -7895,6 +7866,15 @@ whatwg-url@^5.0.0: tr46 "~0.0.3" webidl-conversions "^3.0.0" +whatwg-url@^7.0.0: + version "7.1.0" + resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-7.1.0.tgz#c2c492f1eca612988efd3d2266be1b9fc6170d06" + integrity sha512-WUu7Rg1DroM7oQvGWfOiAK21n74Gg+T4elXEQYkOhtyLeWiJFoOGLXPKI/9gzIie9CtwVLm8wtw6YJdKyxSjeg== + dependencies: + lodash.sortby "^4.7.0" + tr46 "^1.0.1" + webidl-conversions "^4.0.2" + whatwg-url@^8.0.0, whatwg-url@^8.4.0, whatwg-url@^8.5.0: version "8.7.0" resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-8.7.0.tgz#656a78e510ff8f3937bc0bcbe9f5c0ac35941b77" @@ -8088,7 +8068,7 @@ yargs-parser@^18.1.2: camelcase "^5.0.0" decamelize "^1.2.0" -yargs-parser@^20.2.2, yargs-parser@^20.2.7: +yargs-parser@^20.2.2, yargs-parser@^20.2.9: version "20.2.9" resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== From 8be30acb1169cb600b06308ffdeb2caeda0cf3c0 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Tue, 3 May 2022 22:40:57 +0100 Subject: [PATCH 04/38] Apply suggestions from SonarQube (#2340) --- spec/browserify/sync-browserify.spec.js | 4 +- src/autodiscovery.ts | 6 +- src/client.ts | 57 ++++++++----------- src/crypto/OlmDevice.ts | 8 +-- src/crypto/OutgoingRoomKeyRequestManager.ts | 4 +- src/crypto/SecretStorage.ts | 19 +++---- src/crypto/aes.ts | 2 +- src/crypto/algorithms/olm.ts | 8 +-- src/crypto/backup.ts | 14 ++--- src/crypto/dehydration.ts | 12 ++-- src/crypto/index.ts | 6 +- src/crypto/key_passphrase.ts | 4 +- src/crypto/verification/SAS.ts | 4 +- .../verification/request/InRoomChannel.ts | 5 +- src/http-api.ts | 6 +- src/matrix.ts | 3 +- src/pushprocessor.ts | 2 +- src/utils.ts | 12 +++- src/webrtc/call.ts | 6 +- 19 files changed, 86 insertions(+), 96 deletions(-) diff --git a/spec/browserify/sync-browserify.spec.js b/spec/browserify/sync-browserify.spec.js index fd4a0dc9b32..8a087c80722 100644 --- a/spec/browserify/sync-browserify.spec.js +++ b/spec/browserify/sync-browserify.spec.js @@ -47,7 +47,7 @@ describe("Browserify Test", function() { httpBackend.stop(); }); - it("Sync", async function() { + it("Sync", function() { const event = utils.mkMembership({ room: ROOM_ID, mship: "join", @@ -71,7 +71,7 @@ describe("Browserify Test", function() { }; httpBackend.when("GET", "/sync").respond(200, syncData); - return await Promise.race([ + return Promise.race([ httpBackend.flushAllExpected(), new Promise((_, reject) => { client.once("sync.unexpectedError", reject); diff --git a/src/autodiscovery.ts b/src/autodiscovery.ts index c60bd052986..5f875cc6815 100644 --- a/src/autodiscovery.ts +++ b/src/autodiscovery.ts @@ -410,14 +410,14 @@ export class AutoDiscovery { * the following properties: * raw: The JSON object returned by the server. * action: One of SUCCESS, IGNORE, or FAIL_PROMPT. - * reason: Relatively human readable description of what went wrong. + * reason: Relatively human-readable description of what went wrong. * error: The actual Error, if one exists. * @param {string} url The URL to fetch a JSON object from. * @return {Promise} Resolves to the returned state. * @private */ - private static async fetchWellKnownObject(url: string): Promise { - return new Promise(function(resolve, reject) { + private static fetchWellKnownObject(url: string): Promise { + return new Promise(function(resolve) { // eslint-disable-next-line const request = require("./matrix").getRequest(); if (!request) throw new Error("No request library available"); diff --git a/src/client.ts b/src/client.ts index d61ce4f7cf8..45ced3946f9 100644 --- a/src/client.ts +++ b/src/client.ts @@ -1296,9 +1296,9 @@ export class MatrixClient extends TypedEventEmitter { + public getDehydratedDevice(): Promise { try { - return await this.http.authedRequest( + return this.http.authedRequest( undefined, Method.Get, "/dehydrated_device", @@ -1324,7 +1324,7 @@ export class MatrixClient extends TypedEventEmitter { @@ -2605,9 +2602,9 @@ export class MatrixClient extends TypedEventEmitter} Information object from API or null */ public async getKeyBackupVersion(): Promise { - let res; + let res: IKeyBackupInfo; try { - res = await this.http.authedRequest( + res = await this.http.authedRequest( undefined, Method.Get, "/room_keys/version", undefined, undefined, { prefix: PREFIX_UNSTABLE }, ); @@ -2618,11 +2615,7 @@ export class MatrixClient extends TypedEventEmitter( undefined, Method.Get, path.path, path.queryData, undefined, { prefix: PREFIX_UNSTABLE }, - ) as IRoomsKeysResponse | IRoomKeysResponse | IKeyBackupSession; + ); if ((res as IRoomsKeysResponse).rooms) { const rooms = (res as IRoomsKeysResponse).rooms; @@ -3372,7 +3365,7 @@ export class MatrixClient extends TypedEventEmitter(eventType: string): Promise { + public getAccountDataFromServer(eventType: string): Promise { if (this.isInitialSyncComplete()) { const event = this.store.getAccountData(eventType); if (!event) { @@ -3387,7 +3380,7 @@ export class MatrixClient extends TypedEventEmitter { + this.syncLeftRoomsPromise.then(() => { logger.log("Marking success of sync left room request"); this.syncedLeftRooms = true; // flip the bit on success }).finally(() => { @@ -7203,7 +7196,7 @@ export class MatrixClient extends TypedEventEmitter { - return await this.cryptoStore.getEndToEndSessionProblem(deviceKey, timestamp); + public sessionMayHaveProblems(deviceKey: string, timestamp: number): Promise { + return this.cryptoStore.getEndToEndSessionProblem(deviceKey, timestamp); } - public async filterOutNotifiedErrorDevices(devices: IOlmDevice[]): Promise { - return await this.cryptoStore.filterOutNotifiedErrorDevices(devices); + public filterOutNotifiedErrorDevices(devices: IOlmDevice[]): Promise { + return this.cryptoStore.filterOutNotifiedErrorDevices(devices); } // Outbound group session diff --git a/src/crypto/OutgoingRoomKeyRequestManager.ts b/src/crypto/OutgoingRoomKeyRequestManager.ts index e053d8072a4..83229411027 100644 --- a/src/crypto/OutgoingRoomKeyRequestManager.ts +++ b/src/crypto/OutgoingRoomKeyRequestManager.ts @@ -189,9 +189,7 @@ export class OutgoingRoomKeyRequestManager { // in state ROOM_KEY_REQUEST_STATES.SENT, so we must have // raced with another tab to mark the request cancelled. // Try again, to make sure the request is resent. - return await this.queueRoomKeyRequest( - requestBody, recipients, resend, - ); + return this.queueRoomKeyRequest(requestBody, recipients, resend); } // We don't want to wait for the timer, so we send it diff --git a/src/crypto/SecretStorage.ts b/src/crypto/SecretStorage.ts index b0c7891d0d6..f36b66c921f 100644 --- a/src/crypto/SecretStorage.ts +++ b/src/crypto/SecretStorage.ts @@ -329,7 +329,7 @@ export class SecretStorage { // encoded, since this is how a key would normally be stored. if (encInfo.passthrough) return encodeBase64(decryption.get_private_key()); - return await decryption.decrypt(encInfo); + return decryption.decrypt(encInfo); } finally { if (decryption && decryption.free) decryption.free(); } @@ -345,15 +345,10 @@ export class SecretStorage { * with, or null if it is not present or not encrypted with a trusted * key */ - public async isStored(name: string, checkKey: boolean): Promise | null> { + public async isStored(name: string, checkKey = true): Promise | null> { // check if secret exists const secretInfo = await this.accountDataAdapter.getAccountDataFromServer(name); - if (!secretInfo) return null; - if (!secretInfo.encrypted) { - return null; - } - - if (checkKey === undefined) checkKey = true; + if (!secretInfo?.encrypted) return null; const ret = {}; @@ -598,11 +593,11 @@ export class SecretStorage { if (keys[keyId].algorithm === SECRET_STORAGE_ALGORITHM_V1_AES) { const decryption = { - encrypt: async function(secret: string): Promise { - return await encryptAES(secret, privateKey, name); + encrypt: function(secret: string): Promise { + return encryptAES(secret, privateKey, name); }, - decrypt: async function(encInfo: IEncryptedPayload): Promise { - return await decryptAES(encInfo, privateKey, name); + decrypt: function(encInfo: IEncryptedPayload): Promise { + return decryptAES(encInfo, privateKey, name); }, }; return [keyId, decryption]; diff --git a/src/crypto/aes.ts b/src/crypto/aes.ts index 077c0afd0fc..4aa38ac543a 100644 --- a/src/crypto/aes.ts +++ b/src/crypto/aes.ts @@ -250,7 +250,7 @@ async function deriveKeysBrowser(key: Uint8Array, name: string): Promise<[Crypto ['sign', 'verify'], ); - return await Promise.all([aesProm, hmacProm]); + return Promise.all([aesProm, hmacProm]); } export function encryptAES(data: string, key: Uint8Array, name: string, ivStr?: string): Promise { diff --git a/src/crypto/algorithms/olm.ts b/src/crypto/algorithms/olm.ts index 36917873788..c640d14efa1 100644 --- a/src/crypto/algorithms/olm.ts +++ b/src/crypto/algorithms/olm.ts @@ -70,7 +70,7 @@ class OlmEncryption extends EncryptionAlgorithm { return Promise.resolve(); } - this.prepPromise = this.crypto.downloadKeys(roomMembers).then((res) => { + this.prepPromise = this.crypto.downloadKeys(roomMembers).then(() => { return this.crypto.ensureOlmSessionsForUsers(roomMembers); }).then(() => { this.sessionPrepared = true; @@ -144,7 +144,7 @@ class OlmEncryption extends EncryptionAlgorithm { } } - return await Promise.all(promises).then(() => encryptedContent); + return Promise.all(promises).then(() => encryptedContent); } } @@ -261,7 +261,7 @@ class OlmDecryption extends DecryptionAlgorithm { * * @return {string} payload, if decrypted successfully. */ - private async decryptMessage(theirDeviceIdentityKey: string, message: IMessage): Promise { + private decryptMessage(theirDeviceIdentityKey: string, message: IMessage): Promise { // This is a wrapper that serialises decryptions of prekey messages, because // otherwise we race between deciding we have no active sessions for the message // and creating a new one, which we can only do once because it removes the OTK. @@ -274,7 +274,7 @@ class OlmDecryption extends DecryptionAlgorithm { }); // we want the error, but don't propagate it to the next decryption this.olmDevice.olmPrekeyPromise = myPromise.catch(() => {}); - return await myPromise; + return myPromise; } } diff --git a/src/crypto/backup.ts b/src/crypto/backup.ts index eddbabe11bd..c68e5def5fd 100644 --- a/src/crypto/backup.ts +++ b/src/crypto/backup.ts @@ -132,18 +132,18 @@ export class BackupManager { if (!Algorithm) { throw new Error("Unknown backup algorithm: " + info.algorithm); } - if (!(typeof info.auth_data === "object")) { + if (typeof info.auth_data !== "object") { throw new Error("Invalid backup data returned"); } return Algorithm.checkBackupVersion(info); } - public static async makeAlgorithm(info: IKeyBackupInfo, getKey: GetKey): Promise { + public static makeAlgorithm(info: IKeyBackupInfo, getKey: GetKey): Promise { const Algorithm = algorithmsByName[info.algorithm]; if (!Algorithm) { throw new Error("Unknown backup algorithm"); } - return await Algorithm.init(info.auth_data, getKey); + return Algorithm.init(info.auth_data, getKey); } public async enableKeyBackup(info: IKeyBackupInfo): Promise { @@ -777,15 +777,15 @@ export class Aes256 implements BackupAlgorithm { public get untrusted() { return false; } - async encryptSession(data: Record): Promise { + public encryptSession(data: Record): Promise { const plainText: Record = Object.assign({}, data); delete plainText.session_id; delete plainText.room_id; delete plainText.first_known_index; - return await encryptAES(JSON.stringify(plainText), this.key, data.session_id); + return encryptAES(JSON.stringify(plainText), this.key, data.session_id); } - async decryptSessions(sessions: Record): Promise { + public async decryptSessions(sessions: Record): Promise { const keys: IMegolmSessionData[] = []; for (const [sessionId, sessionData] of Object.entries(sessions)) { @@ -800,7 +800,7 @@ export class Aes256 implements BackupAlgorithm { return keys; } - async keyMatches(key: Uint8Array): Promise { + public async keyMatches(key: Uint8Array): Promise { if (this.authData.mac) { const { mac } = await calculateKeyCheck(key, this.authData.iv); return this.authData.mac.replace(/=+$/g, '') === mac.replace(/=+/g, ''); diff --git a/src/crypto/dehydration.ts b/src/crypto/dehydration.ts index 49234481853..b775d76069f 100644 --- a/src/crypto/dehydration.ts +++ b/src/crypto/dehydration.ts @@ -61,11 +61,13 @@ export class DehydrationManager { private key: Uint8Array; private keyInfo: {[props: string]: any}; private deviceDisplayName: string; + constructor(private readonly crypto: Crypto) { this.getDehydrationKeyFromCache(); } - async getDehydrationKeyFromCache(): Promise { - return await this.crypto.cryptoStore.doTxn( + + public getDehydrationKeyFromCache(): Promise { + return this.crypto.cryptoStore.doTxn( 'readonly', [IndexedDBCryptoStore.STORE_ACCOUNT], (txn) => { @@ -93,7 +95,7 @@ export class DehydrationManager { } /** set the key, and queue periodic dehydration to the server in the background */ - async setKeyAndQueueDehydration( + public async setKeyAndQueueDehydration( key: Uint8Array, keyInfo: {[props: string]: any} = {}, deviceDisplayName: string = undefined, ): Promise { @@ -104,7 +106,7 @@ export class DehydrationManager { } } - async setKey( + public async setKey( key: Uint8Array, keyInfo: {[props: string]: any} = {}, deviceDisplayName: string = undefined, ): Promise { @@ -148,7 +150,7 @@ export class DehydrationManager { } /** returns the device id of the newly created dehydrated device */ - async dehydrateDevice(): Promise { + public async dehydrateDevice(): Promise { if (this.inProgress) { logger.log("Dehydration already in progress -- not starting new dehydration"); return; diff --git a/src/crypto/index.ts b/src/crypto/index.ts index 201545e8027..0842dda530c 100644 --- a/src/crypto/index.ts +++ b/src/crypto/index.ts @@ -402,7 +402,7 @@ export class Crypto extends TypedEventEmitter { +export function keyFromAuthData(authData: IAuthData, password: string): Promise { if (!global.Olm) { throw new Error("Olm is not available"); } @@ -50,7 +50,7 @@ export async function keyFromAuthData(authData: IAuthData, password: string): Pr ); } - return await deriveKey( + return deriveKey( password, authData.private_key_salt, authData.private_key_iterations, authData.private_key_bits || DEFAULT_BITSIZE, diff --git a/src/crypto/verification/SAS.ts b/src/crypto/verification/SAS.ts index a909ce7421b..93244464f66 100644 --- a/src/crypto/verification/SAS.ts +++ b/src/crypto/verification/SAS.ts @@ -271,9 +271,9 @@ export class SAS extends Base { do { try { if (this.initiatedByMe) { - return await this.doSendVerification(); + return this.doSendVerification(); } else { - return await this.doRespondVerification(); + return this.doRespondVerification(); } } catch (err) { if (err instanceof SwitchStartEventError) { diff --git a/src/crypto/verification/request/InRoomChannel.ts b/src/crypto/verification/request/InRoomChannel.ts index 9e8690e1d44..67082ff835e 100644 --- a/src/crypto/verification/request/InRoomChannel.ts +++ b/src/crypto/verification/request/InRoomChannel.ts @@ -184,7 +184,7 @@ export class InRoomChannel implements IVerificationChannel { * @param {boolean} isLiveEvent whether this is an even received through sync or not * @returns {Promise} a promise that resolves when any requests as an answer to the passed-in event are sent. */ - public async handleEvent(event: MatrixEvent, request: VerificationRequest, isLiveEvent = false): Promise { + public handleEvent(event: MatrixEvent, request: VerificationRequest, isLiveEvent = false): Promise { // prevent processing the same event multiple times, as under // some circumstances Room.timeline can get emitted twice for the same event if (request.hasEventId(event.getId())) { @@ -221,8 +221,7 @@ export class InRoomChannel implements IVerificationChannel { const isRemoteEcho = !!event.getUnsigned().transaction_id; const isSentByUs = event.getSender() === this.client.getUserId(); - return await request.handleEvent( - type, event, isLiveEvent, isRemoteEcho, isSentByUs); + return request.handleEvent(type, event, isLiveEvent, isRemoteEcho, isSentByUs); } /** diff --git a/src/http-api.ts b/src/http-api.ts index 5ee24312a3d..c5c7517fdde 100644 --- a/src/http-api.ts +++ b/src/http-api.ts @@ -30,7 +30,7 @@ import type { Request as _Request, CoreOptions } from "request"; import * as callbacks from "./realtime-callbacks"; import { IUploadOpts } from "./@types/requests"; import { IAbortablePromise, IUsageLimit } from "./@types/partials"; -import { IDeferred } from "./utils"; +import { IDeferred, sleep } from "./utils"; import { Callback } from "./client"; import * as utils from "./utils"; import { logger } from './logger'; @@ -1114,9 +1114,9 @@ export async function retryNetworkOperation(maxAttempts: number, callback: () const timeout = 1000 * Math.pow(2, attempts); logger.log(`network operation failed ${attempts} times,` + ` retrying in ${timeout}ms...`); - await new Promise(r => setTimeout(r, timeout)); + await sleep(timeout); } - return await callback(); + return callback(); } catch (err) { if (err instanceof ConnectionError) { attempts += 1; diff --git a/src/matrix.ts b/src/matrix.ts index 5379b461acf..c85544e669e 100644 --- a/src/matrix.ts +++ b/src/matrix.ts @@ -17,8 +17,7 @@ limitations under the License. import { MemoryCryptoStore } from "./crypto/store/memory-crypto-store"; import { MemoryStore } from "./store/memory"; import { MatrixScheduler } from "./scheduler"; -import { MatrixClient } from "./client"; -import { ICreateClientOpts } from "./client"; +import { MatrixClient, ICreateClientOpts } from "./client"; import { DeviceTrustLevel } from "./crypto/CrossSigning"; import { ISecretStorageKeyInfo } from "./crypto/api"; diff --git a/src/pushprocessor.ts b/src/pushprocessor.ts index ae170751f00..2f4f58bd429 100644 --- a/src/pushprocessor.ts +++ b/src/pushprocessor.ts @@ -300,7 +300,7 @@ export class PushProcessor { const memberCount = room.currentState.getJoinedMemberCount(); - const m = cond.is.match(/^([=<>]*)([0-9]*)$/); + const m = cond.is.match(/^([=<>]*)(\d*)$/); if (!m) { return false; } diff --git a/src/utils.ts b/src/utils.ts index 95e415502fa..77753128611 100644 --- a/src/utils.ts +++ b/src/utils.ts @@ -465,7 +465,7 @@ export function defer(): IDeferred { export async function promiseMapSeries( promises: Array>, - fn: (t: T) => void, + fn: (t: T) => Promise | void, // if async/promise we don't care about the type as we only await resolution ): Promise { for (const o of promises) { await fn(await o); @@ -473,7 +473,7 @@ export async function promiseMapSeries( } export function promiseTry(fn: () => T | Promise): Promise { - return new Promise((resolve) => resolve(fn())); + return Promise.resolve(fn()); } // Creates and awaits all promises, running no more than `chunkSize` at the same time @@ -676,7 +676,13 @@ export function prevString(s: string, alphabet = DEFAULT_ALPHABET): string { export function lexicographicCompare(a: string, b: string): number { // Dev note: this exists because I'm sad that you can use math operators on strings, so I've // hidden the operation in this function. - return (a < b) ? -1 : ((a === b) ? 0 : 1); + if (a < b) { + return -1; + } else if (a > b) { + return 1; + } else { + return 0; + } } const collator = new Intl.Collator(); diff --git a/src/webrtc/call.ts b/src/webrtc/call.ts index 16f443b4bc3..dcc1016a69a 100644 --- a/src/webrtc/call.ts +++ b/src/webrtc/call.ts @@ -988,9 +988,7 @@ export class MatrixCall extends TypedEventEmitter { + public async setScreensharingEnabled(enabled: boolean, desktopCapturerSourceId?: string): Promise { // Skip if there is nothing to do if (enabled && this.isScreensharing()) { logger.warn(`There is already a screensharing stream - there is nothing to do!`); @@ -1002,7 +1000,7 @@ export class MatrixCall extends TypedEventEmitter Date: Tue, 3 May 2022 22:44:57 +0100 Subject: [PATCH 05/38] Update upgrade_dependencies.yml (#2343) --- .github/workflows/upgrade_dependencies.yml | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/.github/workflows/upgrade_dependencies.yml b/.github/workflows/upgrade_dependencies.yml index 37315444e7e..fcb9e507afc 100644 --- a/.github/workflows/upgrade_dependencies.yml +++ b/.github/workflows/upgrade_dependencies.yml @@ -1,7 +1,10 @@ name: Upgrade Dependencies on: workflow_dispatch: { } - workflow_call: { } + workflow_call: + secrets: + ELEMENT_BOT_TOKEN: + required: true jobs: upgrade: runs-on: ubuntu-latest @@ -16,9 +19,18 @@ jobs: run: yarn upgrade && yarn install - name: Create Pull Request + id: cpr uses: peter-evans/create-pull-request@v4 with: + token: ${{ secrets.ELEMENT_BOT_TOKEN }} branch: actions/upgrade-deps delete-branch: true title: Upgrade dependencies labels: T-Task + + - name: Enable automerge + uses: peter-evans/enable-pull-request-automerge@v2 + if: steps.cpr.outputs.pull-request-operation == 'created' + with: + token: ${{ secrets.ELEMENT_BOT_TOKEN }} + pull-request-number: ${{ steps.cpr.outputs.pull-request-number }} From 592f2931dcf720c8447a6f0e65ff98d515e65eb4 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Wed, 4 May 2022 14:27:42 +0100 Subject: [PATCH 06/38] Add label to dependency upgrade PRs (#2345) --- .github/workflows/upgrade_dependencies.yml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/.github/workflows/upgrade_dependencies.yml b/.github/workflows/upgrade_dependencies.yml index fcb9e507afc..2cabf1f196f 100644 --- a/.github/workflows/upgrade_dependencies.yml +++ b/.github/workflows/upgrade_dependencies.yml @@ -26,7 +26,9 @@ jobs: branch: actions/upgrade-deps delete-branch: true title: Upgrade dependencies - labels: T-Task + labels: | + Dependencies + T-Task - name: Enable automerge uses: peter-evans/enable-pull-request-automerge@v2 From 1cde686a13870331f266a138ef7af97b12fa8460 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C5=A0imon=20Brandner?= Date: Wed, 4 May 2022 16:22:43 +0200 Subject: [PATCH 07/38] MSC3786: Add a default push rule to ignore `m.room.server_acl` events (#2333) Co-authored-by: Michael Telatynski <7t3chguy@gmail.com> --- spec/unit/pushprocessor.spec.js | 17 +++++++++++++++++ src/pushprocessor.ts | 17 +++++++++++++++++ 2 files changed, 34 insertions(+) diff --git a/spec/unit/pushprocessor.spec.js b/spec/unit/pushprocessor.spec.js index 85fadcf78c1..df7666d5cd3 100644 --- a/spec/unit/pushprocessor.spec.js +++ b/spec/unit/pushprocessor.spec.js @@ -1,5 +1,6 @@ import * as utils from "../test-utils/test-utils"; import { PushProcessor } from "../../src/pushprocessor"; +import { EventType } from "../../src"; describe('NotificationService', function() { const testUserId = "@ali:matrix.org"; @@ -208,6 +209,7 @@ describe('NotificationService', function() { msgtype: "m.text", }, }); + matrixClient.pushRules = PushProcessor.rewriteDefaultRules(matrixClient.pushRules); pushProcessor = new PushProcessor(matrixClient); }); @@ -295,6 +297,21 @@ describe('NotificationService', function() { expect(actions.tweaks.highlight).toEqual(false); }); + it('should not bing on room server ACL changes', function() { + testEvent = utils.mkEvent({ + type: EventType.RoomServerAcl, + room: testRoomId, + user: "@alfred:localhost", + event: true, + content: {}, + }); + + const actions = pushProcessor.actionsForEvent(testEvent); + expect(actions.tweaks.highlight).toBeFalsy(); + expect(actions.tweaks.sound).toBeFalsy(); + expect(actions.notify).toBeFalsy(); + }); + // invalid it('should gracefully handle bad input.', function() { diff --git a/src/pushprocessor.ts b/src/pushprocessor.ts index 2f4f58bd429..5afe8505e7c 100644 --- a/src/pushprocessor.ts +++ b/src/pushprocessor.ts @@ -34,6 +34,7 @@ import { PushRuleSet, TweakName, } from "./@types/PushRules"; +import { EventType } from "./@types/event"; /** * @module pushprocessor @@ -96,6 +97,22 @@ const DEFAULT_OVERRIDE_RULES: IPushRule[] = [ PushRuleActionName.DontNotify, ], }, + { + // For homeservers which don't support MSC3786 yet + rule_id: ".org.matrix.msc3786.rule.room.server_acl", + default: true, + enabled: true, + conditions: [ + { + kind: ConditionKind.EventMatch, + key: "type", + pattern: EventType.RoomServerAcl, + }, + ], + actions: [ + PushRuleActionName.DontNotify, + ], + }, ]; export interface IActionsObject { From a388fde3e246bbf8ee4151878802c5d9b2bac13e Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Wed, 4 May 2022 20:36:00 +0100 Subject: [PATCH 08/38] Tweak sonar-project.properties (#2348) --- sonar-project.properties | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/sonar-project.properties b/sonar-project.properties index 0ae44d043e6..20439adeb61 100644 --- a/sonar-project.properties +++ b/sonar-project.properties @@ -1,13 +1,6 @@ sonar.projectKey=matrix-js-sdk sonar.organization=matrix-org -# This is the name and version displayed in the SonarCloud UI. -#sonar.projectName=matrix-js-sdk -#sonar.projectVersion=1.0 - -# Path is relative to the sonar-project.properties file. Replace "\" by "/" on Windows. -#sonar.sources=. - # Encoding of the source code. Default is default system encoding #sonar.sourceEncoding=UTF-8 @@ -17,5 +10,5 @@ sonar.exclusions=docs,examples,git-hooks sonar.typescript.tsconfigPath=./tsconfig.json sonar.javascript.lcov.reportPaths=coverage/lcov.info -sonar.coverage.exclusions=spec/*.ts +sonar.coverage.exclusions=spec/**/* sonar.testExecutionReportPaths=coverage/test-report.xml From dea3f52fe93f64b1e09f9e9c1984f894476e9ed0 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Thu, 5 May 2022 04:34:21 +0100 Subject: [PATCH 09/38] Another SonarQube happiness pass (#2347) --- src/client.ts | 18 ++++++++---------- src/crypto/DeviceList.ts | 4 ++-- src/crypto/verification/SAS.ts | 4 ++-- src/matrix.ts | 2 +- src/models/event-timeline-set.ts | 1 - src/models/room-state.ts | 3 +-- src/models/room.ts | 20 ++++++++++---------- src/store/index.ts | 2 +- src/store/stub.ts | 2 +- 9 files changed, 26 insertions(+), 30 deletions(-) diff --git a/src/client.ts b/src/client.ts index 45ced3946f9..220795e8b65 100644 --- a/src/client.ts +++ b/src/client.ts @@ -1296,9 +1296,9 @@ export class MatrixClient extends TypedEventEmitter { + public async getDehydratedDevice(): Promise { try { - return this.http.authedRequest( + return await this.http.authedRequest( undefined, Method.Get, "/dehydrated_device", @@ -3365,7 +3365,7 @@ export class MatrixClient extends TypedEventEmitter(eventType: string): Promise { + public async getAccountDataFromServer(eventType: string): Promise { if (this.isInitialSyncComplete()) { const event = this.store.getAccountData(eventType); if (!event) { @@ -3380,11 +3380,9 @@ export class MatrixClient extends TypedEventEmitter = {}; // {roomId: Error} + const populationResults: { [roomId: string]: Error } = {}; const promises = []; const doLeave = (roomId: string) => { @@ -5875,7 +5873,7 @@ export class MatrixClient extends TypedEventEmitter | void { let promise: Promise; - let hasDontNotifyRule; + let hasDontNotifyRule = false; // Get the existing room-kind push rule if any const roomPushRule = this.getRoomPushRule(scope, roomId); @@ -5928,7 +5926,7 @@ export class MatrixClient extends TypedEventEmitter { // Update it even if the previous operation fails. This can help the - // app to recover when push settings has been modifed from another client + // app to recover when push settings has been modified from another client this.getPushRules().then((result) => { this.pushRules = result; reject(err); diff --git a/src/crypto/DeviceList.ts b/src/crypto/DeviceList.ts index 5fdae5c245f..40c055c7b50 100644 --- a/src/crypto/DeviceList.ts +++ b/src/crypto/DeviceList.ts @@ -122,7 +122,7 @@ export class DeviceList extends TypedEventEmitter { this.cryptoStore.getEndToEndDeviceData(txn, (deviceData) => { this.hasFetched = Boolean(deviceData && deviceData.devices); - this.devices = deviceData ? deviceData.devices : {}, + this.devices = deviceData ? deviceData.devices : {}; this.crossSigningInfo = deviceData ? deviceData.crossSigningInfo || {} : {}; this.deviceTrackingStatus = deviceData ? @@ -190,7 +190,7 @@ export class DeviceList extends TypedEventEmitter { + savePromise = new Promise((resolve) => { this.resolveSavePromise = resolve; }); this.savePromise = savePromise; diff --git a/src/crypto/verification/SAS.ts b/src/crypto/verification/SAS.ts index 93244464f66..a909ce7421b 100644 --- a/src/crypto/verification/SAS.ts +++ b/src/crypto/verification/SAS.ts @@ -271,9 +271,9 @@ export class SAS extends Base { do { try { if (this.initiatedByMe) { - return this.doSendVerification(); + return await this.doSendVerification(); } else { - return this.doRespondVerification(); + return await this.doRespondVerification(); } } catch (err) { if (err instanceof SwitchStartEventError) { diff --git a/src/matrix.ts b/src/matrix.ts index c85544e669e..e2ce5e11c9a 100644 --- a/src/matrix.ts +++ b/src/matrix.ts @@ -152,7 +152,7 @@ export interface ICryptoCallbacks { export function createClient(opts: ICreateClientOpts | string) { if (typeof opts === "string") { opts = { - "baseUrl": opts as string, + "baseUrl": opts, }; } opts.request = opts.request || requestInstance; diff --git a/src/models/event-timeline-set.ts b/src/models/event-timeline-set.ts index d7396278132..aeb019112d0 100644 --- a/src/models/event-timeline-set.ts +++ b/src/models/event-timeline-set.ts @@ -28,7 +28,6 @@ import { EventType, RelationType } from "../@types/event"; import { RoomState } from "./room-state"; import { TypedEventEmitter } from "./typed-event-emitter"; -// var DEBUG = false; const DEBUG = true; let debuglog: (...args: any[]) => void; diff --git a/src/models/room-state.ts b/src/models/room-state.ts index d6513389948..30b87f487b9 100644 --- a/src/models/room-state.ts +++ b/src/models/room-state.ts @@ -26,10 +26,9 @@ import { MatrixEvent, MatrixEventEvent } from "./event"; import { MatrixClient } from "../client"; import { GuestAccess, HistoryVisibility, IJoinRuleEventContent, JoinRule } from "../@types/partials"; import { TypedEventEmitter } from "./typed-event-emitter"; -import { Beacon, BeaconEvent, BeaconEventHandlerMap } from "./beacon"; +import { Beacon, BeaconEvent, BeaconEventHandlerMap, getBeaconInfoIdentifier, BeaconIdentifier } from "./beacon"; import { TypedReEmitter } from "../ReEmitter"; import { M_BEACON, M_BEACON_INFO } from "../@types/beacon"; -import { getBeaconInfoIdentifier, BeaconIdentifier } from "./beacon"; // possible statuses for out-of-band member loading enum OobStatus { diff --git a/src/models/room.ts b/src/models/room.ts index e0769097ecd..be185255397 100644 --- a/src/models/room.ts +++ b/src/models/room.ts @@ -1124,14 +1124,14 @@ export class Room extends TypedEventEmitter * The aliases returned by this function may not necessarily * still point to this room. * @return {array} The room's alias as an array of strings + * @deprecated this uses m.room.aliases events, replaced by Room::getAltAliases() */ public getAliases(): string[] { const aliasStrings: string[] = []; const aliasEvents = this.currentState.getStateEvents(EventType.RoomAliases); if (aliasEvents) { - for (let i = 0; i < aliasEvents.length; ++i) { - const aliasEvent = aliasEvents[i]; + for (const aliasEvent of aliasEvents) { if (Array.isArray(aliasEvent.getContent().aliases)) { const filteredAliases = aliasEvent.getContent<{ aliases: string[] }>().aliases.filter(a => { if (typeof(a) !== "string") return false; @@ -1141,7 +1141,7 @@ export class Room extends TypedEventEmitter // It's probably valid by here. return true; }); - Array.prototype.push.apply(aliasStrings, filteredAliases); + aliasStrings.push(...filteredAliases); } } } @@ -1644,8 +1644,8 @@ export class Room extends TypedEventEmitter eventsByThread[threadId]?.push(event); } - Object.entries(eventsByThread).map(([threadId, events]) => ( - this.addThreadedEvents(threadId, events, toStartOfTimeline) + Object.entries(eventsByThread).map(([threadId, threadEvents]) => ( + this.addThreadedEvents(threadId, threadEvents, toStartOfTimeline) )); } @@ -2143,23 +2143,23 @@ export class Room extends TypedEventEmitter const threadRoots = this.findThreadRoots(events); const eventsByThread: { [threadId: string]: MatrixEvent[] } = {}; - for (let i = 0; i < events.length; i++) { + for (const event of events) { // TODO: We should have a filter to say "only add state event types X Y Z to the timeline". - this.processLiveEvent(events[i]); + this.processLiveEvent(event); const { shouldLiveInRoom, shouldLiveInThread, threadId, - } = this.eventShouldLiveIn(events[i], events, threadRoots); + } = this.eventShouldLiveIn(event, events, threadRoots); if (shouldLiveInThread && !eventsByThread[threadId]) { eventsByThread[threadId] = []; } - eventsByThread[threadId]?.push(events[i]); + eventsByThread[threadId]?.push(event); if (shouldLiveInRoom) { - this.addLiveEvent(events[i], duplicateStrategy, fromCache); + this.addLiveEvent(event, duplicateStrategy, fromCache); } } diff --git a/src/store/index.ts b/src/store/index.ts index 51d325c953f..c47bd20ad48 100644 --- a/src/store/index.ts +++ b/src/store/index.ts @@ -37,7 +37,7 @@ export interface ISavedSync { export interface IStore { readonly accountData: Record; // type : content - /** @return {Promise} whether or not the database was newly created in this session. */ + /** @return {Promise} whether or not the database was newly created in this session. */ isNewlyCreated(): Promise; /** diff --git a/src/store/stub.ts b/src/store/stub.ts index 47e1188a269..1b3a8773f4e 100644 --- a/src/store/stub.ts +++ b/src/store/stub.ts @@ -123,7 +123,7 @@ export class StubStore implements IStore { /** * No-op. * @param {Room} room - * @param {integer} limit + * @param {number} limit * @return {Array} */ public scrollback(room: Room, limit: number): MatrixEvent[] { From 6b5f4aa0a9c16fa0b3a5252ad5e60802adb05ac0 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Thu, 5 May 2022 07:14:23 +0100 Subject: [PATCH 10/38] Prune both clear & wire content on redaction (#2346) --- spec/unit/models/event.spec.ts | 27 +++++++++++++++++++++++++++ src/models/event.ts | 22 ++++++++++------------ 2 files changed, 37 insertions(+), 12 deletions(-) diff --git a/spec/unit/models/event.spec.ts b/spec/unit/models/event.spec.ts index f1a8969ddfd..7f2b263137c 100644 --- a/spec/unit/models/event.spec.ts +++ b/spec/unit/models/event.spec.ts @@ -57,4 +57,31 @@ describe('MatrixEvent', () => { expect(a.toSnapshot().isEquivalentTo(a)).toBe(true); expect(a.toSnapshot().isEquivalentTo(b)).toBe(false); }); + + it("should prune clearEvent when being redacted", () => { + const ev = new MatrixEvent({ + type: "m.room.message", + content: { + body: "Test", + }, + event_id: "$event1:server", + }); + + expect(ev.getContent().body).toBe("Test"); + expect(ev.getWireContent().body).toBe("Test"); + ev.makeEncrypted("m.room.encrypted", { ciphertext: "xyz" }, "", ""); + expect(ev.getContent().body).toBe("Test"); + expect(ev.getWireContent().body).toBeUndefined(); + expect(ev.getWireContent().ciphertext).toBe("xyz"); + + const redaction = new MatrixEvent({ + type: "m.room.redaction", + redacts: ev.getId(), + }); + + ev.makeRedacted(redaction); + expect(ev.getContent().body).toBeUndefined(); + expect(ev.getWireContent().body).toBeUndefined(); + expect(ev.getWireContent().ciphertext).toBeUndefined(); + }); }); diff --git a/src/models/event.ts b/src/models/event.ts index bcfaab9c658..227036be5e7 100644 --- a/src/models/event.ts +++ b/src/models/event.ts @@ -1112,23 +1112,21 @@ export class MatrixEvent extends TypedEventEmitter Date: Fri, 6 May 2022 13:20:54 -0600 Subject: [PATCH 11/38] Remove hacky custom status feature (#2350) This is unstable, so should be more than safe to just outright remove without notice. --- src/client.ts | 20 -------------------- src/models/user.ts | 21 --------------------- src/sync.ts | 10 ---------- 3 files changed, 51 deletions(-) diff --git a/src/client.ts b/src/client.ts index 220795e8b65..711bf3e4e5e 100644 --- a/src/client.ts +++ b/src/client.ts @@ -5063,26 +5063,6 @@ export class MatrixClient extends TypedEventEmitter { // eslint-disable-line - const type = "im.vector.user_status"; - return Promise.all(this.getRooms().map(async (room) => { - const isJoined = room.getMyMembership() === "join"; - const looksLikeDm = room.getInvitedAndJoinedMemberCount() === 2; - if (!isJoined || !looksLikeDm) return; - // Check power level separately as it's a bit more expensive. - const maySend = room.currentState.mayClientSendStateEvent(type, this); - if (!maySend) return; - await this.sendStateEvent(room.roomId, type, { status: newMessage }, this.getUserId()); - })).then(); // .then to fix return type - } - /** * @param {Object} opts Options to apply * @param {string} opts.presence One of "online", "offline" or "unavailable" diff --git a/src/models/user.ts b/src/models/user.ts index aad80e57501..df580b0f1f5 100644 --- a/src/models/user.ts +++ b/src/models/user.ts @@ -27,8 +27,6 @@ export enum UserEvent { Presence = "User.presence", CurrentlyActive = "User.currentlyActive", LastPresenceTs = "User.lastPresenceTs", - /* @deprecated */ - _UnstableStatusMessage = "User.unstable_statusMessage", } export type UserEventHandlerMap = { @@ -37,7 +35,6 @@ export type UserEventHandlerMap = { [UserEvent.Presence]: (event: MatrixEvent | undefined, user: User) => void; [UserEvent.CurrentlyActive]: (event: MatrixEvent | undefined, user: User) => void; [UserEvent.LastPresenceTs]: (event: MatrixEvent | undefined, user: User) => void; - [UserEvent._UnstableStatusMessage]: (user: User) => void; }; export class User extends TypedEventEmitter { @@ -59,8 +56,6 @@ export class User extends TypedEventEmitter { presence: null, profile: null, }; - // eslint-disable-next-line camelcase - public unstable_statusMessage = ""; /** * Construct a new User. A User must have an ID and can optionally have extra @@ -81,9 +76,6 @@ export class User extends TypedEventEmitter { * when a user was last active. * @prop {Boolean} currentlyActive Whether we should consider lastActiveAgo to be * an approximation and that the user should be seen as active 'now' - * @prop {string} unstable_statusMessage The status message for the user, if known. This is - * different from the presenceStatusMsg in that this is not tied to - * the user's presence, and should be represented differently. * @prop {Object} events The events describing this user. * @prop {MatrixEvent} events.presence The m.presence event for this user. */ @@ -219,19 +211,6 @@ export class User extends TypedEventEmitter { public getLastActiveTs(): number { return this.lastPresenceTs - this.lastActiveAgo; } - - /** - * Manually set the user's status message. - * @param {MatrixEvent} event The im.vector.user_status event. - * @fires module:client~MatrixClient#event:"User.unstable_statusMessage" - */ - // eslint-disable-next-line - public unstable_updateStatusMessage(event: MatrixEvent): void { - if (!event.getContent()) this.unstable_statusMessage = ""; - else this.unstable_statusMessage = event.getContent()["status"]; - this.updateModifiedTime(); - this.emit(UserEvent._UnstableStatusMessage, this); - } } /** diff --git a/src/sync.ts b/src/sync.ts index 30df2cb7e6c..0791920a9ff 100644 --- a/src/sync.ts +++ b/src/sync.ts @@ -1295,16 +1295,6 @@ export class SyncApi { if (e.isState() && e.getType() == "m.room.encryption" && this.opts.crypto) { await this.opts.crypto.onCryptoEvent(e); } - if (e.isState() && e.getType() === "im.vector.user_status") { - let user = client.store.getUser(e.getStateKey()); - if (user) { - user.unstable_updateStatusMessage(e); - } else { - user = createNewUser(client, e.getStateKey()); - user.unstable_updateStatusMessage(e); - client.store.storeUser(user); - } - } }; await utils.promiseMapSeries(stateEvents, processRoomEvent); From da69ca215b9cbe03b135482ef2646225c179fe66 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C5=A0imon=20Brandner?= Date: Fri, 6 May 2022 21:32:41 +0200 Subject: [PATCH 12/38] Implement changes to MSC2285 (private read receipts) (#2221) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Add `ReceiptType` Signed-off-by: Å imon Brandner * Implement changes to MSC2285 Signed-off-by: Å imon Brandner * Improve tests Signed-off-by: Å imon Brandner * Apply suggestions from review Signed-off-by: Å imon Brandner * Update `getEventReadUpTo()` to handle private read receipts Signed-off-by: Å imon Brandner * Write tests for `getEventReadUpTo()` Signed-off-by: Å imon Brandner * Give `getReadReceiptForUserId()` a JSDOC Signed-off-by: Å imon Brandner * Types! Signed-off-by: Å imon Brandner * Try to use receipt `ts`s Signed-off-by: Å imon Brandner --- spec/unit/matrix-client.spec.ts | 41 +++++++++++++++++ spec/unit/room.spec.ts | 29 +++++++++++- spec/unit/sync-accumulator.spec.js | 15 ++++-- src/@types/read_receipts.ts | 21 +++++++++ src/client.ts | 73 +++++++++++++++--------------- src/models/room.ts | 53 ++++++++++++++++------ src/sync-accumulator.ts | 42 ++++++++++++----- 7 files changed, 208 insertions(+), 66 deletions(-) create mode 100644 src/@types/read_receipts.ts diff --git a/spec/unit/matrix-client.spec.ts b/spec/unit/matrix-client.spec.ts index a23d14ba648..24f9d55e348 100644 --- a/spec/unit/matrix-client.spec.ts +++ b/spec/unit/matrix-client.spec.ts @@ -29,6 +29,7 @@ import { import { MEGOLM_ALGORITHM } from "../../src/crypto/olmlib"; import { EventStatus, MatrixEvent } from "../../src/models/event"; import { Preset } from "../../src/@types/partials"; +import { ReceiptType } from "../../src/@types/read_receipts"; import * as testUtils from "../test-utils/test-utils"; import { makeBeaconInfoContent } from "../../src/content-helpers"; import { M_BEACON_INFO } from "../../src/@types/beacon"; @@ -992,6 +993,46 @@ describe("MatrixClient", function() { }); }); + describe("read-markers and read-receipts", () => { + it("setRoomReadMarkers", () => { + client.setRoomReadMarkersHttpRequest = jest.fn(); + const room = { + hasPendingEvent: jest.fn().mockReturnValue(false), + addLocalEchoReceipt: jest.fn(), + }; + const rrEvent = new MatrixEvent({ event_id: "read_event_id" }); + const rpEvent = new MatrixEvent({ event_id: "read_private_event_id" }); + client.getRoom = () => room; + + client.setRoomReadMarkers( + "room_id", + "read_marker_event_id", + rrEvent, + rpEvent, + ); + + expect(client.setRoomReadMarkersHttpRequest).toHaveBeenCalledWith( + "room_id", + "read_marker_event_id", + "read_event_id", + "read_private_event_id", + ); + expect(room.addLocalEchoReceipt).toHaveBeenCalledTimes(2); + expect(room.addLocalEchoReceipt).toHaveBeenNthCalledWith( + 1, + client.credentials.userId, + rrEvent, + ReceiptType.Read, + ); + expect(room.addLocalEchoReceipt).toHaveBeenNthCalledWith( + 2, + client.credentials.userId, + rpEvent, + ReceiptType.ReadPrivate, + ); + }); + }); + describe("beacons", () => { const roomId = '!room:server.org'; const content = makeBeaconInfoContent(100, true); diff --git a/spec/unit/room.spec.ts b/spec/unit/room.spec.ts index abf839a15a0..a33fccfebe2 100644 --- a/spec/unit/room.spec.ts +++ b/spec/unit/room.spec.ts @@ -23,6 +23,7 @@ import * as utils from "../test-utils/test-utils"; import { DuplicateStrategy, EventStatus, + EventTimelineSet, EventType, JoinRule, MatrixEvent, @@ -31,11 +32,12 @@ import { RoomEvent, } from "../../src"; import { EventTimeline } from "../../src/models/event-timeline"; -import { Room } from "../../src/models/room"; +import { IWrappedReceipt, Room } from "../../src/models/room"; import { RoomState } from "../../src/models/room-state"; import { UNSTABLE_ELEMENT_FUNCTIONAL_USERS } from "../../src/@types/event"; import { TestClient } from "../TestClient"; import { emitPromise } from "../test-utils/test-utils"; +import { ReceiptType } from "../../src/@types/read_receipts"; import { Thread, ThreadEvent } from "../../src/models/thread"; describe("Room", function() { @@ -2286,4 +2288,29 @@ describe("Room", function() { expect(responseRelations[0][1].has(threadReaction)).toBeTruthy(); }); }); + + describe("getEventReadUpTo()", () => { + const client = new TestClient(userA).client; + const room = new Room(roomId, client, userA); + + it("handles missing receipt type", () => { + room.getReadReceiptForUserId = (userId, ignore, receiptType) => { + return receiptType === ReceiptType.ReadPrivate ? { eventId: "eventId" } as IWrappedReceipt : null; + }; + + expect(room.getEventReadUpTo(userA)).toEqual("eventId"); + }); + + it("prefers older receipt", () => { + room.getReadReceiptForUserId = (userId, ignore, receiptType) => { + return (receiptType === ReceiptType.Read + ? { eventId: "eventId1" } + : { eventId: "eventId2" } + ) as IWrappedReceipt; + }; + room.getUnfilteredTimelineSet = () => ({ compareEventOrdering: (event1, event2) => 1 } as EventTimelineSet); + + expect(room.getEventReadUpTo(userA)).toEqual("eventId1"); + }); + }); }); diff --git a/spec/unit/sync-accumulator.spec.js b/spec/unit/sync-accumulator.spec.js index b089e0cebc1..5fe9a3611b0 100644 --- a/spec/unit/sync-accumulator.spec.js +++ b/spec/unit/sync-accumulator.spec.js @@ -15,6 +15,7 @@ See the License for the specific language governing permissions and limitations under the License. */ +import { ReceiptType } from "../../src/@types/read_receipts"; import { SyncAccumulator } from "../../src/sync-accumulator"; // The event body & unsigned object get frozen to assert that they don't get altered @@ -294,10 +295,13 @@ describe("SyncAccumulator", function() { room_id: "!foo:bar", content: { "$event1:localhost": { - "m.read": { + [ReceiptType.Read]: { "@alice:localhost": { ts: 1 }, "@bob:localhost": { ts: 2 }, }, + [ReceiptType.ReadPrivate]: { + "@dan:localhost": { ts: 4 }, + }, "some.other.receipt.type": { "@should_be_ignored:localhost": { key: "val" }, }, @@ -309,7 +313,7 @@ describe("SyncAccumulator", function() { room_id: "!foo:bar", content: { "$event2:localhost": { - "m.read": { + [ReceiptType.Read]: { "@bob:localhost": { ts: 2 }, // clobbers event1 receipt "@charlie:localhost": { ts: 3 }, }, @@ -337,12 +341,15 @@ describe("SyncAccumulator", function() { room_id: "!foo:bar", content: { "$event1:localhost": { - "m.read": { + [ReceiptType.Read]: { "@alice:localhost": { ts: 1 }, }, + [ReceiptType.ReadPrivate]: { + "@dan:localhost": { ts: 4 }, + }, }, "$event2:localhost": { - "m.read": { + [ReceiptType.Read]: { "@bob:localhost": { ts: 2 }, "@charlie:localhost": { ts: 3 }, }, diff --git a/src/@types/read_receipts.ts b/src/@types/read_receipts.ts new file mode 100644 index 00000000000..7a3ba268446 --- /dev/null +++ b/src/@types/read_receipts.ts @@ -0,0 +1,21 @@ +/* +Copyright 2022 Å imon Brandner + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +export enum ReceiptType { + Read = "m.read", + FullyRead = "m.fully_read", + ReadPrivate = "org.matrix.msc2285.read.private" +} diff --git a/src/client.ts b/src/client.ts index 711bf3e4e5e..78249b12140 100644 --- a/src/client.ts +++ b/src/client.ts @@ -181,6 +181,7 @@ import { CryptoStore } from "./crypto/store/base"; import { MediaHandler } from "./webrtc/mediaHandler"; import { IRefreshTokenResponse } from "./@types/auth"; import { TypedEventEmitter } from "./models/typed-event-emitter"; +import { ReceiptType } from "./@types/read_receipts"; import { Thread, THREAD_RELATION_TYPE } from "./models/thread"; import { MBeaconInfoEventContent, M_BEACON_INFO } from "./@types/beacon"; @@ -1078,7 +1079,13 @@ export class MatrixClient extends TypedEventEmitter { - return Object.keys(content[eid]['m.read']).includes(this.getUserId()); + const read = content[eid][ReceiptType.Read]; + if (read && Object.keys(read).includes(this.getUserId())) return true; + + const readPrivate = content[eid][ReceiptType.ReadPrivate]; + if (readPrivate && Object.keys(readPrivate).includes(this.getUserId())) return true; + + return false; }).length > 0; if (!isSelf) return; @@ -4491,13 +4498,14 @@ export class MatrixClient extends TypedEventEmitter { + public sendReceipt(event: MatrixEvent, receiptType: ReceiptType, body: any, callback?: Callback): Promise<{}> { if (typeof (body) === 'function') { callback = body as any as Callback; // legacy body = {}; @@ -4524,32 +4532,19 @@ export class MatrixClient extends TypedEventEmitterThis - * property is unstable and may change in the future. + * @param {ReceiptType} receiptType other than ReceiptType.Read are experimental! Optional. * @param {module:client.callback} callback Optional. * @return {Promise} Resolves: to an empty object * @return {module:http-api.MatrixError} Rejects: with an error response. */ - public async sendReadReceipt(event: MatrixEvent, opts?: { hidden?: boolean }, callback?: Callback): Promise<{}> { - if (typeof (opts) === 'function') { - callback = opts as any as Callback; // legacy - opts = {}; - } - if (!opts) opts = {}; - + public async sendReadReceipt(event: MatrixEvent, receiptType = ReceiptType.Read, callback?: Callback): Promise<{}> { const eventId = event.getId(); const room = this.getRoom(event.getRoomId()); if (room && room.hasPendingEvent(eventId)) { throw new Error(`Cannot set read receipt to a pending event (${eventId})`); } - const addlContent = { - "org.matrix.msc2285.hidden": Boolean(opts.hidden), - }; - - return this.sendReceipt(event, "m.read", addlContent, callback); + return this.sendReceipt(event, receiptType, {}, callback); } /** @@ -4562,16 +4557,15 @@ export class MatrixClient extends TypedEventEmitterThis property is unstable and may change in the future. + * @param {MatrixEvent} rpEvent the m.read.private read receipt event for when we don't + * want other users to see the read receipts. This is experimental. Optional. * @return {Promise} Resolves: the empty object, {}. */ public async setRoomReadMarkers( roomId: string, rmEventId: string, - rrEvent: MatrixEvent, - opts: { hidden?: boolean }, + rrEvent?: MatrixEvent, + rpEvent?: MatrixEvent, ): Promise<{}> { const room = this.getRoom(roomId); if (room && room.hasPendingEvent(rmEventId)) { @@ -4579,18 +4573,26 @@ export class MatrixClient extends TypedEventEmitterThis - * property is currently unstable and may change in the future. + * @param {string} rpEventId rpEvent the m.read.private read receipt event for when we + * don't want other users to see the read receipts. This is experimental. Optional. * @return {Promise} Resolves: the empty object, {}. */ public setRoomReadMarkersHttpRequest( roomId: string, rmEventId: string, rrEventId: string, - opts: { hidden?: boolean }, + rpEventId: string, ): Promise<{}> { const path = utils.encodeUri("/rooms/$roomId/read_markers", { $roomId: roomId, }); const content = { - "m.fully_read": rmEventId, - "m.read": rrEventId, - "org.matrix.msc2285.hidden": Boolean(opts ? opts.hidden : false), + [ReceiptType.FullyRead]: rmEventId, + [ReceiptType.Read]: rrEventId, + [ReceiptType.ReadPrivate]: rpEventId, }; return this.http.authedRequest(undefined, Method.Post, path, undefined, content); diff --git a/src/models/room.ts b/src/models/room.ts index be185255397..2d2124657b8 100644 --- a/src/models/room.ts +++ b/src/models/room.ts @@ -47,6 +47,7 @@ import { ThreadFilterType, } from "./thread"; import { TypedEventEmitter } from "./typed-event-emitter"; +import { ReceiptType } from "../@types/read_receipts"; import { IStateEventWithRoomId } from "../@types/search"; // These constants are used as sane defaults when the homeserver doesn't support @@ -58,7 +59,7 @@ import { IStateEventWithRoomId } from "../@types/search"; const KNOWN_SAFE_ROOM_VERSION = '9'; const SAFE_ROOM_VERSIONS = ['1', '2', '3', '4', '5', '6', '7', '8', '9']; -function synthesizeReceipt(userId: string, event: MatrixEvent, receiptType: string): MatrixEvent { +function synthesizeReceipt(userId: string, event: MatrixEvent, receiptType: ReceiptType): MatrixEvent { // console.log("synthesizing receipt for "+event.getId()); return new MatrixEvent({ content: { @@ -93,13 +94,13 @@ interface IReceipt { ts: number; } -interface IWrappedReceipt { +export interface IWrappedReceipt { eventId: string; data: IReceipt; } interface ICachedReceipt { - type: string; + type: ReceiptType; userId: string; data: IReceipt; } @@ -108,7 +109,7 @@ type ReceiptCache = {[eventId: string]: ICachedReceipt[]}; interface IReceiptContent { [eventId: string]: { - [type: string]: { + [key in ReceiptType]: { [userId: string]: IReceipt; }; }; @@ -1792,7 +1793,7 @@ export class Room extends TypedEventEmitter // Don't synthesize RR for m.room.redaction as this causes the RR to go missing. if (event.sender && event.getType() !== EventType.RoomRedaction) { this.addReceipt(synthesizeReceipt( - event.sender.userId, event, "m.read", + event.sender.userId, event, ReceiptType.Read, ), true); // Any live events from a user could be taken as implicit @@ -2314,14 +2315,23 @@ export class Room extends TypedEventEmitter */ public getUsersReadUpTo(event: MatrixEvent): string[] { return this.getReceiptsForEvent(event).filter(function(receipt) { - return receipt.type === "m.read"; + return [ReceiptType.Read, ReceiptType.ReadPrivate].includes(receipt.type); }).map(function(receipt) { return receipt.userId; }); } - public getReadReceiptForUserId(userId: string, ignoreSynthesized = false): IWrappedReceipt | null { - const [realReceipt, syntheticReceipt] = this.receipts["m.read"]?.[userId] ?? []; + /** + * Gets the latest receipt for a given user in the room + * @param userId The id of the user for which we want the receipt + * @param ignoreSynthesized Whether to ignore synthesized receipts or not + * @param receiptType Optional. The type of the receipt we want to get + * @returns the latest receipts of the chosen type for the chosen user + */ + public getReadReceiptForUserId( + userId: string, ignoreSynthesized = false, receiptType = ReceiptType.Read, + ): IWrappedReceipt | null { + const [realReceipt, syntheticReceipt] = this.receipts[receiptType]?.[userId] ?? []; if (ignoreSynthesized) { return realReceipt; } @@ -2339,8 +2349,25 @@ export class Room extends TypedEventEmitter * @return {String} ID of the latest event that the given user has read, or null. */ public getEventReadUpTo(userId: string, ignoreSynthesized = false): string | null { - const readReceipt = this.getReadReceiptForUserId(userId, ignoreSynthesized); - return readReceipt?.eventId ?? null; + const timelineSet = this.getUnfilteredTimelineSet(); + const publicReadReceipt = this.getReadReceiptForUserId(userId, ignoreSynthesized, ReceiptType.Read); + const privateReadReceipt = this.getReadReceiptForUserId(userId, ignoreSynthesized, ReceiptType.ReadPrivate); + + // If we have both, compare them + let comparison: number | undefined; + if (publicReadReceipt?.eventId && privateReadReceipt?.eventId) { + comparison = timelineSet.compareEventOrdering(publicReadReceipt?.eventId, privateReadReceipt?.eventId); + } + + // If we didn't get a comparison try to compare the ts of the receipts + if (!comparison) comparison = publicReadReceipt?.data?.ts - privateReadReceipt?.data?.ts; + + // The public receipt is more likely to drift out of date so the private + // one has precedence + if (!comparison) return privateReadReceipt?.eventId ?? publicReadReceipt?.eventId ?? null; + + // If public read receipt is older, return the private one + return (comparison < 0) ? privateReadReceipt?.eventId : publicReadReceipt?.eventId; } /** @@ -2493,7 +2520,7 @@ export class Room extends TypedEventEmitter } this.receiptCacheByEventId[eventId].push({ userId: userId, - type: receiptType, + type: receiptType as ReceiptType, data: receipt, }); }); @@ -2506,9 +2533,9 @@ export class Room extends TypedEventEmitter * client the fact that we've sent one. * @param {string} userId The user ID if the receipt sender * @param {MatrixEvent} e The event that is to be acknowledged - * @param {string} receiptType The type of receipt + * @param {ReceiptType} receiptType The type of receipt */ - public addLocalEchoReceipt(userId: string, e: MatrixEvent, receiptType: string): void { + public addLocalEchoReceipt(userId: string, e: MatrixEvent, receiptType: ReceiptType): void { this.addReceipt(synthesizeReceipt(userId, e, receiptType), true); } diff --git a/src/sync-accumulator.ts b/src/sync-accumulator.ts index f50f80b566a..3f307a23355 100644 --- a/src/sync-accumulator.ts +++ b/src/sync-accumulator.ts @@ -24,6 +24,7 @@ import { deepCopy } from "./utils"; import { IContent, IUnsigned } from "./models/event"; import { IRoomSummary } from "./models/room-summary"; import { EventType } from "./@types/event"; +import { ReceiptType } from "./@types/read_receipts"; interface IOpts { maxTimelineEntries?: number; @@ -157,6 +158,7 @@ interface IRoom { _readReceipts: { [userId: string]: { data: IMinimalEvent; + type: ReceiptType; eventId: string; }; }; @@ -416,16 +418,31 @@ export class SyncAccumulator { // of a hassle to work with. We'll inflate this back out when // getJSON() is called. Object.keys(e.content).forEach((eventId) => { - if (!e.content[eventId]["m.read"]) { + if (!e.content[eventId][ReceiptType.Read] && !e.content[eventId][ReceiptType.ReadPrivate]) { return; } - Object.keys(e.content[eventId]["m.read"]).forEach((userId) => { - // clobber on user ID - currentData._readReceipts[userId] = { - data: e.content[eventId]["m.read"][userId], - eventId: eventId, - }; - }); + const read = e.content[eventId][ReceiptType.Read]; + if (read) { + Object.keys(read).forEach((userId) => { + // clobber on user ID + currentData._readReceipts[userId] = { + data: e.content[eventId][ReceiptType.Read][userId], + type: ReceiptType.Read, + eventId: eventId, + }; + }); + } + const readPrivate = e.content[eventId][ReceiptType.ReadPrivate]; + if (readPrivate) { + Object.keys(readPrivate).forEach((userId) => { + // clobber on user ID + currentData._readReceipts[userId] = { + data: e.content[eventId][ReceiptType.ReadPrivate][userId], + type: ReceiptType.ReadPrivate, + eventId: eventId, + }; + }); + } }); }); } @@ -552,11 +569,12 @@ export class SyncAccumulator { Object.keys(roomData._readReceipts).forEach((userId) => { const receiptData = roomData._readReceipts[userId]; if (!receiptEvent.content[receiptData.eventId]) { - receiptEvent.content[receiptData.eventId] = { - "m.read": {}, - }; + receiptEvent.content[receiptData.eventId] = {}; + } + if (!receiptEvent.content[receiptData.eventId][receiptData.type]) { + receiptEvent.content[receiptData.eventId][receiptData.type] = {}; } - receiptEvent.content[receiptData.eventId]["m.read"][userId] = ( + receiptEvent.content[receiptData.eventId][receiptData.type][userId] = ( receiptData.data ); }); From 706b4d605481a66d02e24d15f34cd7e0dbebef4b Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Mon, 9 May 2022 11:58:52 +0100 Subject: [PATCH 13/38] Improve typing (#2352) * Fix typing of the store interface * Fix typed s'more * re-add check * Be less dumb * arg * Fix types --- src/@types/global.d.ts | 1 + src/client.ts | 4 ++-- src/crypto/DeviceList.ts | 2 +- src/crypto/OutgoingRoomKeyRequestManager.ts | 2 +- src/crypto/index.ts | 2 +- src/crypto/recoverykey.ts | 2 +- src/crypto/store/indexeddb-crypto-store-backend.ts | 2 +- src/crypto/verification/Base.ts | 2 +- src/crypto/verification/request/VerificationRequest.ts | 2 +- src/index.ts | 2 +- src/models/beacon.ts | 2 +- src/store/index.ts | 6 +++++- src/sync.ts | 4 ++-- src/utils.ts | 2 +- src/webrtc/call.ts | 8 ++++---- src/webrtc/callFeed.ts | 2 +- 16 files changed, 25 insertions(+), 20 deletions(-) diff --git a/src/@types/global.d.ts b/src/@types/global.d.ts index c7e65ff77d1..679a6afba6e 100644 --- a/src/@types/global.d.ts +++ b/src/@types/global.d.ts @@ -23,6 +23,7 @@ declare global { // use `number` as the return type in all cases for global.set{Interval,Timeout}, // so we don't accidentally use the methods on NodeJS.Timeout - they only exist in a subset of environments. // The overload for clear{Interval,Timeout} is resolved as expected. + // We use `ReturnType` in the code to be agnostic of if this definition gets loaded. function setInterval(handler: TimerHandler, timeout: number, ...arguments: any[]): number; function setTimeout(handler: TimerHandler, timeout: number, ...arguments: any[]): number; diff --git a/src/client.ts b/src/client.ts index 78249b12140..a705f5df5c4 100644 --- a/src/client.ts +++ b/src/client.ts @@ -913,7 +913,7 @@ export class MatrixClient extends TypedEventEmitter; protected syncedLeftRooms = false; protected clientOpts: IStoredClientOpts; - protected clientWellKnownIntervalID: number; + protected clientWellKnownIntervalID: ReturnType; protected canResetTimelineCallback: ResetTimelineCallback; // The pushprocessor caches useful things, so keep one and re-use it @@ -931,7 +931,7 @@ export class MatrixClient extends TypedEventEmitter; protected turnServers: ITurnServer[] = []; protected turnServersExpiry = 0; - protected checkTurnServersIntervalID: number; + protected checkTurnServersIntervalID: ReturnType; protected exportedOlmDeviceToImport: IOlmDevice; protected txnCtr = 0; protected mediaHandler = new MediaHandler(this); diff --git a/src/crypto/DeviceList.ts b/src/crypto/DeviceList.ts index 40c055c7b50..000e79f937f 100644 --- a/src/crypto/DeviceList.ts +++ b/src/crypto/DeviceList.ts @@ -95,7 +95,7 @@ export class DeviceList extends TypedEventEmitter = null; // True if we have fetched data from the server or loaded a non-empty // set of device data from the store private hasFetched: boolean = null; diff --git a/src/crypto/OutgoingRoomKeyRequestManager.ts b/src/crypto/OutgoingRoomKeyRequestManager.ts index 83229411027..013a6d08e68 100644 --- a/src/crypto/OutgoingRoomKeyRequestManager.ts +++ b/src/crypto/OutgoingRoomKeyRequestManager.ts @@ -78,7 +78,7 @@ export enum RoomKeyRequestState { export class OutgoingRoomKeyRequestManager { // handle for the delayed call to sendOutgoingRoomKeyRequests. Non-null // if the callback has been set, or if it is still running. - private sendOutgoingRoomKeyRequestsTimer: number = null; + private sendOutgoingRoomKeyRequestsTimer: ReturnType = null; // sanity check to ensure that we don't end up with two concurrent runs // of sendOutgoingRoomKeyRequests diff --git a/src/crypto/index.ts b/src/crypto/index.ts index 0842dda530c..df18d83a0ff 100644 --- a/src/crypto/index.ts +++ b/src/crypto/index.ts @@ -309,7 +309,7 @@ export class Crypto extends TypedEventEmitter; /** * Cryptography bits diff --git a/src/crypto/recoverykey.ts b/src/crypto/recoverykey.ts index 5c54e60852a..124f6c77b4c 100644 --- a/src/crypto/recoverykey.ts +++ b/src/crypto/recoverykey.ts @@ -14,7 +14,7 @@ See the License for the specific language governing permissions and limitations under the License. */ -import bs58 from 'bs58'; +import * as bs58 from 'bs58'; // picked arbitrarily but to try & avoid clashing with any bitcoin ones // (which are also base58 encoded, but bitcoin's involve a lot more hashing) diff --git a/src/crypto/store/indexeddb-crypto-store-backend.ts b/src/crypto/store/indexeddb-crypto-store-backend.ts index 8e311a1a2b9..6666fcf0165 100644 --- a/src/crypto/store/indexeddb-crypto-store-backend.ts +++ b/src/crypto/store/indexeddb-crypto-store-backend.ts @@ -873,7 +873,7 @@ export class Backend implements CryptoStore { public doTxn( mode: Mode, - stores: Iterable, + stores: string | string[], func: (txn: IDBTransaction) => T, log: PrefixedLogger = logger, ): Promise { diff --git a/src/crypto/verification/Base.ts b/src/crypto/verification/Base.ts index 68e9c96fc0a..35100499084 100644 --- a/src/crypto/verification/Base.ts +++ b/src/crypto/verification/Base.ts @@ -55,7 +55,7 @@ export class VerificationBase< private cancelled = false; private _done = false; private promise: Promise = null; - private transactionTimeoutTimer: number = null; + private transactionTimeoutTimer: ReturnType = null; protected expectedEvent: string; private resolve: () => void; private reject: (e: Error | MatrixEvent) => void; diff --git a/src/crypto/verification/request/VerificationRequest.ts b/src/crypto/verification/request/VerificationRequest.ts index 8af56f354d5..e8eb5b8d366 100644 --- a/src/crypto/verification/request/VerificationRequest.ts +++ b/src/crypto/verification/request/VerificationRequest.ts @@ -95,7 +95,7 @@ export class VerificationRequest< private eventsByUs = new Map(); private eventsByThem = new Map(); private _observeOnly = false; - private timeoutTimer: number = null; + private timeoutTimer: ReturnType = null; private _accepting = false; private _declining = false; private verifierHasFinished = false; diff --git a/src/index.ts b/src/index.ts index faab0fed08b..c651438fb75 100644 --- a/src/index.ts +++ b/src/index.ts @@ -14,7 +14,7 @@ See the License for the specific language governing permissions and limitations under the License. */ -import request from "request"; +import * as request from "request"; import * as matrixcs from "./matrix"; import * as utils from "./utils"; diff --git a/src/models/beacon.ts b/src/models/beacon.ts index caea773275d..a4f7694588b 100644 --- a/src/models/beacon.ts +++ b/src/models/beacon.ts @@ -54,7 +54,7 @@ export class Beacon extends TypedEventEmitter; private _latestLocationState: BeaconLocationState | undefined; constructor( diff --git a/src/store/index.ts b/src/store/index.ts index c47bd20ad48..f71f7c093a5 100644 --- a/src/store/index.ts +++ b/src/store/index.ts @@ -37,6 +37,10 @@ export interface ISavedSync { export interface IStore { readonly accountData: Record; // type : content + // XXX: The indexeddb store exposes a non-standard emitter for the "degraded" event + // for when it falls back to being a memory store due to errors. + on?: (event: string, handler: (...args: any[]) => void) => void; + /** @return {Promise} whether or not the database was newly created in this session. */ isNewlyCreated(): Promise; @@ -105,7 +109,7 @@ export interface IStore { /** * No-op. * @param {Room} room - * @param {integer} limit + * @param {number} limit * @return {Array} */ scrollback(room: Room, limit: number): MatrixEvent[]; diff --git a/src/sync.ts b/src/sync.ts index 0791920a9ff..d3aec0d5c00 100644 --- a/src/sync.ts +++ b/src/sync.ts @@ -152,7 +152,7 @@ export class SyncApi { private syncStateData: ISyncStateData = null; // additional data (eg. error object for failed sync) private catchingUp = false; private running = false; - private keepAliveTimer: number = null; + private keepAliveTimer: ReturnType = null; private connectionReturnedDefer: IDeferred = null; private notifEvents: MatrixEvent[] = []; // accumulator of sync events in the current sync response private failedSyncCount = 0; // Number of consecutive failed /sync requests @@ -1390,7 +1390,7 @@ export class SyncApi { * Starts polling the connectivity check endpoint * @param {number} delay How long to delay until the first poll. * defaults to a short, randomised interval (to prevent - * tightlooping if /versions succeeds but /sync etc. fail). + * tight-looping if /versions succeeds but /sync etc. fail). * @return {promise} which resolves once the connection returns */ private startKeepAlives(delay?: number): Promise { diff --git a/src/utils.ts b/src/utils.ts index 77753128611..4885fb94861 100644 --- a/src/utils.ts +++ b/src/utils.ts @@ -23,7 +23,7 @@ limitations under the License. import unhomoglyph from "unhomoglyph"; import promiseRetry from "p-retry"; -import type NodeCrypto from "crypto"; +import type * as NodeCrypto from "crypto"; import { MatrixEvent } from "."; import { M_TIMESTAMP } from "./@types/location"; diff --git a/src/webrtc/call.ts b/src/webrtc/call.ts index dcc1016a69a..d6a574713ac 100644 --- a/src/webrtc/call.ts +++ b/src/webrtc/call.ts @@ -298,7 +298,7 @@ export class MatrixCall extends TypedEventEmitter; // The logic of when & if a call is on hold is nontrivial and explained in is*OnHold // This flag represents whether we want the other party to be on hold @@ -322,7 +322,7 @@ export class MatrixCall extends TypedEventEmitter; private callLength = 0; constructor(opts: CallOpts) { @@ -708,9 +708,9 @@ export class MatrixCall extends TypedEventEmitter { stats.push(item[1]); - } + }); return stats; } diff --git a/src/webrtc/callFeed.ts b/src/webrtc/callFeed.ts index 8f61afaa5d0..fbe308e5378 100644 --- a/src/webrtc/callFeed.ts +++ b/src/webrtc/callFeed.ts @@ -69,7 +69,7 @@ export class CallFeed extends TypedEventEmitter private frequencyBinCount: Float32Array; private speakingThreshold = SPEAKING_THRESHOLD; private speaking = false; - private volumeLooperTimeout: number; + private volumeLooperTimeout: ReturnType; constructor(opts: ICallFeedOpts) { super(); From 62d77231afd4ec404621ac09557570d2dcff8d6b Mon Sep 17 00:00:00 2001 From: Travis Ralston Date: Mon, 9 May 2022 16:11:04 -0600 Subject: [PATCH 14/38] Remove spec v1.3 check for threads (#2354) * Remove spec v1.3 check for threads Citation: https://matrix.to/#/!ewdjhNcPcEmYNKzlWp:t2l.io/$CkPuvKdFZyFL547JCy5J3MfvLaWUo_a1XEdmiop1PKc?via=matrix.org&via=element.io&via=envs.net * Enable stable support always for threads * Fix tests differently --- spec/unit/matrix-client.spec.ts | 7 ++++++- src/client.ts | 9 +++++++-- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/spec/unit/matrix-client.spec.ts b/spec/unit/matrix-client.spec.ts index 24f9d55e348..d1562d766cc 100644 --- a/spec/unit/matrix-client.spec.ts +++ b/spec/unit/matrix-client.spec.ts @@ -91,7 +91,12 @@ describe("MatrixClient", function() { let pendingLookup = null; function httpReq(cb, method, path, qp, data, prefix) { if (path === KEEP_ALIVE_PATH && acceptKeepalives) { - return Promise.resolve(); + return Promise.resolve({ + unstable_features: { + "org.matrix.msc3440.stable": true, + }, + versions: ["r0.6.0", "r0.6.1"], + }); } const next = httpLookups.shift(); const logLine = ( diff --git a/src/client.ts b/src/client.ts index a705f5df5c4..ecec0ead1aa 100644 --- a/src/client.ts +++ b/src/client.ts @@ -1171,6 +1171,8 @@ export class MatrixClient extends TypedEventEmitter { try { const hasUnstableSupport = await this.doesServerSupportUnstableFeature("org.matrix.msc3440"); - const hasStableSupport = await this.doesServerSupportUnstableFeature("org.matrix.msc3440.stable") - || await this.isVersionSupported("v1.3"); + const hasStableSupport = await this.doesServerSupportUnstableFeature("org.matrix.msc3440.stable"); + + // TODO: Use `this.isVersionSupported("v1.3")` for whatever spec version includes MSC3440 formally. return { serverSupport: hasUnstableSupport || hasStableSupport, stable: hasStableSupport, }; } catch (e) { + // Assume server support and stability aren't available: null/no data return. + // XXX: This should just return an object with `false` booleans instead. return null; } } From 03a79dc6dd631caa2655bf02290ad3a58424f0c2 Mon Sep 17 00:00:00 2001 From: RiotRobot Date: Tue, 10 May 2022 14:50:07 +0100 Subject: [PATCH 15/38] Resetting package fields for development --- package.json | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/package.json b/package.json index 495405d76cd..b4e6763d4cc 100644 --- a/package.json +++ b/package.json @@ -32,7 +32,7 @@ "keywords": [ "matrix-org" ], - "main": "./lib/index.js", + "main": "./src/index.ts", "browser": "./lib/browser-index.js", "matrix_src_main": "./src/index.ts", "matrix_src_browser": "./src/browser-index.js", @@ -125,6 +125,5 @@ "jestSonar": { "reportPath": "coverage", "sonar56x": true - }, - "typings": "./lib/index.d.ts" + } } From 685276f056bd376efa672db983e6c3c83c900515 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Tue, 10 May 2022 16:49:03 +0100 Subject: [PATCH 16/38] Pass more args to Sonar (#2356) * Pass projectVersion to Sonar * Fix s'more * Fix sonar.lang.patterns.ts --- .github/workflows/sonarqube.yml | 18 ++++++++++++++++-- sonar-project.properties | 2 ++ 2 files changed, 18 insertions(+), 2 deletions(-) diff --git a/.github/workflows/sonarqube.yml b/.github/workflows/sonarqube.yml index 7029be97f3b..ecf76be487a 100644 --- a/.github/workflows/sonarqube.yml +++ b/.github/workflows/sonarqube.yml @@ -10,9 +10,15 @@ jobs: runs-on: ubuntu-latest if: github.event.workflow_run.conclusion == 'success' steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 with: - fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis + ref: ${{ github.event.workflow_run.head_sha }} # checkout commit that triggered this workflow + fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis + + # fetch develop so that Sonar can identify new issues in PR builds + - name: Fetch develop + if: "github.event.workflow_run.head_branch != 'develop'" + run: git rev-parse HEAD && git fetch origin develop:develop && git status && git rev-parse HEAD # There's a 'download artifact' action, but it hasn't been updated for the workflow_run action # (https://github.com/actions/download-artifact/issues/60) so instead we get this mess: @@ -40,8 +46,16 @@ jobs: - name: Extract Coverage Report run: unzip -d coverage coverage.zip && rm coverage.zip + - name: Read version + id: version + uses: WyriHaximus/github-action-get-previous-tag@v1 + - name: SonarCloud Scan uses: SonarSource/sonarcloud-github-action@master + with: + args: > + -Dsonar.projectVersion=${{ steps.version.outputs.tag }} + -Dsonar.scm.revision=${{ github.event.workflow_run.head_sha }} env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Needed to get PR information, if any SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} diff --git a/sonar-project.properties b/sonar-project.properties index 20439adeb61..4f5b65e3811 100644 --- a/sonar-project.properties +++ b/sonar-project.properties @@ -12,3 +12,5 @@ sonar.typescript.tsconfigPath=./tsconfig.json sonar.javascript.lcov.reportPaths=coverage/lcov.info sonar.coverage.exclusions=spec/**/* sonar.testExecutionReportPaths=coverage/test-report.xml + +sonar.lang.patterns.ts=**/*.ts,**/*.tsx From 34cfa511049e513c3c3a0e939bfb481231c9cb9a Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Tue, 10 May 2022 17:11:07 +0100 Subject: [PATCH 17/38] Pass more args to Sonar (#2358) * Pass projectVersion to Sonar * Fix s'more * Fix sonar.lang.patterns.ts * Apply more tweaks Based on https://community.sonarsource.com/t/how-to-use-sonarcloud-with-a-forked-repository-on-github/7363/28 --- .github/workflows/sonarqube.yml | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/.github/workflows/sonarqube.yml b/.github/workflows/sonarqube.yml index ecf76be487a..61238ed1b48 100644 --- a/.github/workflows/sonarqube.yml +++ b/.github/workflows/sonarqube.yml @@ -12,7 +12,8 @@ jobs: steps: - uses: actions/checkout@v3 with: - ref: ${{ github.event.workflow_run.head_sha }} # checkout commit that triggered this workflow + repository: ${{ github.event.workflow_run.head_repository.full_name }} + ref: ${{ github.event.workflow_run.head_branch }} # checkout commit that triggered this workflow fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis # fetch develop so that Sonar can identify new issues in PR builds @@ -56,6 +57,9 @@ jobs: args: > -Dsonar.projectVersion=${{ steps.version.outputs.tag }} -Dsonar.scm.revision=${{ github.event.workflow_run.head_sha }} + -Dsonar.pullrequest.key=${{ github.event.workflow_run.pull_requests[0].number }} + -Dsonar.pullrequest.branch=${{ github.event.workflow_run.pull_requests[0].head.ref }} + -Dsonar.pullrequest.base=${{ github.event.workflow_run.pull_requests[0].base.ref }} env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Needed to get PR information, if any SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} From 49dd76b91e0a081a4ab3c7ab3ddc66bbf9fff1a2 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Wed, 11 May 2022 10:53:52 +0100 Subject: [PATCH 18/38] Remove redundant checkKey param on isSecretStored (#2360) --- src/client.ts | 9 +++------ src/crypto/CrossSigning.ts | 4 ++-- src/crypto/SecretStorage.ts | 3 +-- src/crypto/index.ts | 7 ++----- 4 files changed, 8 insertions(+), 15 deletions(-) diff --git a/src/client.ts b/src/client.ts index ecec0ead1aa..12e02a227f3 100644 --- a/src/client.ts +++ b/src/client.ts @@ -2388,18 +2388,15 @@ export class MatrixClient extends TypedEventEmitter | null> { + public isSecretStored(name: string): Promise | null> { if (!this.crypto) { throw new Error("End-to-end encryption disabled"); } - return this.crypto.isSecretStored(name, checkKey); + return this.crypto.isSecretStored(name); } /** @@ -2728,7 +2725,7 @@ export class MatrixClient extends TypedEventEmitter | null> { - return Promise.resolve(this.isSecretStored("m.megolm_backup.v1", false /* checkKey */)); + return Promise.resolve(this.isSecretStored("m.megolm_backup.v1")); } /** diff --git a/src/crypto/CrossSigning.ts b/src/crypto/CrossSigning.ts index 21dd0ee1623..4e5c9f452ec 100644 --- a/src/crypto/CrossSigning.ts +++ b/src/crypto/CrossSigning.ts @@ -171,7 +171,7 @@ export class CrossSigningInfo { */ public async isStoredInSecretStorage(secretStorage: SecretStorage): Promise> { // check what SSSS keys have encrypted the master key (if any) - const stored = await secretStorage.isStored("m.cross_signing.master", false) || {}; + const stored = await secretStorage.isStored("m.cross_signing.master") || {}; // then check which of those SSSS keys have also encrypted the SSK and USK function intersect(s: Record) { for (const k of Object.keys(stored)) { @@ -181,7 +181,7 @@ export class CrossSigningInfo { } } for (const type of ["self_signing", "user_signing"]) { - intersect(await secretStorage.isStored(`m.cross_signing.${type}`, false) || {}); + intersect(await secretStorage.isStored(`m.cross_signing.${type}`) || {}); } return Object.keys(stored).length ? stored : null; } diff --git a/src/crypto/SecretStorage.ts b/src/crypto/SecretStorage.ts index f36b66c921f..0eef2ee7d50 100644 --- a/src/crypto/SecretStorage.ts +++ b/src/crypto/SecretStorage.ts @@ -339,13 +339,12 @@ export class SecretStorage { * Check if a secret is stored on the server. * * @param {string} name the name of the secret - * @param {boolean} checkKey check if the secret is encrypted by a trusted key * * @return {object?} map of key name to key info the secret is encrypted * with, or null if it is not present or not encrypted with a trusted * key */ - public async isStored(name: string, checkKey = true): Promise | null> { + public async isStored(name: string): Promise | null> { // check if secret exists const secretInfo = await this.accountDataAdapter.getAccountDataFromServer(name); if (!secretInfo?.encrypted) return null; diff --git a/src/crypto/index.ts b/src/crypto/index.ts index df18d83a0ff..a8370238519 100644 --- a/src/crypto/index.ts +++ b/src/crypto/index.ts @@ -1076,11 +1076,8 @@ export class Crypto extends TypedEventEmitter | null> { - return this.secretStorage.isStored(name, checkKey); + public isSecretStored(name: string): Promise | null> { + return this.secretStorage.isStored(name); } public requestSecret(name: string, devices: string[]): ISecretRequest { From 923ff4b282b7c28060a6714cbbbb4d9ee3d72878 Mon Sep 17 00:00:00 2001 From: Janne Mareike Koschinski Date: Wed, 11 May 2022 13:17:36 +0200 Subject: [PATCH 19/38] registration: add function to re-request email token (#2357) --- spec/unit/interactive-auth.spec.js | 105 +++++++++++++++++++++++++++++ src/interactive-auth.ts | 51 ++++++++------ 2 files changed, 137 insertions(+), 19 deletions(-) diff --git a/spec/unit/interactive-auth.spec.js b/spec/unit/interactive-auth.spec.js index da2bf1917cb..6742d05909b 100644 --- a/spec/unit/interactive-auth.spec.js +++ b/spec/unit/interactive-auth.spec.js @@ -18,6 +18,8 @@ limitations under the License. import { logger } from "../../src/logger"; import { InteractiveAuth } from "../../src/interactive-auth"; import { MatrixError } from "../../src/http-api"; +import { sleep } from "../../src/utils"; +import { randomString } from "../../src/randomstring"; // Trivial client object to test interactive auth // (we do not need TestClient here) @@ -172,4 +174,107 @@ describe("InteractiveAuth", function() { expect(error.message).toBe('No appropriate authentication flow found'); }); }); + + describe("requestEmailToken", () => { + it("increases auth attempts", async () => { + const doRequest = jest.fn(); + const stateUpdated = jest.fn(); + const requestEmailToken = jest.fn(); + requestEmailToken.mockImplementation(async () => ({ sid: "" })); + + const ia = new InteractiveAuth({ + matrixClient: new FakeClient(), + doRequest, stateUpdated, requestEmailToken, + }); + + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 1, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 2, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 3, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 4, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 5, undefined); + }); + + it("increases auth attempts", async () => { + const doRequest = jest.fn(); + const stateUpdated = jest.fn(); + const requestEmailToken = jest.fn(); + requestEmailToken.mockImplementation(async () => ({ sid: "" })); + + const ia = new InteractiveAuth({ + matrixClient: new FakeClient(), + doRequest, stateUpdated, requestEmailToken, + }); + + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 1, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 2, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 3, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 4, undefined); + requestEmailToken.mockClear(); + await ia.requestEmailToken(); + expect(requestEmailToken).toHaveBeenLastCalledWith(undefined, ia.getClientSecret(), 5, undefined); + }); + + it("passes errors through", async () => { + const doRequest = jest.fn(); + const stateUpdated = jest.fn(); + const requestEmailToken = jest.fn(); + requestEmailToken.mockImplementation(async () => { + throw new Error("unspecific network error"); + }); + + const ia = new InteractiveAuth({ + matrixClient: new FakeClient(), + doRequest, stateUpdated, requestEmailToken, + }); + + expect(async () => await ia.requestEmailToken()).rejects.toThrowError("unspecific network error"); + }); + + it("only starts one request at a time", async () => { + const doRequest = jest.fn(); + const stateUpdated = jest.fn(); + const requestEmailToken = jest.fn(); + requestEmailToken.mockImplementation(() => sleep(500, { sid: "" })); + + const ia = new InteractiveAuth({ + matrixClient: new FakeClient(), + doRequest, stateUpdated, requestEmailToken, + }); + + await Promise.all([ia.requestEmailToken(), ia.requestEmailToken(), ia.requestEmailToken()]); + expect(requestEmailToken).toHaveBeenCalledTimes(1); + }); + + it("stores result in email sid", async () => { + const doRequest = jest.fn(); + const stateUpdated = jest.fn(); + const requestEmailToken = jest.fn(); + const sid = randomString(24); + requestEmailToken.mockImplementation(() => sleep(500, { sid })); + + const ia = new InteractiveAuth({ + matrixClient: new FakeClient(), + doRequest, stateUpdated, requestEmailToken, + }); + + await ia.requestEmailToken(); + expect(ia.getEmailSid()).toEqual(sid); + }); + }); }); diff --git a/src/interactive-auth.ts b/src/interactive-auth.ts index f06369fe736..2732023d44c 100644 --- a/src/interactive-auth.ts +++ b/src/interactive-auth.ts @@ -203,6 +203,8 @@ export class InteractiveAuth { private chosenFlow: IFlow = null; private currentStage: string = null; + private emailAttempt = 1; + // if we are currently trying to submit an auth dict (which includes polling) // the promise the will resolve/reject when it completes private submitPromise: Promise = null; @@ -408,6 +410,34 @@ export class InteractiveAuth { this.emailSid = sid; } + /** + * Requests a new email token and sets the email sid for the validation session + */ + public requestEmailToken = async () => { + if (!this.requestingEmailToken) { + logger.trace("Requesting email token. Attempt: " + this.emailAttempt); + // If we've picked a flow with email auth, we send the email + // now because we want the request to fail as soon as possible + // if the email address is not valid (ie. already taken or not + // registered, depending on what the operation is). + this.requestingEmailToken = true; + try { + const requestTokenResult = await this.requestEmailTokenCallback( + this.inputs.emailAddress, + this.clientSecret, + this.emailAttempt++, + this.data.session, + ); + this.emailSid = requestTokenResult.sid; + logger.trace("Email token request succeeded"); + } finally { + this.requestingEmailToken = false; + } + } else { + logger.warn("Could not request email token: Already requesting"); + } + }; + /** * Fire off a request, and either resolve the promise, or call * startAuthStage. @@ -458,24 +488,9 @@ export class InteractiveAuth { return; } - if ( - !this.emailSid && - !this.requestingEmailToken && - this.chosenFlow.stages.includes(AuthType.Email) - ) { - // If we've picked a flow with email auth, we send the email - // now because we want the request to fail as soon as possible - // if the email address is not valid (ie. already taken or not - // registered, depending on what the operation is). - this.requestingEmailToken = true; + if (!this.emailSid && this.chosenFlow.stages.includes(AuthType.Email)) { try { - const requestTokenResult = await this.requestEmailTokenCallback( - this.inputs.emailAddress, - this.clientSecret, - 1, // TODO: Multiple send attempts? - this.data.session, - ); - this.emailSid = requestTokenResult.sid; + await this.requestEmailToken(); // NB. promise is not resolved here - at some point, doRequest // will be called again and if the user has jumped through all // the hoops correctly, auth will be complete and the request @@ -491,8 +506,6 @@ export class InteractiveAuth { // send the email, for whatever reason. this.attemptAuthDeferred.reject(e); this.attemptAuthDeferred = null; - } finally { - this.requestingEmailToken = false; } } } From 67f5293d6c9c8a9eda37885a5569ed428aad44f3 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Wed, 11 May 2022 16:42:25 +0100 Subject: [PATCH 20/38] Tweaks for sonar to correctly report on forked PRs (#2359) --- .github/workflows/sonarqube.yml | 43 ++++++++++++++++++++++++++------- 1 file changed, 34 insertions(+), 9 deletions(-) diff --git a/.github/workflows/sonarqube.yml b/.github/workflows/sonarqube.yml index 61238ed1b48..acaf3d1bff3 100644 --- a/.github/workflows/sonarqube.yml +++ b/.github/workflows/sonarqube.yml @@ -10,20 +10,21 @@ jobs: runs-on: ubuntu-latest if: github.event.workflow_run.conclusion == 'success' steps: - - uses: actions/checkout@v3 + - name: "🧮 Checkout code" + uses: actions/checkout@v3 with: repository: ${{ github.event.workflow_run.head_repository.full_name }} ref: ${{ github.event.workflow_run.head_branch }} # checkout commit that triggered this workflow fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis # fetch develop so that Sonar can identify new issues in PR builds - - name: Fetch develop + - name: "📕 Fetch develop" if: "github.event.workflow_run.head_branch != 'develop'" run: git rev-parse HEAD && git fetch origin develop:develop && git status && git rev-parse HEAD # There's a 'download artifact' action, but it hasn't been updated for the workflow_run action # (https://github.com/actions/download-artifact/issues/60) so instead we get this mess: - - name: Download Coverage Report + - name: "đŸ“Ĩ Download Coverage Report" uses: actions/github-script@v3.1.0 with: script: | @@ -44,22 +45,46 @@ jobs: const fs = require('fs'); fs.writeFileSync('${{github.workspace}}/coverage.zip', Buffer.from(download.data)); - - name: Extract Coverage Report + - name: "🗃ī¸ Extract Coverage Report" run: unzip -d coverage coverage.zip && rm coverage.zip - - name: Read version + - name: "🔍 Read latest tag" id: version uses: WyriHaximus/github-action-get-previous-tag@v1 - - name: SonarCloud Scan + - name: "🔍 Read PR details" + id: prdetails + if: github.event.workflow_run.event == 'pull_request' + # We need to find the PR number that corresponds to the branch, which we do by searching the GH API + # The workflow_run event includes a list of pull requests, but it doesn't get populated for + # forked PRs: https://docs.github.com/en/rest/reference/checks#create-a-check-run + run: | + head_branch='${{github.event.workflow_run.head_repository.owner.login}}:${{github.event.workflow_run.head_branch}}' + echo "Head branch: $head_branch" + pulls_uri="https://api.github.com/repos/${{ github.repository }}/pulls?head=$(jq -Rr '@uri' <<<$head_branch)" + pr_data=$(curl -s -H 'Authorization: Bearer ${{ secrets.GITHUB_TOKEN }}' "$pulls_uri") + + pr_number=$(jq -r '.[] | .number' <<< "$pr_data") + echo "PR number: $pr_number" + echo "::set-output name=prnumber::$pr_number" + + head_ref=$(jq -r '.[] | .head.ref' <<< "$pr_data") + echo "Head ref: $head_ref" + echo "::set-output name=headref::$head_ref" + + base_ref=$(jq -r '.[] | .base.ref' <<< "$pr_data") + echo "Base ref: $base_ref" + echo "::set-output name=baseref::$base_ref" + + - name: "đŸŠģ SonarCloud Scan" uses: SonarSource/sonarcloud-github-action@master with: args: > -Dsonar.projectVersion=${{ steps.version.outputs.tag }} -Dsonar.scm.revision=${{ github.event.workflow_run.head_sha }} - -Dsonar.pullrequest.key=${{ github.event.workflow_run.pull_requests[0].number }} - -Dsonar.pullrequest.branch=${{ github.event.workflow_run.pull_requests[0].head.ref }} - -Dsonar.pullrequest.base=${{ github.event.workflow_run.pull_requests[0].base.ref }} + -Dsonar.pullrequest.key=${{ steps.prdetails.outputs.prnumber }} + -Dsonar.pullrequest.branch=${{ steps.prdetails.outputs.headref }} + -Dsonar.pullrequest.base=${{ steps.prdetails.outputs.baseref }} env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Needed to get PR information, if any SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} From 4d4d6e1411b6cf29b029f4f82cb67508404b8c36 Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Wed, 11 May 2022 17:04:10 +0100 Subject: [PATCH 21/38] NodeURL isn't needed as Node exports the standard URL c'tor as global (#2361) Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> --- src/autodiscovery.ts | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/src/autodiscovery.ts b/src/autodiscovery.ts index 5f875cc6815..58c4cb15736 100644 --- a/src/autodiscovery.ts +++ b/src/autodiscovery.ts @@ -17,8 +17,6 @@ limitations under the License. /** @module auto-discovery */ -import { URL as NodeURL } from "url"; - import { IClientWellKnown, IWellKnownConfig } from "./client"; import { logger } from './logger'; @@ -372,16 +370,11 @@ export class AutoDiscovery { if (!url) return false; try { - // We have to try and parse the URL using the NodeJS URL - // library if we're on NodeJS and use the browser's URL - // library when we're in a browser. To accomplish this, we - // try the NodeJS version first and fall back to the browser. let parsed = null; try { - if (NodeURL) parsed = new NodeURL(url); - else parsed = new URL(url); - } catch (e) { parsed = new URL(url); + } catch (e) { + logger.error("Could not parse url", e); } if (!parsed || !parsed.hostname) return false; From 4721aa1d241a46601601259ec7ca6db9ff1bb5fb Mon Sep 17 00:00:00 2001 From: Michael Telatynski <7t3chguy@gmail.com> Date: Thu, 12 May 2022 10:12:39 +0100 Subject: [PATCH 22/38] Fix up more types & Sonar warnings (#2363) * Fix up more types & Sonar warnings * Fix test * Add first test for callEventHandler --- .../matrix-client-event-timeline.spec.js | 7 ++- spec/unit/webrtc/callEventHandler.spec.ts | 54 +++++++++++++++++++ src/@types/requests.ts | 37 ++++++++++++- src/client.ts | 23 ++++---- src/crypto/DeviceList.ts | 2 +- src/crypto/index.ts | 6 +-- src/models/event.ts | 6 +-- src/sync-accumulator.ts | 1 - src/sync.ts | 8 +-- src/webrtc/callEventHandler.ts | 12 ++--- 10 files changed, 119 insertions(+), 37 deletions(-) create mode 100644 spec/unit/webrtc/callEventHandler.spec.ts diff --git a/spec/integ/matrix-client-event-timeline.spec.js b/spec/integ/matrix-client-event-timeline.spec.js index 6e93a063a8d..6df4a9a813c 100644 --- a/spec/integ/matrix-client-event-timeline.spec.js +++ b/spec/integ/matrix-client-event-timeline.spec.js @@ -526,8 +526,7 @@ describe("MatrixClient event timelines", function() { return { original_event: THREAD_ROOT, chunk: [THREAD_REPLY], - next_batch: "next_batch_token0", - prev_batch: "prev_batch_token0", + // no next batch as this is the oldest end of the timeline }; }); @@ -536,8 +535,8 @@ describe("MatrixClient event timelines", function() { const timeline = await timelinePromise; - expect(timeline.getEvents().find(e => e.getId() === THREAD_ROOT.event_id)); - expect(timeline.getEvents().find(e => e.getId() === THREAD_REPLY.event_id)); + expect(timeline.getEvents().find(e => e.getId() === THREAD_ROOT.event_id)).toBeTruthy(); + expect(timeline.getEvents().find(e => e.getId() === THREAD_REPLY.event_id)).toBeTruthy(); }); }); diff --git a/spec/unit/webrtc/callEventHandler.spec.ts b/spec/unit/webrtc/callEventHandler.spec.ts new file mode 100644 index 00000000000..d60ae299791 --- /dev/null +++ b/spec/unit/webrtc/callEventHandler.spec.ts @@ -0,0 +1,54 @@ +/* +Copyright 2022 The Matrix.org Foundation C.I.C. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +import { TestClient } from '../../TestClient'; +import { ClientEvent, EventType, MatrixEvent, RoomEvent } from "../../../src"; +import { CallEventHandler, CallEventHandlerEvent } from "../../../src/webrtc/callEventHandler"; +import { SyncState } from "../../../src/sync"; + +describe("callEventHandler", () => { + it("should ignore a call if invite & hangup come within a single sync", () => { + const testClient = new TestClient(); + const client = testClient.client; + client.callEventHandler = new CallEventHandler(client); + client.callEventHandler.start(); + + // Fire off call invite then hangup within a single sync + const callInvite = new MatrixEvent({ + type: EventType.CallInvite, + content: { + call_id: "123", + }, + }); + client.emit(RoomEvent.Timeline, callInvite); + + const callHangup = new MatrixEvent({ + type: EventType.CallHangup, + content: { + call_id: "123", + }, + }); + client.emit(RoomEvent.Timeline, callHangup); + + const incomingCallEmitted = jest.fn(); + client.on(CallEventHandlerEvent.Incoming, incomingCallEmitted); + + client.getSyncState = jest.fn().mockReturnValue(SyncState.Syncing); + client.emit(ClientEvent.Sync); + + expect(incomingCallEmitted).not.toHaveBeenCalled(); + }); +}); diff --git a/src/@types/requests.ts b/src/@types/requests.ts index a3c950ab135..f3ff33e4aec 100644 --- a/src/@types/requests.ts +++ b/src/@types/requests.ts @@ -17,9 +17,11 @@ limitations under the License. import { Callback } from "../client"; import { IContent, IEvent } from "../models/event"; import { Preset, Visibility } from "./partials"; -import { SearchKey } from "./search"; +import { IEventWithRoomId, SearchKey } from "./search"; import { IRoomEventFilter } from "../filter"; import { Direction } from "../models/event-timeline"; +import { PushRuleAction } from "./PushRules"; +import { IRoomEvent } from "../sync-accumulator"; // allow camelcase as these are things that go onto the wire /* eslint-disable camelcase */ @@ -155,4 +157,37 @@ export interface IRelationsResponse { prev_batch?: string; } +export interface IContextResponse { + end: string; + start: string; + state: IEventWithRoomId[]; + events_before: IEventWithRoomId[]; + events_after: IEventWithRoomId[]; + event: IEventWithRoomId; +} + +export interface IEventsResponse { + chunk: IEventWithRoomId[]; + end: string; + start: string; +} + +export interface INotification { + actions: PushRuleAction[]; + event: IRoomEvent; + profile_tag?: string; + read: boolean; + room_id: string; + ts: number; +} + +export interface INotificationsResponse { + next_token: string; + notifications: INotification[]; +} + +export interface IFilterResponse { + filter_id: string; +} + /* eslint-enable camelcase */ diff --git a/src/client.ts b/src/client.ts index 12e02a227f3..386152f92e2 100644 --- a/src/client.ts +++ b/src/client.ts @@ -113,6 +113,8 @@ import { RoomMemberEventHandlerMap, RoomStateEvent, RoomStateEventHandlerMap, + INotificationsResponse, + IFilterResponse, } from "./matrix"; import { CrossSigningKey, @@ -132,6 +134,7 @@ import { Room } from "./models/room"; import { IAddThreePidOnlyBody, IBindThreePidBody, + IContextResponse, ICreateRoomOpts, IEventSearchOpts, IGuestAccessOpts, @@ -5245,7 +5248,7 @@ export class MatrixClient extends TypedEventEmitter(undefined, Method.Get, path, params); // TODO types + const res = await this.http.authedRequest(undefined, Method.Get, path, params); if (!res.event) { throw new Error("'event' not in '/context' result - homeserver too old?"); } @@ -5424,7 +5427,7 @@ export class MatrixClient extends TypedEventEmitter( // TODO types + promise = this.http.authedRequest( undefined, Method.Get, path, params, undefined, ).then(async (res) => { const token = res.next_token; @@ -6101,15 +6104,13 @@ export class MatrixClient extends TypedEventEmitter(undefined, Method.Post, path, undefined, content).then((response) => { - // persist the filter - const filter = Filter.fromJson( - this.credentials.userId, response.filter_id, content, - ); - this.store.storeFilter(filter); - return filter; - }); + return this.http.authedRequest(undefined, Method.Post, path, undefined, content) + .then((response) => { + // persist the filter + const filter = Filter.fromJson(this.credentials.userId, response.filter_id, content); + this.store.storeFilter(filter); + return filter; + }); } /** diff --git a/src/crypto/DeviceList.ts b/src/crypto/DeviceList.ts index 000e79f937f..c203ce5dae6 100644 --- a/src/crypto/DeviceList.ts +++ b/src/crypto/DeviceList.ts @@ -942,7 +942,7 @@ async function updateStoredDeviceKeysForUser( async function storeDeviceKeys( olmDevice: OlmDevice, userStore: Record, - deviceResult: any, // TODO types + deviceResult: IDownloadKeyResult["device_keys"]["user_id"]["device_id"], ): Promise { if (!deviceResult.keys) { // no keys? diff --git a/src/crypto/index.ts b/src/crypto/index.ts index a8370238519..474bfd3f636 100644 --- a/src/crypto/index.ts +++ b/src/crypto/index.ts @@ -58,7 +58,7 @@ import { keyFromPassphrase } from './key_passphrase'; import { decodeRecoveryKey, encodeRecoveryKey } from './recoverykey'; import { VerificationRequest } from "./verification/request/VerificationRequest"; import { InRoomChannel, InRoomRequests } from "./verification/request/InRoomChannel"; -import { ToDeviceChannel, ToDeviceRequests } from "./verification/request/ToDeviceChannel"; +import { ToDeviceChannel, ToDeviceRequests, Request } from "./verification/request/ToDeviceChannel"; import { IllegalMethod } from "./verification/IllegalMethod"; import { KeySignatureUploadError } from "../errors"; import { calculateKeyCheck, decryptAES, encryptAES } from './aes'; @@ -2318,8 +2318,8 @@ export class Crypto extends TypedEventEmitter { + let request: Request; if (transactionId) { request = this.toDeviceVerificationRequests.getRequestBySenderAndTxnId(userId, transactionId); if (!request) { diff --git a/src/models/event.ts b/src/models/event.ts index 227036be5e7..e188e860787 100644 --- a/src/models/event.ts +++ b/src/models/event.ts @@ -1043,7 +1043,7 @@ export class MatrixEvent extends TypedEventEmitter