diff --git a/.github/workflows/docker.yaml b/.github/workflows/docker.yaml index 76107876..fccaf634 100644 --- a/.github/workflows/docker.yaml +++ b/.github/workflows/docker.yaml @@ -2,24 +2,13 @@ name: Docker Test & Publish on: push: - # branches: - # - "main" tags: - "*" - paths-ignore: - - ".github/**" - - "!.github/workflows/docker.yml" - - ".vscode/**" - - "doc/**" - - ".gitignore" - - "LICENSE" - - "README" pull_request: branches: - "main" paths: - "Dockerfile" - workflow_dispatch: permissions: contents: read @@ -27,8 +16,9 @@ permissions: jobs: base: + name: Test base image build runs-on: ubuntu-latest - name: Build base image + if: github.event_name == 'pull_request' steps: # Configure build environment - name: Checkout @@ -36,33 +26,21 @@ jobs: - name: Set up Docker Buildx uses: docker/setup-buildx-action@v2 - # Authenticate with GHCR - - name: Login to Github Container Registry - if: ${{ github.event_name != 'pull_request' }} - uses: docker/login-action@v2 - with: - registry: ghcr.io - username: ${{ github.actor }} - password: ${{ secrets.GITHUB_TOKEN }} - + # Build the image - name: Build base image uses: docker/build-push-action@v4 with: context: . - push: ${{ github.event_name != 'pull_request' }} + push: false platforms: linux/amd64,linux/arm64 tags: ghcr.io/${{ github.repository_owner }}/base:latest cache-from: type=gha,scope=buildx-base-multi-arch cache-to: type=gha,scope=buildx-base-multi-arch,mode=max publish: - needs: [base] - runs-on: ubuntu-latest + runs-on: self-hosted if: github.event_name != 'pull_request' - strategy: - matrix: - project: [delta, bonfire, autumn, january, pushd] - name: Build ${{ matrix.project }} image + name: Publish Docker images steps: # Configure build environment - name: Checkout @@ -77,6 +55,7 @@ jobs: registry: docker.io username: ${{ secrets.DOCKERHUB_USERNAME }} password: ${{ secrets.DOCKERHUB_TOKEN }} + - name: Login to Github Container Registry uses: docker/login-action@v2 with: @@ -84,58 +63,131 @@ jobs: username: ${{ github.actor }} password: ${{ secrets.GITHUB_TOKEN }} - # Resolve the correct project - - uses: kanga333/variable-mapper@master - id: export + # Build the image + - name: Build base image + uses: docker/build-push-action@v4 with: - key: "${{ matrix.project }}" - map: | - { - "delta": { - "path": "crates/delta", - "tag": "${{ github.repository_owner }}/server" - }, - "bonfire": { - "path": "crates/bonfire", - "tag": "${{ github.repository_owner }}/bonfire" - }, - "autumn": { - "path": "crates/services/autumn", - "tag": "${{ github.repository_owner }}/autumn" - }, - "january": { - "path": "crates/services/january", - "tag": "${{ github.repository_owner }}/january" - }, - "pushd": { - "path": "crates/daemons/pushd", - "tag": "${{ github.repository_owner }}/pushd" - }, - "crond": { - "path": "crates/daemons/crond", - "tag": "${{ github.repository_owner }}/crond" - } - } - export_to: output + context: . + push: true + platforms: linux/amd64,linux/arm64 + tags: ghcr.io/${{ github.repository_owner }}/base:latest - # Configure metadata + # revoltchat/server - name: Docker meta - id: meta + id: meta-delta uses: docker/metadata-action@v4 with: images: | - docker.io/${{ steps.export.outputs.tag }} - ghcr.io/${{ steps.export.outputs.tag }} - - # Build crate image + docker.io/revoltchat/server + ghcr.io/revoltchat/server - name: Publish uses: docker/build-push-action@v4 with: context: . push: true platforms: linux/amd64,linux/arm64 - file: ${{ steps.export.outputs.path }}/Dockerfile - tags: ${{ steps.meta.outputs.tags }} + file: crates/delta/Dockerfile + tags: ${{ steps.meta-delta.outputs.tags }} build-args: | BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest - labels: ${{ steps.meta.outputs.labels }} + labels: ${{ steps.meta-delta.outputs.labels }} + + # revoltchat/bonfire + - name: Docker meta + id: meta-bonfire + uses: docker/metadata-action@v4 + with: + images: | + docker.io/revoltchat/bonfire + ghcr.io/revoltchat/bonfire + - name: Publish + uses: docker/build-push-action@v4 + with: + context: . + push: true + platforms: linux/amd64,linux/arm64 + file: crates/bonfire/Dockerfile + tags: ${{ steps.meta-bonfire.outputs.tags }} + build-args: | + BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest + labels: ${{ steps.meta-bonfire.outputs.labels }} + + # revoltchat/autumn + - name: Docker meta + id: meta-autumn + uses: docker/metadata-action@v4 + with: + images: | + docker.io/revoltchat/autumn + ghcr.io/revoltchat/autumn + - name: Publish + uses: docker/build-push-action@v4 + with: + context: . + push: true + platforms: linux/amd64,linux/arm64 + file: crates/services/autumn/Dockerfile + tags: ${{ steps.meta-autumn.outputs.tags }} + build-args: | + BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest + labels: ${{ steps.meta-autumn.outputs.labels }} + + # revoltchat/january + - name: Docker meta + id: meta-january + uses: docker/metadata-action@v4 + with: + images: | + docker.io/revoltchat/january + ghcr.io/revoltchat/january + - name: Publish + uses: docker/build-push-action@v4 + with: + context: . + push: true + platforms: linux/amd64,linux/arm64 + file: crates/services/january/Dockerfile + tags: ${{ steps.meta-january.outputs.tags }} + build-args: | + BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest + labels: ${{ steps.meta-january.outputs.labels }} + + # revoltchat/crond + - name: Docker meta + id: meta-crond + uses: docker/metadata-action@v4 + with: + images: | + docker.io/revoltchat/crond + ghcr.io/revoltchat/crond + - name: Publish + uses: docker/build-push-action@v4 + with: + context: . + push: true + platforms: linux/amd64,linux/arm64 + file: crates/daemons/crond/Dockerfile + tags: ${{ steps.meta-crond.outputs.tags }} + build-args: | + BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest + labels: ${{ steps.meta-crond.outputs.labels }} + + # revoltchat/pushd + - name: Docker meta + id: meta-pushd + uses: docker/metadata-action@v4 + with: + images: | + docker.io/revoltchat/pushd + ghcr.io/revoltchat/pushd + - name: Publish + uses: docker/build-push-action@v4 + with: + context: . + push: true + platforms: linux/amd64,linux/arm64 + file: crates/daemons/pushd/Dockerfile + tags: ${{ steps.meta-pushd.outputs.tags }} + build-args: | + BASE_IMAGE=ghcr.io/${{ github.repository_owner }}/base:latest + labels: ${{ steps.meta-pushd.outputs.labels }} diff --git a/.vscode/settings.json b/.vscode/settings.json index 7f8ecfcd..707af02f 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,6 +1,6 @@ { "editor.formatOnSave": true, - "rust-analyzer.checkOnSave.command": "clippy", + "rust-analyzer.check.command": "clippy", "nixEnvSelector.suggestion": false, "nixEnvSelector.nixFile": "${workspaceFolder}/default.nix" -} \ No newline at end of file +} diff --git a/Cargo.lock b/Cargo.lock index 668dad17..be8edb59 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -65,15 +65,15 @@ dependencies = [ [[package]] name = "ahash" -version = "0.8.11" +version = "0.8.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e89da841a80418a9b391ebaea17f5c112ffaaa96f621d2c285b5174da76b9011" +checksum = "5a15f179cd60c4584b8a8c596927aadc462e27f2ca70c04e0071964a73ba7a75" dependencies = [ "cfg-if", - "getrandom 0.2.16", + "getrandom 0.3.3", "once_cell", "version_check", - "zerocopy 0.7.35", + "zerocopy", ] [[package]] @@ -119,7 +119,7 @@ dependencies = [ "bytes 1.10.1", "serde", "serde_bytes_ng", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -142,6 +142,9 @@ name = "anyhow" version = "1.0.98" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e16d2d3311acee920a9eb8d33b8cbc1787ce4a264e85f964c2404b969bdcd487" +dependencies = [ + "backtrace", +] [[package]] name = "arbitrary" @@ -239,14 +242,14 @@ dependencies = [ "futures-lite 2.6.0", "once_cell", "tokio 0.2.25", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] name = "async-io" -version = "2.4.0" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43a2b323ccce0a1d90b449fd71f2a06ca7faa7c54c2751f06c9bd851fc061059" +checksum = "1237c0ae75a0f3765f58910ff9cdd0a12eeb39ab2f4c7de23262f337f0aacbb3" dependencies = [ "async-lock 3.4.0", "cfg-if", @@ -254,8 +257,8 @@ dependencies = [ "futures-io", "futures-lite 2.6.0", "parking", - "polling 3.7.4", - "rustix 0.38.44", + "polling 3.8.0", + "rustix 1.0.7", "slab", "tracing", "windows-sys 0.59.0", @@ -283,9 +286,9 @@ dependencies = [ [[package]] name = "async-process" -version = "2.3.0" +version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "63255f1dc2381611000436537bbedfe83183faa303a5a0edaf191edef06526bb" +checksum = "cde3f4e40e6021d7acffc90095cbd6dc54cb593903d1de5832f435eb274b85dc" dependencies = [ "async-channel 2.3.1", "async-io", @@ -296,7 +299,7 @@ dependencies = [ "cfg-if", "event-listener 5.4.0", "futures-lite 2.6.0", - "rustix 0.38.44", + "rustix 1.0.7", "tracing", ] @@ -313,9 +316,9 @@ dependencies = [ [[package]] name = "async-signal" -version = "0.2.10" +version = "0.2.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "637e00349800c0bdf8bfc21ebbc0b6524abea702b0da4168ac00d070d0c0b9f3" +checksum = "d7605a4e50d4b06df3898d5a70bf5fde51ed9059b0434b73105193bc27acce0d" dependencies = [ "async-io", "async-lock 3.4.0", @@ -323,7 +326,7 @@ dependencies = [ "cfg-if", "futures-core", "futures-io", - "rustix 0.38.44", + "rustix 1.0.7", "signal-hook-registry", "slab", "windows-sys 0.59.0", @@ -444,9 +447,9 @@ dependencies = [ [[package]] name = "authifier" -version = "1.0.12" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43b1f94d08726258a899aa4ee827e6bf161513f1b78c8b25e47873d573d6ceee" +checksum = "b1a03b810b342b4c584cdc1cfc40d1ec763b1d653ef4086f7494740f35d9e1f0" dependencies = [ "async-std", "async-trait", @@ -471,6 +474,7 @@ dependencies = [ "schemars", "serde", "serde_json", + "sha1", "totp-lite", "ulid 0.5.0", "validator 0.15.0", @@ -499,9 +503,9 @@ checksum = "ace50bade8e6234aa140d9a2f552bbee1db4d353f69b8217bc503490fc1a9f26" [[package]] name = "av1-grain" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6678909d8c5d46a42abcf571271e15fdbc0a225e3646cf23762cd415046c78bf" +checksum = "4f3efb2ca85bc610acfa917b5aaa36f3fcbebed5b3182d7f877b02531c4b80c8" dependencies = [ "anyhow", "arrayvec", @@ -522,9 +526,9 @@ dependencies = [ [[package]] name = "aws-config" -version = "1.6.2" +version = "1.6.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6fcc63c9860579e4cb396239570e979376e70aab79e496621748a09913f8b36" +checksum = "02a18fd934af6ae7ca52410d4548b98eb895aab0f1ea417d168d85db1434a141" dependencies = [ "aws-credential-types", "aws-runtime", @@ -544,7 +548,7 @@ dependencies = [ "http 1.3.1", "ring", "time", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", "url", "zeroize", @@ -564,9 +568,9 @@ dependencies = [ [[package]] name = "aws-lc-rs" -version = "1.13.0" +version = "1.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19b756939cb2f8dc900aa6dcd505e6e2428e9cae7ff7b028c49e3946efa70878" +checksum = "93fcc8f365936c834db5514fc45aee5b1202d677e6b40e48468aaaa8183ca8c7" dependencies = [ "aws-lc-sys", "zeroize", @@ -574,9 +578,9 @@ dependencies = [ [[package]] name = "aws-lc-sys" -version = "0.28.2" +version = "0.29.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfa9b6986f250236c27e5a204062434a773a13243d2ffc2955f37bdba4c5c6a1" +checksum = "61b1d86e7705efe1be1b569bab41d4fa1e14e220b60a160f78de2db687add079" dependencies = [ "bindgen", "cc", @@ -612,9 +616,9 @@ dependencies = [ [[package]] name = "aws-sdk-s3" -version = "1.83.0" +version = "1.90.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51384750334005f40e1a334b0d54eca822a77eacdcf3c50fdf38f583c5eee7a2" +checksum = "5934beb9403c562bd129a1de1bd51ab67209c05ddf3a4a8c86714120181c860f" dependencies = [ "aws-credential-types", "aws-runtime", @@ -637,7 +641,6 @@ dependencies = [ "http 1.3.1", "http-body 0.4.6", "lru 0.12.5", - "once_cell", "percent-encoding", "regex-lite", "sha2", @@ -647,9 +650,9 @@ dependencies = [ [[package]] name = "aws-sdk-sso" -version = "1.65.0" +version = "1.71.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8efec445fb78df585327094fcef4cad895b154b58711e504db7a93c41aa27151" +checksum = "95a4fd09d6e863655d99cd2260f271c6d1030dc6bfad68e19e126d2e4c8ceb18" dependencies = [ "aws-credential-types", "aws-runtime", @@ -663,16 +666,15 @@ dependencies = [ "bytes 1.10.1", "fastrand 2.3.0", "http 0.2.12", - "once_cell", "regex-lite", "tracing", ] [[package]] name = "aws-sdk-ssooidc" -version = "1.66.0" +version = "1.72.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e49cca619c10e7b002dc8e66928ceed66ab7f56c1a3be86c5437bf2d8d89bba" +checksum = "3224ab02ebb3074467a33d57caf6fcb487ca36f3697fdd381b0428dc72380696" dependencies = [ "aws-credential-types", "aws-runtime", @@ -686,16 +688,15 @@ dependencies = [ "bytes 1.10.1", "fastrand 2.3.0", "http 0.2.12", - "once_cell", "regex-lite", "tracing", ] [[package]] name = "aws-sdk-sts" -version = "1.66.0" +version = "1.72.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7420479eac0a53f776cc8f0d493841ffe58ad9d9783f3947be7265784471b47a" +checksum = "f6933f189ed1255e78175fbd73fb200c0aae7240d220ed3346f567b0ddca3083" dependencies = [ "aws-credential-types", "aws-runtime", @@ -710,16 +711,15 @@ dependencies = [ "aws-types", "fastrand 2.3.0", "http 0.2.12", - "once_cell", "regex-lite", "tracing", ] [[package]] name = "aws-sigv4" -version = "1.3.1" +version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3503af839bd8751d0bdc5a46b9cac93a003a353e635b0c12cf2376b5b53e41ea" +checksum = "3734aecf9ff79aa401a6ca099d076535ab465ff76b46440cf567c8e70b65dc13" dependencies = [ "aws-credential-types", "aws-smithy-eventstream", @@ -751,21 +751,19 @@ checksum = "1e190749ea56f8c42bf15dd76c65e14f8f765233e6df9b0506d9d934ebef867c" dependencies = [ "futures-util", "pin-project-lite 0.2.16", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] name = "aws-smithy-checksums" -version = "0.63.1" +version = "0.63.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b65d21e1ba6f2cdec92044f904356a19f5ad86961acf015741106cdfafd747c0" +checksum = "d2f77a921dbd2c78ebe70726799787c1d110a2245dd65e39b20923dfdfb2deee" dependencies = [ "aws-smithy-http", "aws-smithy-types", "bytes 1.10.1", - "crc32c", - "crc32fast", - "crc64fast-nvme", + "crc-fast", "hex", "http 0.2.12", "http-body 0.4.6", @@ -810,28 +808,28 @@ dependencies = [ [[package]] name = "aws-smithy-http-client" -version = "1.0.1" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8aff1159006441d02e57204bf57a1b890ba68bedb6904ffd2873c1c4c11c546b" +checksum = "7e44697a9bded898dcd0b1cb997430d949b87f4f8940d91023ae9062bf218250" dependencies = [ "aws-smithy-async", "aws-smithy-runtime-api", "aws-smithy-types", - "h2 0.4.9", + "h2 0.4.10", "http 0.2.12", "http 1.3.1", "http-body 0.4.6", "hyper 0.14.32", "hyper 1.6.0", "hyper-rustls 0.24.2", - "hyper-rustls 0.27.5", + "hyper-rustls 0.27.6", "hyper-util", "pin-project-lite 0.2.16", "rustls 0.21.12", - "rustls 0.23.26", + "rustls 0.23.27", "rustls-native-certs 0.8.1", "rustls-pki-types", - "tokio 1.44.2", + "tokio 1.45.1", "tower", "tracing", ] @@ -884,7 +882,7 @@ dependencies = [ "http-body 1.0.1", "pin-project-lite 0.2.16", "pin-utils", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", ] @@ -900,7 +898,7 @@ dependencies = [ "http 0.2.12", "http 1.3.1", "pin-project-lite 0.2.16", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", "zeroize", ] @@ -927,7 +925,7 @@ dependencies = [ "ryu", "serde", "time", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", ] @@ -982,7 +980,7 @@ dependencies = [ "serde_path_to_error", "serde_urlencoded", "sync_wrapper 1.0.2", - "tokio 1.44.2", + "tokio 1.45.1", "tower", "tower-layer", "tower-service", @@ -1060,7 +1058,7 @@ dependencies = [ "futures-util", "tempfile", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", "uuid", ] @@ -1080,9 +1078,9 @@ dependencies = [ [[package]] name = "backtrace" -version = "0.3.74" +version = "0.3.75" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d82cb332cdfaed17ae235a638438ac4d4839913cc2af585c3c6746e8f8bee1a" +checksum = "6806a6321ec58106fea15becdad98371e28d92ccbc7c8f1b3b6dd724fe8f1002" dependencies = [ "addr2line", "cfg-if", @@ -1172,7 +1170,7 @@ version = "0.69.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "271383c67ccabffb7381723dea0672a673f292304fcb45c01cc648c7a8d58088" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "cexpr", "clang-sys", "itertools 0.12.1", @@ -1191,9 +1189,9 @@ dependencies = [ [[package]] name = "binstring" -version = "0.1.6" +version = "0.1.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a3a3c2603413428303761fae99d4b6d936404208221a44eba47d7c1e6dd03a3" +checksum = "0669d5a35b64fdb5ab7fb19cae13148b6b5cbdf4b8247faf54ece47f699c8cef" [[package]] name = "bit_field" @@ -1215,9 +1213,9 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" [[package]] name = "bitflags" -version = "2.9.0" +version = "2.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c8214115b7bf84099f1309324e63141d4c5d7cc26862f97a0a857dbefe165bd" +checksum = "1b8e56985ec62d17e9c1001dc89c88ecd7dc08e47eba5ec7c29c7b5eeecde967" [[package]] name = "bitstream-io" @@ -1272,15 +1270,15 @@ dependencies = [ [[package]] name = "bson" -version = "2.14.0" +version = "2.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af8113ff51309e2779e8785a246c10fb783e8c2452f134d6257fd71cc03ccd6c" +checksum = "7969a9ba84b0ff843813e7249eed1678d9b6607ce5a3b8f0a47af3fcf7978e6e" dependencies = [ - "ahash 0.8.11", + "ahash 0.8.12", "base64 0.22.1", "bitvec", "getrandom 0.2.16", - "getrandom 0.3.2", + "getrandom 0.3.3", "hex", "indexmap 2.9.0", "js-sys", @@ -1359,7 +1357,7 @@ dependencies = [ "instant", "once_cell", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -1389,9 +1387,9 @@ checksum = "a2698f953def977c68f935bb0dfa959375ad4638570e969e2f1e9f433cbf1af6" [[package]] name = "cc" -version = "1.2.20" +version = "1.2.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "04da6a0d40b948dfc4fa8f5bbf402b0fc1a64a28dbf7d12ffd683550f2c1b63a" +checksum = "d0fc897dc1e865cc67c0e05a836d9d3f1df3cbe442aa4a9473b18e12624a4951" dependencies = [ "jobserver", "libc", @@ -1515,7 +1513,7 @@ dependencies = [ "futures-core", "memchr", "pin-project-lite 0.2.16", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", ] @@ -1623,9 +1621,9 @@ dependencies = [ [[package]] name = "core-foundation" -version = "0.10.0" +version = "0.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b55271e5c8c478ad3f38ad24ef34923091e0548492a266d19b3c0b4d82574c63" +checksum = "b2a6cd9ae233e7f62ba4e9353e81a88df7fc8a5987b8d445b4d90c879bd156f6" dependencies = [ "core-foundation-sys", "libc", @@ -1657,9 +1655,9 @@ dependencies = [ [[package]] name = "crc" -version = "3.2.1" +version = "3.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69e6e4d7b33a94f0991c26729976b10ebde1d34c3ee82408fb536164fa10d636" +checksum = "9710d3b3739c2e349eb44fe848ad0b7c8cb1e42bd87ee49371df2f7acaf3e675" dependencies = [ "crc-catalog", ] @@ -1670,21 +1668,26 @@ version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "19d374276b40fb8bbdee95aef7c7fa6b5316ec764510eb64b8dd0e2ed0d7e7f5" +[[package]] +name = "crc-fast" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "add8d3a4c789d77eeb0f0e3c1035f73610d017f9047e87db94f89c02a56d8fef" +dependencies = [ + "cc", + "crc", + "digest", + "libc", + "rand 0.9.1", + "regex", +] + [[package]] name = "crc16" version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "338089f42c427b86394a5ee60ff321da23a5c89c9d89514c829687b26359fcff" -[[package]] -name = "crc32c" -version = "0.6.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3a47af21622d091a8f0fb295b88bc886ac74efcc613efc19f5d0b21de5c89e47" -dependencies = [ - "rustc_version", -] - [[package]] name = "crc32fast" version = "1.4.2" @@ -1694,15 +1697,6 @@ dependencies = [ "cfg-if", ] -[[package]] -name = "crc64fast-nvme" -version = "1.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4955638f00a809894c947f85a024020a20815b65a5eea633798ea7924edab2b3" -dependencies = [ - "crc", -] - [[package]] name = "crossbeam-channel" version = "0.5.15" @@ -1812,9 +1806,9 @@ dependencies = [ [[package]] name = "ct-codecs" -version = "1.1.3" +version = "1.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b916ba8ce9e4182696896f015e8a5ae6081b305f74690baa8465e35f5a142ea4" +checksum = "9b10589d1a5e400d61f9f38f12f884cfd080ff345de8f17efda36fe0e4a02aa8" [[package]] name = "ctr" @@ -1836,7 +1830,7 @@ dependencies = [ "openssl-probe", "openssl-sys", "schannel", - "socket2 0.5.9", + "socket2 0.5.10", "windows-sys 0.52.0", ] @@ -1993,7 +1987,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "16a2561fd313df162315935989dceb8c99db4ee1933358270a57a3cfb8c957f3" dependencies = [ "crossbeam-queue", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -2079,9 +2073,9 @@ dependencies = [ [[package]] name = "derive-where" -version = "1.3.0" +version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2364b9aa47e460ce9bca6ac1777d14c98eef7e274eb077beed49f3adc94183ed" +checksum = "e73f2692d4bd3cac41dca28934a39894200c9fabf49586d77d0e5954af1d7902" dependencies = [ "proc-macro2", "quote 1.0.40", @@ -2127,7 +2121,7 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b035a542cf7abf01f2e3c4d5a7acbaebfefe120ae4efc7bde3df98186e4b8af7" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "proc-macro2", "proc-macro2-diagnostics", "quote 1.0.40", @@ -2384,9 +2378,9 @@ dependencies = [ [[package]] name = "errno" -version = "0.3.11" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "976dd42dc7e85965fe702eb8164f21f450704bdde31faefd6471dba214cb594e" +checksum = "cea14ef9355e3beab063703aa9dab15afd25f0667c341310c1e5274bb1d0da18" dependencies = [ "libc", "windows-sys 0.59.0", @@ -2566,9 +2560,9 @@ checksum = "d9c4f5dac5e15c24eb999c26181a6ca40b39fe946cbe4c263c7209467bc83af2" [[package]] name = "fontconfig-parser" -version = "0.5.7" +version = "0.5.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c1fcfcd44ca6e90c921fee9fa665d530b21ef1327a4c1a6c5250ea44b776ada7" +checksum = "bbc773e24e02d4ddd8395fd30dc147524273a83e54e0f312d986ea30de5f5646" dependencies = [ "roxmltree", ] @@ -2629,8 +2623,8 @@ dependencies = [ "rand 0.8.5", "redis-protocol", "semver", - "socket2 0.5.9", - "tokio 1.44.2", + "socket2 0.5.10", + "tokio 1.45.1", "tokio-stream", "tokio-util", "url", @@ -2749,7 +2743,7 @@ checksum = "45ec6fe3675af967e67c5536c0b9d44e34e6c52f86bedc4ea49c5317b8e94d06" dependencies = [ "futures-channel", "futures-task", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -2823,15 +2817,16 @@ dependencies = [ [[package]] name = "generator" -version = "0.8.4" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc6bd114ceda131d3b1d665eba35788690ad37f5916457286b32ab6fd3c438dd" +checksum = "d18470a76cb7f8ff746cf1f7470914f900252ec36bbc40b569d74b1258446827" dependencies = [ + "cc", "cfg-if", "libc", "log", "rustversion", - "windows 0.58.0", + "windows 0.61.1", ] [[package]] @@ -2878,9 +2873,9 @@ dependencies = [ [[package]] name = "getrandom" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "73fea8450eea4bac3940448fb7ae50d91f034f941199fcd9d909a5a07aa455f0" +checksum = "26145e563e54f2cadc477553f1ec5ee650b00862f0a58bcd12cbdc5f0ea2d2f4" dependencies = [ "cfg-if", "js-sys", @@ -2995,16 +2990,16 @@ dependencies = [ "http 0.2.12", "indexmap 2.9.0", "slab", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", "tracing", ] [[package]] name = "h2" -version = "0.4.9" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "75249d144030531f8dee69fe9cea04d3edf809a017ae445e2abdff6629e86633" +checksum = "a9421a676d1b147b16b82c9225157dc629087ef8ec4d5e2960f9437a90dac0a5" dependencies = [ "atomic-waker", "bytes 1.10.1", @@ -3014,7 +3009,7 @@ dependencies = [ "http 1.3.1", "indexmap 2.9.0", "slab", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", "tracing", ] @@ -3064,15 +3059,15 @@ version = "0.14.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1" dependencies = [ - "ahash 0.8.11", + "ahash 0.8.12", "allocator-api2", ] [[package]] name = "hashbrown" -version = "0.15.2" +version = "0.15.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289" +checksum = "84b26c544d002229e640969970a2e74021aadf6e2f96372b9c58eff97de08eb3" dependencies = [ "allocator-api2", "equivalent", @@ -3126,21 +3121,9 @@ dependencies = [ [[package]] name = "hermit-abi" -version = "0.3.9" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024" - -[[package]] -name = "hermit-abi" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fbf6a919d6cf397374f7dfeeea91d974c7c0a7221d0d0f4f20d859d329e53fcc" - -[[package]] -name = "hermit-abi" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fbd780fe5cc30f81464441920d82ac8740e2e46b29a6fad543ddd075229ce37e" +checksum = "f154ce46856750ed433c8649605bf7ed2de3bc35fd9d2a9f30cddd873c80cb08" [[package]] name = "hex" @@ -3167,7 +3150,7 @@ dependencies = [ "rand 0.8.5", "thiserror 1.0.69", "tinyvec", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", "url", ] @@ -3189,7 +3172,7 @@ dependencies = [ "resolv-conf", "smallvec", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", ] @@ -3219,18 +3202,18 @@ checksum = "18492c9f6f9a560e0d346369b665ad2bdbc89fa9bceca75796584e79042694c3" [[package]] name = "hmac-sha256" -version = "1.1.8" +version = "1.1.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4a8575493d277c9092b988c780c94737fb9fd8651a1001e16bee3eccfc1baedb" +checksum = "ad6880c8d4a9ebf39c6e8b77007ce223f646a4d21ce29d99f70cb16420545425" dependencies = [ "digest", ] [[package]] name = "hmac-sha512" -version = "1.1.6" +version = "1.1.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b0b3a0f572aa8389d325f5852b9e0a333a15b0f86ecccbb3fdb6e97cd86dc67c" +checksum = "e89e8d20b3799fa526152a5301a771eaaad80857f83e01b23216ceaafb2d9280" dependencies = [ "digest", ] @@ -3255,17 +3238,6 @@ dependencies = [ "winapi", ] -[[package]] -name = "hostname" -version = "0.4.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a56f203cd1c76362b69e3863fd987520ac36cf70a8c92627449b2f64a8cf7d65" -dependencies = [ - "cfg-if", - "libc", - "windows-link", -] - [[package]] name = "html5ever" version = "0.27.0" @@ -3374,8 +3346,8 @@ dependencies = [ "httpdate", "itoa", "pin-project-lite 0.2.16", - "socket2 0.5.9", - "tokio 1.44.2", + "socket2 0.5.10", + "tokio 1.45.1", "tower-service", "tracing", "want", @@ -3390,7 +3362,7 @@ dependencies = [ "bytes 1.10.1", "futures-channel", "futures-util", - "h2 0.4.9", + "h2 0.4.10", "http 1.3.1", "http-body 1.0.1", "httparse", @@ -3398,7 +3370,7 @@ dependencies = [ "itoa", "pin-project-lite 0.2.16", "smallvec", - "tokio 1.44.2", + "tokio 1.45.1", "want", ] @@ -3414,7 +3386,7 @@ dependencies = [ "log", "rustls 0.21.12", "rustls-native-certs 0.6.3", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-rustls 0.24.1", ] @@ -3430,26 +3402,25 @@ dependencies = [ "hyper-util", "rustls 0.22.4", "rustls-pki-types", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-rustls 0.25.0", "tower-service", - "webpki-roots 0.26.9", + "webpki-roots 0.26.11", ] [[package]] name = "hyper-rustls" -version = "0.27.5" +version = "0.27.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d191583f3da1305256f22463b9bb0471acad48a4e534a5218b9963e9c1f59b2" +checksum = "03a01595e11bdcec50946522c32dde3fc6914743000a68b93000965f2f02406d" dependencies = [ - "futures-util", "http 1.3.1", "hyper 1.6.0", "hyper-util", - "rustls 0.23.26", + "rustls 0.23.27", "rustls-native-certs 0.8.1", "rustls-pki-types", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-rustls 0.26.2", "tower-service", ] @@ -3463,7 +3434,7 @@ dependencies = [ "bytes 1.10.1", "hyper 0.14.32", "native-tls", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-native-tls", ] @@ -3478,29 +3449,35 @@ dependencies = [ "hyper 1.6.0", "hyper-util", "native-tls", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-native-tls", "tower-service", ] [[package]] name = "hyper-util" -version = "0.1.11" +version = "0.1.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "497bbc33a26fdd4af9ed9c70d63f61cf56a938375fbb32df34db9b1cd6d643f2" +checksum = "b1c293b6b3d21eca78250dc7dbebd6b9210ec5530e038cbfe0661b5c47ab06e8" dependencies = [ + "base64 0.22.1", "bytes 1.10.1", "futures-channel", + "futures-core", "futures-util", "http 1.3.1", "http-body 1.0.1", "hyper 1.6.0", + "ipnet", "libc", + "percent-encoding", "pin-project-lite 0.2.16", - "socket2 0.5.9", - "tokio 1.44.2", + "socket2 0.5.10", + "system-configuration 0.6.1", + "tokio 1.45.1", "tower-service", "tracing", + "windows-registry", ] [[package]] @@ -3515,7 +3492,7 @@ dependencies = [ "js-sys", "log", "wasm-bindgen", - "windows-core 0.61.0", + "windows-core", ] [[package]] @@ -3529,21 +3506,22 @@ dependencies = [ [[package]] name = "icu_collections" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "db2fa452206ebee18c4b5c2274dbf1de17008e874b4dc4f0aea9d01ca79e4526" +checksum = "200072f5d0e3614556f94a9930d5dc3e0662a652823904c3a75dc3b0af7fee47" dependencies = [ "displaydoc", + "potential_utf", "yoke", "zerofrom", "zerovec", ] [[package]] -name = "icu_locid" -version = "1.5.0" +name = "icu_locale_core" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "13acbb8371917fc971be86fc8057c41a64b521c184808a698c02acc242dbf637" +checksum = "0cde2700ccaed3872079a65fb1a78f6c0a36c91570f28755dda67bc8f7d9f00a" dependencies = [ "displaydoc", "litemap", @@ -3552,31 +3530,11 @@ dependencies = [ "zerovec", ] -[[package]] -name = "icu_locid_transform" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "01d11ac35de8e40fdeda00d9e1e9d92525f3f9d887cdd7aa81d727596788b54e" -dependencies = [ - "displaydoc", - "icu_locid", - "icu_locid_transform_data", - "icu_provider", - "tinystr", - "zerovec", -] - -[[package]] -name = "icu_locid_transform_data" -version = "1.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7515e6d781098bf9f7205ab3fc7e9709d34554ae0b21ddbcb5febfa4bc7df11d" - [[package]] name = "icu_normalizer" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19ce3e0da2ec68599d193c93d088142efd7f9c5d6fc9b803774855747dc6a84f" +checksum = "436880e8e18df4d7bbc06d58432329d6458cc84531f7ac5f024e93deadb37979" dependencies = [ "displaydoc", "icu_collections", @@ -3584,67 +3542,54 @@ dependencies = [ "icu_properties", "icu_provider", "smallvec", - "utf16_iter", - "utf8_iter", - "write16", "zerovec", ] [[package]] name = "icu_normalizer_data" -version = "1.5.1" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c5e8338228bdc8ab83303f16b797e177953730f601a96c25d10cb3ab0daa0cb7" +checksum = "00210d6893afc98edb752b664b8890f0ef174c8adbb8d0be9710fa66fbbf72d3" [[package]] name = "icu_properties" -version = "1.5.1" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93d6020766cfc6302c15dbbc9c8778c37e62c14427cb7f6e601d849e092aeef5" +checksum = "016c619c1eeb94efb86809b015c58f479963de65bdb6253345c1a1276f22e32b" dependencies = [ "displaydoc", "icu_collections", - "icu_locid_transform", + "icu_locale_core", "icu_properties_data", "icu_provider", - "tinystr", + "potential_utf", + "zerotrie", "zerovec", ] [[package]] name = "icu_properties_data" -version = "1.5.1" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "85fb8799753b75aee8d2a21d7c14d9f38921b54b3dbda10f5a3c7a7b82dba5e2" +checksum = "298459143998310acd25ffe6810ed544932242d3f07083eee1084d83a71bd632" [[package]] name = "icu_provider" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ed421c8a8ef78d3e2dbc98a973be2f3770cb42b606e3ab18d6237c4dfde68d9" +checksum = "03c80da27b5f4187909049ee2d72f276f0d9f99a42c306bd0131ecfe04d8e5af" dependencies = [ "displaydoc", - "icu_locid", - "icu_provider_macros", + "icu_locale_core", "stable_deref_trait", "tinystr", "writeable", "yoke", "zerofrom", + "zerotrie", "zerovec", ] -[[package]] -name = "icu_provider_macros" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" -dependencies = [ - "proc-macro2", - "quote 1.0.40", - "syn 2.0.101", -] - [[package]] name = "ident_case" version = "1.0.1" @@ -3695,9 +3640,9 @@ dependencies = [ [[package]] name = "idna_adapter" -version = "1.2.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "daca1df1c957320b2cf139ac61e7bd64fed304c5040df000a745aa1de3b4ef71" +checksum = "3acae9609540aa318d1bc588455225fb2085b9ed0c4f6bd0d9d5bcd86f1a0344" dependencies = [ "icu_normalizer", "icu_properties", @@ -3788,7 +3733,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cea70ddb795996207ad57735b50c5982d8844f38ba9ee5f1aedcfb708a2aa11e" dependencies = [ "equivalent", - "hashbrown 0.15.2", + "hashbrown 0.15.3", "serde", ] @@ -3842,7 +3787,7 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b58db92f96b720de98181bbbe63c831e87005ab460c1bf306eb2622b4707997f" dependencies = [ - "socket2 0.5.9", + "socket2 0.5.10", "widestring", "windows-sys 0.48.0", "winreg", @@ -3854,13 +3799,23 @@ version = "2.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "469fb0b9cefa57e3ef31275ee7cacb78f2fdca44e4765491884a2b119d4eb130" +[[package]] +name = "iri-string" +version = "0.7.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dbc5ebe9c3a1a7a5127f920a418f7585e9e758e911d0466ed004f393b0e380b2" +dependencies = [ + "memchr", + "serde", +] + [[package]] name = "is-terminal" version = "0.4.16" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e04d7f318608d35d4b61ddd75cbdaee86b023ebe2bd5a66ee0915f0bf93095a9" dependencies = [ - "hermit-abi 0.5.0", + "hermit-abi 0.5.1", "libc", "windows-sys 0.59.0", ] @@ -3936,7 +3891,7 @@ version = "0.1.33" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "38f262f097c174adebe41eb73d66ae9c06b2844fb0da69969647bbddd9b0538a" dependencies = [ - "getrandom 0.3.2", + "getrandom 0.3.3", "libc", ] @@ -4221,7 +4176,7 @@ dependencies = [ "email_address", "fastrand 1.9.0", "futures-util", - "hostname 0.3.1", + "hostname", "httpdate", "idna 0.3.0", "mime", @@ -4230,7 +4185,7 @@ dependencies = [ "once_cell", "quoted_printable", "socket2 0.4.10", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -4263,19 +4218,19 @@ dependencies = [ [[package]] name = "libloading" -version = "0.8.6" +version = "0.8.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" +checksum = "07033963ba89ebaf1584d767badaa2e8fcec21aedea6b8c0346d487d49c28667" dependencies = [ "cfg-if", - "windows-targets 0.52.6", + "windows-targets 0.53.0", ] [[package]] name = "libm" -version = "0.2.13" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c9627da5196e5d8ed0b0495e61e518847578da83483c37288316d9b2e03a7f72" +checksum = "f9fbbcab51052fe104eb5e5d351cf728d30a5be1fe14d9be8a3b097481fb97de" [[package]] name = "libnghttp2-sys" @@ -4347,15 +4302,15 @@ checksum = "cd945864f07fe9f5371a27ad7b52a172b4b499999f1d97574c9fa68373937e12" [[package]] name = "litemap" -version = "0.7.5" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23fb14cb19457329c82206317a5663005a4d404783dc74f4252769b0d5f42856" +checksum = "241eaef5fd12c88705a01fc1066c48c4b36e0dd4377dcdc7ec3942cea7a69956" [[package]] name = "livekit-api" -version = "0.4.2" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fcfd2e0622b4ef8a6d534c742071fcad52d4388047bd2182696dc080c8174d4e" +checksum = "73fb2a1b706a08e27a951a9f2140746ff48be3d4e15ba3c80f9ef4c41ccd1d42" dependencies = [ "base64 0.21.7", "http 0.2.12", @@ -4377,9 +4332,9 @@ dependencies = [ [[package]] name = "livekit-protocol" -version = "0.3.9" +version = "0.3.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0be4affc7654bf3f2c9571b02614ef27f436c5b68ee30db6151e8ab601f7e3fb" +checksum = "5dc3a6cc2da425e0a0dd7e97795fe14b9215336c10a5df7f4a98a2948a41c76d" dependencies = [ "futures-util", "livekit-runtime 0.4.0", @@ -4390,7 +4345,7 @@ dependencies = [ "prost-types", "serde", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -4399,7 +4354,7 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6ae53eb874eb86e96e8ccffc31b5a00926d46174cbcb1c24ce4e57b1fcc5c8f6" dependencies = [ - "tokio 1.44.2", + "tokio 1.45.1", "tokio-stream", ] @@ -4409,15 +4364,15 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "532e84c6cdc5fe774f2b5d9912597b5f3bea561927a48296d03e24549d21c3f6" dependencies = [ - "tokio 1.44.2", + "tokio 1.45.1", "tokio-stream", ] [[package]] name = "lock_api" -version = "0.4.12" +version = "0.4.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17" +checksum = "96936507f153605bddfcda068dd804796c84324ed2510809e5b2a624c81da765" dependencies = [ "autocfg 1.4.0", "scopeguard", @@ -4488,7 +4443,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "419e0dc8046cb947daa77eb95ae174acfbddb7673b4151f56d1eed8e93fbfaca" dependencies = [ "cfg-if", - "generator 0.8.4", + "generator 0.8.5", "scoped-tls", "tracing", "tracing-subscriber", @@ -4527,7 +4482,7 @@ version = "0.12.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "234cf4f4a04dc1f57e24b96cc0cd600cf2af460d4161ac5ecdd0af8e1f3b2a38" dependencies = [ - "hashbrown 0.15.2", + "hashbrown 0.15.3", ] [[package]] @@ -4681,7 +4636,7 @@ version = "0.23.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3045b4193fbdc5b5681f32f11070da9be3609f189a79f3390706d42587f46bb5" dependencies = [ - "ahash 0.8.11", + "ahash 0.8.12", "portable-atomic", ] @@ -4709,13 +4664,13 @@ dependencies = [ [[package]] name = "mio" -version = "1.0.3" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2886843bf800fba2e3377cff24abf6379b4c4d5c6681eaf9ea5b0d15090450bd" +checksum = "78bed444cc8a2160f01cbcf811ef18cac863ad68ae8ca62092e8db51d51c761c" dependencies = [ "libc", "wasi 0.11.0+wasi-snapshot-preview1", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -4733,7 +4688,7 @@ dependencies = [ "log", "metrics", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", "tracing-subscriber", ] @@ -4806,12 +4761,12 @@ dependencies = [ "serde_with", "sha-1", "sha2", - "socket2 0.5.9", + "socket2 0.5.10", "stringprep", "strsim 0.11.1", "take_mut", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-rustls 0.24.1", "tokio-util", "typed-builder", @@ -4845,16 +4800,16 @@ dependencies = [ "memchr", "mime", "spin", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", "version_check", ] [[package]] name = "multimap" -version = "0.10.0" +version = "0.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "defc4c55412d89136f966bbb339008b474350e5e6e78d2714439c386b3137a03" +checksum = "1d87ecb2933e8aeadb3e3a02b828fed80a7528047e68b4f424523a0981a3a084" [[package]] name = "mutate_once" @@ -4888,43 +4843,6 @@ dependencies = [ "tempfile", ] -[[package]] -name = "neon" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d75440242411c87dc39847b0e33e961ec1f10326a9d8ecf9c1ea64a3b3c13dc" -dependencies = [ - "getrandom 0.2.16", - "libloading", - "neon-macros", - "once_cell", - "semver", - "send_wrapper", - "smallvec", -] - -[[package]] -name = "neon-macros" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6813fde79b646e47e7ad75f480aa80ef76a5d9599e2717407961531169ee38b" -dependencies = [ - "quote 1.0.40", - "syn 2.0.101", - "syn-mid", -] - -[[package]] -name = "neon-serde4" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8778b4afaa506e067da24566623873c38797987be593232a4f9ad82c84bb3eb3" -dependencies = [ - "neon", - "num", - "serde", -] - [[package]] name = "new_debug_unreachable" version = "1.0.6" @@ -4966,19 +4884,6 @@ dependencies = [ "winapi", ] -[[package]] -name = "num" -version = "0.4.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35bd024e8b2ff75562e5f34e7f4905839deb4b22955ef5e73d2fea1b9813cb23" -dependencies = [ - "num-complex", - "num-integer", - "num-iter", - "num-rational", - "num-traits", -] - [[package]] name = "num-bigint" version = "0.4.6" @@ -5006,15 +4911,6 @@ dependencies = [ "zeroize", ] -[[package]] -name = "num-complex" -version = "0.4.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "73f88a1307638156682bada9d7604135552957b7818057dcef22705b4d509495" -dependencies = [ - "num-traits", -] - [[package]] name = "num-conv" version = "0.1.0" @@ -5075,11 +4971,11 @@ dependencies = [ [[package]] name = "num_cpus" -version = "1.16.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +checksum = "91df4bbde75afed763b708b7eee1e8e7651e02d97f6d5dd763e89367e957b23b" dependencies = [ - "hermit-abi 0.3.9", + "hermit-abi 0.5.1", "libc", ] @@ -5157,11 +5053,11 @@ checksum = "c08d65885ee38876c4f86fa503fb49d7b507c2b62552df7c70b2fce627e06381" [[package]] name = "openssl" -version = "0.10.72" +version = "0.10.73" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fedfea7d58a1f73118430a55da6a286e7b044961736ce96a16a17068ea25e5da" +checksum = "8505734d46c8ab1e19a1dce3aef597ad87dcb4c37e7188231769bd6bd51cebf8" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "cfg-if", "foreign-types", "libc", @@ -5189,9 +5085,9 @@ checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e" [[package]] name = "openssl-sys" -version = "0.9.107" +version = "0.9.109" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8288979acd84749c744a9014b4382d42b8f7b2592847b5afb2ed29e5d16ede07" +checksum = "90096e2e47630d78b7d1c20952dc621f957103f8bc2c8359ec81290d75238571" dependencies = [ "cc", "libc", @@ -5211,9 +5107,9 @@ dependencies = [ [[package]] name = "os_info" -version = "3.10.0" +version = "3.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2a604e53c24761286860eba4e2c8b23a0161526476b1de520139d69cdb85a6b5" +checksum = "41fc863e2ca13dc2d5c34fb22ea4a588248ac14db929616ba65c45f21744b1e9" dependencies = [ "log", "serde", @@ -5275,9 +5171,9 @@ checksum = "f38d5652c16fde515bb1ecef450ab0f6a219d619a7274976324d5e377f7dceba" [[package]] name = "parking_lot" -version = "0.12.3" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27" +checksum = "70d58bf43669b5795d1576d0641cfb6fbb2057bf629506267a92807158584a13" dependencies = [ "lock_api", "parking_lot_core", @@ -5285,9 +5181,9 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.9.10" +version = "0.9.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8" +checksum = "bc838d2a56b5b1a6c25f55575dfc605fabb63bb2365f6c2353ef9159aa69e4a5" dependencies = [ "cfg-if", "libc", @@ -5691,15 +5587,15 @@ dependencies = [ [[package]] name = "polling" -version = "3.7.4" +version = "3.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a604568c3202727d1507653cb121dbd627a58684eb09a820fd746bee38b4442f" +checksum = "b53a684391ad002dd6a596ceb6c74fd004fdce75f4be2e3f615068abbea5fd50" dependencies = [ "cfg-if", "concurrent-queue", - "hermit-abi 0.4.0", + "hermit-abi 0.5.1", "pin-project-lite 0.2.16", - "rustix 0.38.44", + "rustix 1.0.7", "tracing", "windows-sys 0.59.0", ] @@ -5722,6 +5618,15 @@ version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "350e9b48cbc6b0e028b0473b114454c6316e57336ee184ceab6e53f72c178b3e" +[[package]] +name = "potential_utf" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5a7c30837279ca13e7c867e9e40053bc68740f988cb07f7ca6df43cc734b585" +dependencies = [ + "zerovec", +] + [[package]] name = "powerfmt" version = "0.2.0" @@ -5734,7 +5639,7 @@ version = "0.2.21" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9" dependencies = [ - "zerocopy 0.8.25", + "zerocopy", ] [[package]] @@ -5755,9 +5660,9 @@ dependencies = [ [[package]] name = "prettyplease" -version = "0.2.32" +version = "0.2.33" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "664ec5419c51e34154eec046ebcba56312d5a2fc3b09a06da188e1ad21afadf6" +checksum = "9dee91521343f4c5c6a63edd65e54f31f5c92fe8978c40a4282f8372194c6a7d" dependencies = [ "proc-macro2", "syn 2.0.101", @@ -6096,7 +6001,7 @@ version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38" dependencies = [ - "getrandom 0.3.2", + "getrandom 0.3.3", ] [[package]] @@ -6257,7 +6162,7 @@ dependencies = [ "ryu", "sha1_smol", "socket2 0.4.10", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-util", "url", ] @@ -6294,11 +6199,11 @@ dependencies = [ [[package]] name = "redox_syscall" -version = "0.5.11" +version = "0.5.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2f103c6d277498fbceb16e84d317e2a400f160f46904d5f5410848c829511a3" +checksum = "928fca9cf2aa042393a8325b9ead81d2f0df4cb12e1e24cef072922ccd99c5af" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", ] [[package]] @@ -6401,7 +6306,7 @@ dependencies = [ "serde_urlencoded", "sync_wrapper 0.1.2", "system-configuration 0.5.1", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-native-tls", "tower-service", "url", @@ -6413,21 +6318,20 @@ dependencies = [ [[package]] name = "reqwest" -version = "0.12.15" +version = "0.12.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d19c46a6fdd48bc4dab94b6103fccc55d34c67cc0ad04653aad4ea2a07cd7bbb" +checksum = "e98ff6b0dbbe4d5a37318f433d4fc82babd21631f194d370409ceb2e40b2f0b5" dependencies = [ "base64 0.22.1", "bytes 1.10.1", "encoding_rs", "futures-core", - "futures-util", - "h2 0.4.9", + "h2 0.4.10", "http 1.3.1", "http-body 1.0.1", "http-body-util", "hyper 1.6.0", - "hyper-rustls 0.27.5", + "hyper-rustls 0.27.6", "hyper-tls 0.6.0", "hyper-util", "ipnet", @@ -6438,31 +6342,27 @@ dependencies = [ "once_cell", "percent-encoding", "pin-project-lite 0.2.16", - "rustls-pemfile 2.2.0", + "rustls-pki-types", "serde", "serde_json", "serde_urlencoded", "sync_wrapper 1.0.2", - "system-configuration 0.6.1", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-native-tls", "tower", + "tower-http 0.6.4", "tower-service", "url", "wasm-bindgen", "wasm-bindgen-futures", "web-sys", - "windows-registry", ] [[package]] name = "resolv-conf" -version = "0.7.1" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "48375394603e3dd4b2d64371f7148fd8c7baa2680e28741f2cb8d23b59e3d4c4" -dependencies = [ - "hostname 0.4.1", -] +checksum = "95325155c684b1c89f7765e30bc1c42e4a6da51ca513615660cb8a62ef9a88e3" [[package]] name = "resvg" @@ -6483,7 +6383,7 @@ dependencies = [ [[package]] name = "revolt-autumn" -version = "0.8.4" +version = "0.8.7" dependencies = [ "axum", "axum-macros", @@ -6508,8 +6408,8 @@ dependencies = [ "simdutf8", "strum_macros", "tempfile", - "tokio 1.44.2", - "tower-http", + "tokio 1.45.1", + "tower-http 0.5.2", "tracing", "tracing-subscriber", "ulid 1.2.1", @@ -6520,7 +6420,7 @@ dependencies = [ [[package]] name = "revolt-bonfire" -version = "0.8.4" +version = "0.8.7" dependencies = [ "async-channel 2.3.1", "async-std", @@ -6550,7 +6450,7 @@ dependencies = [ [[package]] name = "revolt-config" -version = "0.8.4" +version = "0.8.7" dependencies = [ "async-std", "cached", @@ -6561,24 +6461,25 @@ dependencies = [ "pretty_env_logger", "revolt-result", "sentry", + "sentry-anyhow", "serde", ] [[package]] name = "revolt-crond" -version = "0.8.4" +version = "0.8.7" dependencies = [ "log", "revolt-config", "revolt-database", "revolt-files", "revolt-result", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] name = "revolt-database" -version = "0.8.4" +version = "0.8.7" dependencies = [ "amqprs", "async-lock 2.8.0", @@ -6631,7 +6532,7 @@ dependencies = [ [[package]] name = "revolt-delta" -version = "0.8.4" +version = "0.8.7" dependencies = [ "amqprs", "async-channel 1.9.0", @@ -6680,7 +6581,7 @@ dependencies = [ [[package]] name = "revolt-files" -version = "0.8.4" +version = "0.8.7" dependencies = [ "aes-gcm", "aws-config", @@ -6703,7 +6604,7 @@ dependencies = [ [[package]] name = "revolt-january" -version = "0.8.4" +version = "0.8.7" dependencies = [ "async-recursion", "axum", @@ -6713,7 +6614,7 @@ dependencies = [ "mime", "moka", "regex", - "reqwest 0.12.15", + "reqwest 0.12.18", "revolt-config", "revolt-files", "revolt-models", @@ -6722,7 +6623,7 @@ dependencies = [ "serde", "serde_json", "tempfile", - "tokio 1.44.2", + "tokio 1.45.1", "tracing", "tracing-subscriber", "utoipa", @@ -6731,7 +6632,7 @@ dependencies = [ [[package]] name = "revolt-models" -version = "0.8.4" +version = "0.8.7" dependencies = [ "indexmap 1.9.3", "iso8601-timestamp", @@ -6748,29 +6649,16 @@ dependencies = [ "validator 0.16.1", ] -[[package]] -name = "revolt-nodejs-bindings" -version = "0.8.4" -dependencies = [ - "async-std", - "neon", - "neon-serde4", - "revolt-config", - "revolt-database", - "revolt-result", - "serde", -] - [[package]] name = "revolt-parser" -version = "0.1.0" +version = "0.8.7" dependencies = [ "logos", ] [[package]] name = "revolt-permissions" -version = "0.8.4" +version = "0.8.7" dependencies = [ "async-std", "async-trait", @@ -6785,7 +6673,7 @@ dependencies = [ [[package]] name = "revolt-presence" -version = "0.8.4" +version = "0.8.7" dependencies = [ "async-std", "log", @@ -6796,9 +6684,10 @@ dependencies = [ [[package]] name = "revolt-pushd" -version = "0.8.4" +version = "0.8.7" dependencies = [ "amqprs", + "anyhow", "async-trait", "authifier", "base64 0.22.1", @@ -6811,18 +6700,19 @@ dependencies = [ "revolt-database", "revolt-models", "revolt-presence", + "revolt-result", "revolt_a2", "revolt_optional_struct", "serde", "serde_json", - "tokio 1.44.2", + "tokio 1.45.1", "ulid 1.2.1", "web-push", ] [[package]] name = "revolt-result" -version = "0.8.4" +version = "0.8.7" dependencies = [ "axum", "log", @@ -6882,7 +6772,7 @@ dependencies = [ "serde", "serde_json", "thiserror 1.0.69", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -7038,7 +6928,7 @@ dependencies = [ "state", "tempfile", "time", - "tokio 1.44.2", + "tokio 1.45.1", "tokio-stream", "tokio-util", "ubyte", @@ -7048,9 +6938,9 @@ dependencies = [ [[package]] name = "rocket_authifier" -version = "1.0.12" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8a325016a62c2541a19bf4d74c93bfc16674526bcd49d94f2fdaa6f8b599e0b" +checksum = "c1f98a5be96ac4144ee1adc809c1594e8212032b8a08d9bc4cef70735dfd976e" dependencies = [ "authifier", "iso8601-timestamp", @@ -7129,7 +7019,7 @@ dependencies = [ "stable-pattern", "state", "time", - "tokio 1.44.2", + "tokio 1.45.1", "uncased", ] @@ -7240,7 +7130,7 @@ version = "0.38.44" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fdb5bc1ae2baa591800df16c9ca78619bf65c0488b41b96ccec5d11220d8c154" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "errno", "libc", "linux-raw-sys 0.4.15", @@ -7249,11 +7139,11 @@ dependencies = [ [[package]] name = "rustix" -version = "1.0.5" +version = "1.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d97817398dd4bb2e6da002002db259209759911da105da92bec29ccb12cf58bf" +checksum = "c71e83d6afe7ff64890ec6b71d6a69bb8a610ab78ce364b3352876bb4c801266" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "errno", "libc", "linux-raw-sys 0.9.4", @@ -7288,14 +7178,14 @@ dependencies = [ [[package]] name = "rustls" -version = "0.23.26" +version = "0.23.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "df51b5869f3a441595eac5e8ff14d486ff285f7b8c0df8770e49c3b56351f0f0" +checksum = "730944ca083c1c233a75c09f199e973ca499344a2b7ba9e755c457e86fb4a321" dependencies = [ "aws-lc-rs", "once_cell", "rustls-pki-types", - "rustls-webpki 0.103.1", + "rustls-webpki 0.103.3", "subtle", "zeroize", ] @@ -7344,9 +7234,12 @@ dependencies = [ [[package]] name = "rustls-pki-types" -version = "1.11.0" +version = "1.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "917ce264624a4b4db1c364dcc35bfca9ded014d0a958cd47ad3e960e988ea51c" +checksum = "229a4a4c221013e7e1f1a043678c5cc39fe5171437c88fb47151a21e6f5b5c79" +dependencies = [ + "zeroize", +] [[package]] name = "rustls-webpki" @@ -7371,9 +7264,9 @@ dependencies = [ [[package]] name = "rustls-webpki" -version = "0.103.1" +version = "0.103.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fef8b8769aaccf73098557a87cd1816b4f9c7c16811c9c77142aa695c16f2c03" +checksum = "e4a72fe2bcf7a6ac6fd7d0b9e5cb68aeb7d4c0a0271730218b3e92d43b4eb435" dependencies = [ "aws-lc-rs", "ring", @@ -7383,9 +7276,9 @@ dependencies = [ [[package]] name = "rustversion" -version = "1.0.20" +version = "1.0.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eded382c5f5f786b989652c49544c4877d9f015cc22e145a5ea8ea66c2921cd2" +checksum = "8a0d197bd2c9dc6e53b84da9556a69ba4cdfab8619eb41a8bd1cc2027a0f6b1d" [[package]] name = "rustybuzz" @@ -7393,7 +7286,7 @@ version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c85d1ccd519e61834798eb52c4e886e8c2d7d698dd3d6ce0b1b47eb8557f1181" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "bytemuck", "core_maths", "log", @@ -7463,7 +7356,7 @@ version = "0.20.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b90460b31bfe1fc07be8262e42c665ad97118d4585869de9345a84d501a9eaf0" dependencies = [ - "ahash 0.8.11", + "ahash 0.8.12", "cssparser", "ego-tree", "getopts", @@ -7534,7 +7427,7 @@ version = "2.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "897b2245f0b511c87893af39b033e5ca9cce68824c4d7e7630b5a1d339658d02" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "core-foundation 0.9.4", "core-foundation-sys", "libc", @@ -7547,8 +7440,8 @@ version = "3.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "271720403f46ca04f7ba6f55d438f8bd878d6b8ca0a1046e8228c4145bcbb316" dependencies = [ - "bitflags 2.9.0", - "core-foundation 0.10.0", + "bitflags 2.9.1", + "core-foundation 0.10.1", "core-foundation-sys", "libc", "security-framework-sys", @@ -7570,7 +7463,7 @@ version = "0.25.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4eb30575f3638fc8f6815f448d50cb1a2e255b0897985c8c59f4d37b72a07b06" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "cssparser", "derive_more", "fxhash", @@ -7589,12 +7482,6 @@ version = "1.0.26" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "56e6fa9c48d24d85fb3de5ad847117517440f6beceb7798af16b4a87d616b8d0" -[[package]] -name = "send_wrapper" -version = "0.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd0b0ec5f1c1ca621c432a25813d8d60c88abe6d3e08a3eb9cf37d97a0fe3d73" - [[package]] name = "sentry" version = "0.31.8" @@ -7604,16 +7491,27 @@ dependencies = [ "httpdate", "native-tls", "reqwest 0.11.27", - "sentry-backtrace", + "sentry-backtrace 0.31.8", "sentry-contexts", - "sentry-core", + "sentry-core 0.31.8", "sentry-debug-images", "sentry-panic", "sentry-tracing", - "tokio 1.44.2", + "tokio 1.45.1", "ureq", ] +[[package]] +name = "sentry-anyhow" +version = "0.38.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c93cfb800654dc846ccbeb35254a2f6f194aaf7e187223fd90aeb7afafe722c" +dependencies = [ + "anyhow", + "sentry-backtrace 0.38.1", + "sentry-core 0.38.1", +] + [[package]] name = "sentry-backtrace" version = "0.31.8" @@ -7623,7 +7521,18 @@ dependencies = [ "backtrace", "once_cell", "regex", - "sentry-core", + "sentry-core 0.31.8", +] + +[[package]] +name = "sentry-backtrace" +version = "0.38.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8dace796060e4ad10e3d1405b122ae184a8b2e71dce05ae450e4f81b7686b0d9" +dependencies = [ + "backtrace", + "regex", + "sentry-core 0.38.1", ] [[package]] @@ -7632,11 +7541,11 @@ version = "0.31.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6436c1bad22cdeb02179ea8ef116ffc217797c028927def303bc593d9320c0d1" dependencies = [ - "hostname 0.3.1", + "hostname", "libc", "os_info", "rustc_version", - "sentry-core", + "sentry-core 0.31.8", "uname", ] @@ -7648,7 +7557,18 @@ checksum = "901f761681f97db3db836ef9e094acdd8756c40215326c194201941947164ef1" dependencies = [ "once_cell", "rand 0.8.5", - "sentry-types", + "sentry-types 0.31.8", + "serde", + "serde_json", +] + +[[package]] +name = "sentry-core" +version = "0.38.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7426d4beec270cfdbb50f85f0bb2ce176ea57eed0b11741182a163055a558187" +dependencies = [ + "sentry-types 0.38.1", "serde", "serde_json", ] @@ -7661,7 +7581,7 @@ checksum = "afdb263e73d22f39946f6022ed455b7561b22ff5553aca9be3c6a047fa39c328" dependencies = [ "findshlibs", "once_cell", - "sentry-core", + "sentry-core 0.31.8", ] [[package]] @@ -7670,8 +7590,8 @@ version = "0.31.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "74fbf1c163f8b6a9d05912e1b272afa27c652e8b47ea60cb9a57ad5e481eea99" dependencies = [ - "sentry-backtrace", - "sentry-core", + "sentry-backtrace 0.31.8", + "sentry-core 0.31.8", ] [[package]] @@ -7680,8 +7600,8 @@ version = "0.31.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "82eabcab0a047040befd44599a1da73d3adb228ff53b5ed9795ae04535577704" dependencies = [ - "sentry-backtrace", - "sentry-core", + "sentry-backtrace 0.31.8", + "sentry-core 0.31.8", "tracing-core", "tracing-subscriber", ] @@ -7703,6 +7623,23 @@ dependencies = [ "uuid", ] +[[package]] +name = "sentry-types" +version = "0.38.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "04b6c9287202294685cb1f749b944dbbce8160b81a1061ecddc073025fed129f" +dependencies = [ + "debugid", + "hex", + "rand 0.9.1", + "serde", + "serde_json", + "thiserror 2.0.12", + "time", + "url", + "uuid", +] + [[package]] name = "serde" version = "1.0.219" @@ -7865,9 +7802,9 @@ checksum = "bbfa15b3dddfee50a0fff136974b3e1bde555604ba463834a7eb7deb6417705d" [[package]] name = "sha2" -version = "0.10.8" +version = "0.10.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" +checksum = "a7507d819769d01a365ab707794a4084392c824f54a7a6a7862f8c3d0892b283" dependencies = [ "cfg-if", "cpufeatures", @@ -8007,9 +7944,9 @@ dependencies = [ [[package]] name = "socket2" -version = "0.5.9" +version = "0.5.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f5fd57c80058a56cf5c777ab8a126398ece8e442983605d280a44ce79d0edef" +checksum = "e22376abed350d73dd1cd119b57ffccad95b4e585a7cda43e286245ce23c0678" dependencies = [ "libc", "windows-sys 0.52.0", @@ -8184,17 +8121,6 @@ dependencies = [ "unicode-ident", ] -[[package]] -name = "syn-mid" -version = "0.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5dc35bb08dd1ca3dfb09dce91fd2d13294d6711c88897d9a9d60acf39bce049" -dependencies = [ - "proc-macro2", - "quote 1.0.40", - "syn 2.0.101", -] - [[package]] name = "sync_wrapper" version = "0.1.2" @@ -8233,9 +8159,9 @@ dependencies = [ [[package]] name = "synstructure" -version = "0.13.1" +version = "0.13.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" +checksum = "728a70f3dbaf5bab7f0c4b1ac8d7ae5ea60a4b5549c8a5914361c99147a709d2" dependencies = [ "proc-macro2", "quote 1.0.40", @@ -8273,7 +8199,7 @@ version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3c879d448e9d986b661742763247d3693ed13609438cf3d006f51f5368a5ba6b" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "core-foundation 0.9.4", "system-configuration-sys 0.6.0", ] @@ -8337,14 +8263,14 @@ checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1" [[package]] name = "tempfile" -version = "3.19.1" +version = "3.20.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7437ac7763b9b123ccf33c338a5cc1bac6f69b45a136c19bdd8a65e3916435bf" +checksum = "e8a64e3985349f2441a1a9ef0b853f869006c3855f2cda6862a94d26ebb9d6a1" dependencies = [ "fastrand 2.3.0", - "getrandom 0.3.2", + "getrandom 0.3.3", "once_cell", - "rustix 1.0.5", + "rustix 1.0.7", "windows-sys 0.59.0", ] @@ -8499,9 +8425,9 @@ dependencies = [ [[package]] name = "tinystr" -version = "0.7.6" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9117f5d4db391c1cf6927e7bea3db74b9a1c1add8f7eda9ffd5364f40f57b82f" +checksum = "5d4f6d1145dcb577acf783d4e601bc1d76a13337bb54e6233add580b07344c8b" dependencies = [ "displaydoc", "zerovec", @@ -8535,9 +8461,9 @@ dependencies = [ [[package]] name = "tokio" -version = "1.44.2" +version = "1.45.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e6b88822cbe49de4185e3a4cbf8321dd487cf5fe0c5c65695fef6346371e9c48" +checksum = "75ef51a33ef1da925cea3e4eb122833cb377c61439ca401b770f54902b806779" dependencies = [ "backtrace", "bytes 1.10.1", @@ -8546,7 +8472,7 @@ dependencies = [ "parking_lot", "pin-project-lite 0.2.16", "signal-hook-registry", - "socket2 0.5.9", + "socket2 0.5.10", "tokio-macros", "windows-sys 0.52.0", ] @@ -8569,7 +8495,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" dependencies = [ "native-tls", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -8579,7 +8505,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" dependencies = [ "rustls 0.21.12", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -8590,7 +8516,7 @@ checksum = "775e0c0f0adb3a2f22a00c4745d728b479985fc15ee7ca6a2608388c5569860f" dependencies = [ "rustls 0.22.4", "rustls-pki-types", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -8599,8 +8525,8 @@ version = "0.26.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8e727b36a1a0e8b74c376ac2211e40c2c8af09fb4013c60d910495810f008e9b" dependencies = [ - "rustls 0.23.26", - "tokio 1.44.2", + "rustls 0.23.27", + "tokio 1.45.1", ] [[package]] @@ -8611,7 +8537,7 @@ checksum = "eca58d7bba4a75707817a2c44174253f9236b2d5fbd055602e9d5c07c139a047" dependencies = [ "futures-core", "pin-project-lite 0.2.16", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -8625,7 +8551,7 @@ dependencies = [ "futures-io", "futures-sink", "pin-project-lite 0.2.16", - "tokio 1.44.2", + "tokio 1.45.1", ] [[package]] @@ -8680,7 +8606,7 @@ dependencies = [ "serde_spanned", "toml_datetime", "toml_write", - "winnow 0.7.7", + "winnow 0.7.10", ] [[package]] @@ -8711,7 +8637,7 @@ dependencies = [ "futures-util", "pin-project-lite 0.2.16", "sync_wrapper 1.0.2", - "tokio 1.44.2", + "tokio 1.45.1", "tower-layer", "tower-service", "tracing", @@ -8723,7 +8649,7 @@ version = "0.5.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1e9cd434a998747dd2c4276bc96ee2e0c7a2eadf3cae88e52be55a05fa9053f5" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "bytes 1.10.1", "http 1.3.1", "http-body 1.0.1", @@ -8733,6 +8659,24 @@ dependencies = [ "tower-service", ] +[[package]] +name = "tower-http" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0fdb0c213ca27a9f57ab69ddb290fd80d970922355b83ae380b395d3986b8a2e" +dependencies = [ + "bitflags 2.9.1", + "bytes 1.10.1", + "futures-util", + "http 1.3.1", + "http-body 1.0.1", + "iri-string", + "pin-project-lite 0.2.16", + "tower", + "tower-layer", + "tower-service", +] + [[package]] name = "tower-layer" version = "0.3.3" @@ -8902,6 +8846,7 @@ checksum = "220b18413e1fe5e85a5580b22f44241f82404a66c792c9f3c9eda74c52d9a22e" dependencies = [ "chrono", "rand 0.8.5", + "serde", ] [[package]] @@ -9113,12 +9058,6 @@ version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" -[[package]] -name = "utf16_iter" -version = "1.0.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8232dd3cdaed5356e0f716d285e4b40b932ac434100fe9b7e0e8e935b9e6246" - [[package]] name = "utf8_iter" version = "1.0.4" @@ -9165,11 +9104,11 @@ dependencies = [ [[package]] name = "uuid" -version = "1.16.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "458f7a779bf54acc9f347480ac654f68407d3aab21269a6e3c9f922acd9e2da9" +checksum = "3cf4199d1e5d15ddd86a694e4d0dffa9c323ce759fea589f00fef9d81cc1931d" dependencies = [ - "getrandom 0.3.2", + "getrandom 0.3.3", "js-sys", "serde", "wasm-bindgen", @@ -9467,18 +9406,27 @@ checksum = "5f20c57d8d7db6d3b86154206ae5d8fba62dd39573114de97c2cb0578251f8e1" [[package]] name = "webpki-roots" -version = "0.26.9" +version = "0.26.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "29aad86cec885cafd03e8305fd727c418e970a521322c91688414d5b8efba16b" +checksum = "521bc38abb08001b01866da9f51eb7c5d647a19260e00054a8c7fd5f9e57f7a9" +dependencies = [ + "webpki-roots 1.0.0", +] + +[[package]] +name = "webpki-roots" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2853738d1cc4f2da3a225c18ec6c3721abb31961096e9dbf5ab35fa88b19cfdb" dependencies = [ "rustls-pki-types", ] [[package]] name = "weezl" -version = "0.1.8" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53a85b86a771b1c87058196170769dd264f66c0782acf1ae6cc51bfd64b39082" +checksum = "a751b3277700db47d3e574514de2eced5e54dc8a5436a3bf7a0b248b2cee16f3" [[package]] name = "which" @@ -9540,49 +9488,48 @@ dependencies = [ [[package]] name = "windows" -version = "0.58.0" +version = "0.61.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dd04d41d93c4992d421894c18c8b43496aa748dd4c081bac0dc93eb0489272b6" +checksum = "c5ee8f3d025738cb02bad7868bbb5f8a6327501e870bf51f1b455b0a2454a419" dependencies = [ - "windows-core 0.58.0", - "windows-targets 0.52.6", -] - -[[package]] -name = "windows-core" -version = "0.58.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ba6d44ec8c2591c134257ce647b7ea6b20335bf6379a27dac5f1641fcf59f99" -dependencies = [ - "windows-implement 0.58.0", - "windows-interface 0.58.0", - "windows-result 0.2.0", - "windows-strings 0.1.0", - "windows-targets 0.52.6", -] - -[[package]] -name = "windows-core" -version = "0.61.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4763c1de310c86d75a878046489e2e5ba02c649d185f21c67d4cf8a56d098980" -dependencies = [ - "windows-implement 0.60.0", - "windows-interface 0.59.1", + "windows-collections", + "windows-core", + "windows-future", "windows-link", - "windows-result 0.3.2", - "windows-strings 0.4.0", + "windows-numerics", ] [[package]] -name = "windows-implement" -version = "0.58.0" +name = "windows-collections" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2bbd5b46c938e506ecbce286b6628a02171d56153ba733b6c741fc627ec9579b" +checksum = "3beeceb5e5cfd9eb1d76b381630e82c4241ccd0d27f1a39ed41b2760b255c5e8" dependencies = [ - "proc-macro2", - "quote 1.0.40", - "syn 2.0.101", + "windows-core", +] + +[[package]] +name = "windows-core" +version = "0.61.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c0fdd3ddb90610c7638aa2b3a3ab2904fb9e5cdbecc643ddb3647212781c4ae3" +dependencies = [ + "windows-implement", + "windows-interface", + "windows-link", + "windows-result", + "windows-strings 0.4.2", +] + +[[package]] +name = "windows-future" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc6a41e98427b19fe4b73c550f060b59fa592d7d686537eebf9385621bfbad8e" +dependencies = [ + "windows-core", + "windows-link", + "windows-threading", ] [[package]] @@ -9596,17 +9543,6 @@ dependencies = [ "syn 2.0.101", ] -[[package]] -name = "windows-interface" -version = "0.58.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "053c4c462dc91d3b1504c6fe5a726dd15e216ba718e84a0e46a88fbe5ded3515" -dependencies = [ - "proc-macro2", - "quote 1.0.40", - "syn 2.0.101", -] - [[package]] name = "windows-interface" version = "0.59.1" @@ -9624,45 +9560,36 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76840935b766e1b0a05c0066835fb9ec80071d4c09a16f6bd5f7e655e3c14c38" +[[package]] +name = "windows-numerics" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9150af68066c4c5c07ddc0ce30421554771e528bde427614c61038bc2c92c2b1" +dependencies = [ + "windows-core", + "windows-link", +] + [[package]] name = "windows-registry" version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4286ad90ddb45071efd1a66dfa43eb02dd0dfbae1545ad6cc3c51cf34d7e8ba3" dependencies = [ - "windows-result 0.3.2", + "windows-result", "windows-strings 0.3.1", "windows-targets 0.53.0", ] [[package]] name = "windows-result" -version = "0.2.0" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d1043d8214f791817bab27572aaa8af63732e11bf84aa21a45a78d6c317ae0e" -dependencies = [ - "windows-targets 0.52.6", -] - -[[package]] -name = "windows-result" -version = "0.3.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c64fd11a4fd95df68efcfee5f44a294fe71b8bc6a91993e2791938abcc712252" +checksum = "56f42bd332cc6c8eac5af113fc0c1fd6a8fd2aa08a0119358686e5160d0586c6" dependencies = [ "windows-link", ] -[[package]] -name = "windows-strings" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4cd9b125c486025df0eabcb585e62173c6c9eddcec5d117d3b6e8c30e2ee4d10" -dependencies = [ - "windows-result 0.2.0", - "windows-targets 0.52.6", -] - [[package]] name = "windows-strings" version = "0.3.1" @@ -9674,9 +9601,9 @@ dependencies = [ [[package]] name = "windows-strings" -version = "0.4.0" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a2ba9642430ee452d5a7aa78d72907ebe8cfda358e8cb7918a2050581322f97" +checksum = "56e6c93f3a0c3b36176cb1327a4958a0353d5d166c2a35cb268ace15e91d3b57" dependencies = [ "windows-link", ] @@ -9755,6 +9682,15 @@ dependencies = [ "windows_x86_64_msvc 0.53.0", ] +[[package]] +name = "windows-threading" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b66463ad2e0ea3bbf808b7f1d371311c80e115c0b71d60efc142cafbcfb057a6" +dependencies = [ + "windows-link", +] + [[package]] name = "windows_aarch64_gnullvm" version = "0.48.5" @@ -9904,9 +9840,9 @@ dependencies = [ [[package]] name = "winnow" -version = "0.7.7" +version = "0.7.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6cb8234a863ea0e8cd7284fcdd4f145233eb00fee02bbdd9861aec44e6477bc5" +checksum = "c06928c8748d81b05c9be96aad92e1b6ff01833332f281e8cfca3be4b35fc9ec" dependencies = [ "memchr", ] @@ -9927,20 +9863,14 @@ version = "0.39.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", ] -[[package]] -name = "write16" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d1890f4022759daae28ed4fe62859b1236caebfc61ede2f63ed4e695f3f6d936" - [[package]] name = "writeable" -version = "0.5.5" +version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" +checksum = "ea2f10b9bb0928dfb1b42b65e1f9e36f7f54dbdf08457afefb38afcdec4fa2bb" [[package]] name = "wyz" @@ -9983,9 +9913,9 @@ dependencies = [ [[package]] name = "yoke" -version = "0.7.5" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "120e6aef9aa629e3d4f52dc8cc43a015c7724194c97dfaf45180d2daf2b77f40" +checksum = "5f41bb01b8226ef4bfd589436a297c53d118f65921786300e427be8d487695cc" dependencies = [ "serde", "stable_deref_trait", @@ -9995,14 +9925,14 @@ dependencies = [ [[package]] name = "yoke-derive" -version = "0.7.5" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" +checksum = "38da3c9736e16c5d3c8c597a9aaa5d1fa565d0532ae05e27c24aa62fb32c0ab6" dependencies = [ "proc-macro2", "quote 1.0.40", "syn 2.0.101", - "synstructure 0.13.1", + "synstructure 0.13.2", ] [[package]] @@ -10027,38 +9957,18 @@ dependencies = [ "serde", "serde_json", "time", - "tokio 1.44.2", + "tokio 1.45.1", "tower-service", "url", ] -[[package]] -name = "zerocopy" -version = "0.7.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b9b4fd18abc82b8136838da5d50bae7bdea537c574d8dc1a34ed098d6c166f0" -dependencies = [ - "zerocopy-derive 0.7.35", -] - [[package]] name = "zerocopy" version = "0.8.25" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a1702d9583232ddb9174e01bb7c15a2ab8fb1bc6f227aa1233858c351a3ba0cb" dependencies = [ - "zerocopy-derive 0.8.25", -] - -[[package]] -name = "zerocopy-derive" -version = "0.7.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e" -dependencies = [ - "proc-macro2", - "quote 1.0.40", - "syn 2.0.101", + "zerocopy-derive", ] [[package]] @@ -10090,7 +10000,7 @@ dependencies = [ "proc-macro2", "quote 1.0.40", "syn 2.0.101", - "synstructure 0.13.1", + "synstructure 0.13.2", ] [[package]] @@ -10100,10 +10010,21 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ced3678a2879b30306d323f4542626697a464a97c0a07c9aebf7ebca65cd4dde" [[package]] -name = "zerovec" -version = "0.10.4" +name = "zerotrie" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa2b893d79df23bfb12d5461018d408ea19dfafe76c2c7ef6d4eba614f8ff079" +checksum = "36f0bbd478583f79edad978b407914f61b2972f5af6fa089686016be8f9af595" +dependencies = [ + "displaydoc", + "yoke", + "zerofrom", +] + +[[package]] +name = "zerovec" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4a05eb080e015ba39cc9e23bbe5e7fb04d5fb040350f99f34e338d5fdd294428" dependencies = [ "yoke", "zerofrom", @@ -10112,9 +10033,9 @@ dependencies = [ [[package]] name = "zerovec-derive" -version = "0.10.3" +version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" +checksum = "5b96237efa0c878c64bd89c436f661be4e46b2f3eff1ebb976f7ef2321d2f58f" dependencies = [ "proc-macro2", "quote 1.0.40", diff --git a/Cargo.toml b/Cargo.toml index 6c69df09..19808e67 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,7 +6,6 @@ members = [ "crates/bonfire", "crates/core/*", "crates/services/*", - "crates/bindings/*", "crates/daemons/*", ] @@ -16,6 +15,6 @@ redis23 = { package = "redis", version = "0.23.3", git = "https://github.com/rev # I'm 99% sure this is overloading the GitHub worker # hence builds have been failing since, let's just # disable it for now. In the future, we could use this -# if we were rolling our own CI. -# [profile.release] -# lto = true +# if we were rolling our own CI (that is now). +[profile.release] +lto = true diff --git a/Dockerfile b/Dockerfile index c75748c2..524e7e0e 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,5 +1,5 @@ # Build Stage -FROM --platform="${BUILDPLATFORM}" rust:1.77.2-slim-bookworm +FROM --platform="${BUILDPLATFORM}" rust:1.86.0-slim-bookworm USER 0:0 WORKDIR /home/rust/src @@ -17,13 +17,13 @@ RUN sh /tmp/build-image-layer.sh tools # Build all dependencies COPY Cargo.toml Cargo.lock ./ -COPY crates/bindings/node/Cargo.toml ./crates/bindings/node/ COPY crates/bonfire/Cargo.toml ./crates/bonfire/ COPY crates/delta/Cargo.toml ./crates/delta/ COPY crates/core/config/Cargo.toml ./crates/core/config/ COPY crates/core/database/Cargo.toml ./crates/core/database/ COPY crates/core/files/Cargo.toml ./crates/core/files/ COPY crates/core/models/Cargo.toml ./crates/core/models/ +COPY crates/core/parser/Cargo.toml ./crates/core/parser/ COPY crates/core/permissions/Cargo.toml ./crates/core/permissions/ COPY crates/core/presence/Cargo.toml ./crates/core/presence/ COPY crates/core/result/Cargo.toml ./crates/core/result/ diff --git a/Dockerfile.useCurrentArch b/Dockerfile.useCurrentArch index 54b508ef..f36c0808 100644 --- a/Dockerfile.useCurrentArch +++ b/Dockerfile.useCurrentArch @@ -1,5 +1,5 @@ # Build Stage -FROM rust:1.77.2-slim-bookworm +FROM rust:1.86.0-slim-bookworm USER 0:0 WORKDIR /home/rust/src @@ -13,13 +13,13 @@ COPY scripts/build-image-layer.sh /tmp/ # Build all dependencies COPY Cargo.toml Cargo.lock ./ -COPY crates/bindings/node/Cargo.toml ./crates/bindings/node/ COPY crates/bonfire/Cargo.toml ./crates/bonfire/ COPY crates/delta/Cargo.toml ./crates/delta/ COPY crates/core/config/Cargo.toml ./crates/core/config/ COPY crates/core/database/Cargo.toml ./crates/core/database/ COPY crates/core/files/Cargo.toml ./crates/core/files/ COPY crates/core/models/Cargo.toml ./crates/core/models/ +COPY crates/core/parser/Cargo.toml ./crates/core/parser/ COPY crates/core/permissions/Cargo.toml ./crates/core/permissions/ COPY crates/core/presence/Cargo.toml ./crates/core/presence/ COPY crates/core/result/Cargo.toml ./crates/core/result/ diff --git a/README.md b/README.md index d0894dee..1973ee20 100644 --- a/README.md +++ b/README.md @@ -12,32 +12,31 @@ The services and libraries that power the Revolt service.

-| Crate | Path | Description | | -| ------------------ | -------------------------------------------------- | ---------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `core/config` | [crates/core/config](crates/core/config) | Core: Configuration | ![Crates.io Version](https://img.shields.io/crates/v/revolt-config) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-config) ![Crates.io Version](https://img.shields.io/crates/size/revolt-config) ![Crates.io License](https://img.shields.io/crates/l/revolt-config) | -| `core/database` | [crates/core/database](crates/core/database) | Core: Database Implementation | ![Crates.io Version](https://img.shields.io/crates/v/revolt-database) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-database) ![Crates.io Version](https://img.shields.io/crates/size/revolt-database) ![Crates.io License](https://img.shields.io/crates/l/revolt-database) | -| `core/files` | [crates/core/files](crates/core/files) | Core: S3 and encryption subroutines | ![Crates.io Version](https://img.shields.io/crates/v/revolt-files) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-files) ![Crates.io Version](https://img.shields.io/crates/size/revolt-files) ![Crates.io License](https://img.shields.io/crates/l/revolt-files) | -| `core/models` | [crates/core/models](crates/core/models) | Core: API Models | ![Crates.io Version](https://img.shields.io/crates/v/revolt-models) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-models) ![Crates.io Version](https://img.shields.io/crates/size/revolt-models) ![Crates.io License](https://img.shields.io/crates/l/revolt-models) | -| `core/permissions` | [crates/core/permissions](crates/core/permissions) | Core: Permission Logic | ![Crates.io Version](https://img.shields.io/crates/v/revolt-permissions) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-permissions) ![Crates.io Version](https://img.shields.io/crates/size/revolt-permissions) ![Crates.io License](https://img.shields.io/crates/l/revolt-permissions) | -| `core/presence` | [crates/core/presence](crates/core/presence) | Core: User Presence | ![Crates.io Version](https://img.shields.io/crates/v/revolt-presence) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-presence) ![Crates.io Version](https://img.shields.io/crates/size/revolt-presence) ![Crates.io License](https://img.shields.io/crates/l/revolt-presence) | -| `core/result` | [crates/core/result](crates/core/result) | Core: Result and Error types | ![Crates.io Version](https://img.shields.io/crates/v/revolt-result) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-result) ![Crates.io Version](https://img.shields.io/crates/size/revolt-result) ![Crates.io License](https://img.shields.io/crates/l/revolt-result) | -| `delta` | [crates/delta](crates/delta) | REST API server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `bonfire` | [crates/bonfire](crates/bonfire) | WebSocket events server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `services/january` | [crates/services/january](crates/services/january) | Proxy server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `services/autumn` | [crates/services/autumn](crates/services/autumn) | File server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `bindings/node` | [crates/bindings/node](crates/bindings/node) | Node.js bindings for the Revolt software | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `daemons/crond` | [crates/daemons/crond](crates/daemons/crond) | Timed data clean up daemon server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | -| `daemons/pushd` | [crates/daemons/pushd](crates/daemons/pushd) | Push notification daemon server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| Crate | Path | Description | | +| ------------------ | -------------------------------------------------- | ----------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `core/config` | [crates/core/config](crates/core/config) | Core: Configuration | ![Crates.io Version](https://img.shields.io/crates/v/revolt-config) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-config) ![Crates.io Version](https://img.shields.io/crates/size/revolt-config) ![Crates.io License](https://img.shields.io/crates/l/revolt-config) | +| `core/database` | [crates/core/database](crates/core/database) | Core: Database Implementation | ![Crates.io Version](https://img.shields.io/crates/v/revolt-database) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-database) ![Crates.io Version](https://img.shields.io/crates/size/revolt-database) ![Crates.io License](https://img.shields.io/crates/l/revolt-database) | +| `core/files` | [crates/core/files](crates/core/files) | Core: S3 and encryption subroutines | ![Crates.io Version](https://img.shields.io/crates/v/revolt-files) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-files) ![Crates.io Version](https://img.shields.io/crates/size/revolt-files) ![Crates.io License](https://img.shields.io/crates/l/revolt-files) | +| `core/models` | [crates/core/models](crates/core/models) | Core: API Models | ![Crates.io Version](https://img.shields.io/crates/v/revolt-models) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-models) ![Crates.io Version](https://img.shields.io/crates/size/revolt-models) ![Crates.io License](https://img.shields.io/crates/l/revolt-models) | +| `core/permissions` | [crates/core/permissions](crates/core/permissions) | Core: Permission Logic | ![Crates.io Version](https://img.shields.io/crates/v/revolt-permissions) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-permissions) ![Crates.io Version](https://img.shields.io/crates/size/revolt-permissions) ![Crates.io License](https://img.shields.io/crates/l/revolt-permissions) | +| `core/presence` | [crates/core/presence](crates/core/presence) | Core: User Presence | ![Crates.io Version](https://img.shields.io/crates/v/revolt-presence) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-presence) ![Crates.io Version](https://img.shields.io/crates/size/revolt-presence) ![Crates.io License](https://img.shields.io/crates/l/revolt-presence) | +| `core/result` | [crates/core/result](crates/core/result) | Core: Result and Error types | ![Crates.io Version](https://img.shields.io/crates/v/revolt-result) ![Crates.io Version](https://img.shields.io/crates/msrv/revolt-result) ![Crates.io Version](https://img.shields.io/crates/size/revolt-result) ![Crates.io License](https://img.shields.io/crates/l/revolt-result) | +| `delta` | [crates/delta](crates/delta) | REST API server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| `bonfire` | [crates/bonfire](crates/bonfire) | WebSocket events server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| `services/january` | [crates/services/january](crates/services/january) | Proxy server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| `services/autumn` | [crates/services/autumn](crates/services/autumn) | File server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| `daemons/crond` | [crates/daemons/crond](crates/daemons/crond) | Timed data clean up daemon server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) | +| `daemons/pushd` | [crates/daemons/pushd](crates/daemons/pushd) | Push notification daemon server | ![License](https://img.shields.io/badge/license-AGPL--3.0--or--later-blue) |
## Minimum Supported Rust Version -Rust 1.76 or higher. +Rust 1.86.0 or higher. > [!CAUTION] -> The events server has a significant performance regression between Rust 1.77.2 and 1.78.0 onwards, see [issue #341](https://github.com/revoltchat/backend/issues/341). +> The events server has a significant performance regression between Rust 1.77.2 and 1.78.0 onwards, see [issue #341](https://github.com/revoltchat/backend/issues/341). This is currently solved by build time options but we are looking for a proper fix. ## Development Guide diff --git a/Revolt.toml b/Revolt.toml index 2f7988c9..76f908f3 100644 --- a/Revolt.toml +++ b/Revolt.toml @@ -43,6 +43,7 @@ from_address = "development@revolt.chat" reply_to = "support@revolt.chat" port = 14025 use_tls = false +use_starttls = false [api.livekit] diff --git a/crates/bindings/node/.gitignore b/crates/bindings/node/.gitignore deleted file mode 100644 index c76a159c..00000000 --- a/crates/bindings/node/.gitignore +++ /dev/null @@ -1,7 +0,0 @@ -target -index.node -**/node_modules -**/.DS_Store -npm-debug.log* -cargo.log -cross.log diff --git a/crates/bindings/node/Cargo.toml b/crates/bindings/node/Cargo.toml deleted file mode 100644 index e2cfba1c..00000000 --- a/crates/bindings/node/Cargo.toml +++ /dev/null @@ -1,25 +0,0 @@ -[package] -name = "revolt-nodejs-bindings" -version = "0.8.4" -description = "Node.js bindings for the Revolt software" -authors = ["Paul Makles "] -license = "MIT" -edition = "2021" -exclude = ["index.node"] - -[lib] -crate-type = ["cdylib"] - -# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html - -[dependencies] -neon = "1.0.0" -neon-serde4 = "1.0.0" - -serde = { version = "1", features = ["derive"] } - -async-std = "1.12.0" - -revolt-config = { version = "0.8.4", path = "../../core/config" } -revolt-result = { version = "0.8.4", path = "../../core/result" } -revolt-database = { version = "0.8.4", path = "../../core/database" } diff --git a/crates/bindings/node/README.md b/crates/bindings/node/README.md deleted file mode 100644 index f2ccee6e..00000000 --- a/crates/bindings/node/README.md +++ /dev/null @@ -1,92 +0,0 @@ -# revolt.node - -**revolt.node:** Node.js bindings for the Revolt software - -This project was bootstrapped by [create-neon](https://www.npmjs.com/package/create-neon). - -## Building revolt.node - -Building revolt.node requires a [supported version of Node and Rust](https://github.com/neon-bindings/neon#platform-support). - -To run the build, run: - -```sh -$ npm run build -``` - -This command uses the [@neon-rs/cli](https://www.npmjs.com/package/@neon-rs/cli) utility to assemble the binary Node addon from the output of `cargo`. - -## Exploring revolt.node - -After building revolt.node, you can explore its exports at the Node console: - -```sh -$ npm i -$ npm run build -$ node -> require('.').hello() -'hello node' -``` - -## Available Scripts - -In the project directory, you can run: - -#### `npm install` - -Installs the project, including running `npm run build`. - -#### `npm run build` - -Builds the Node addon (`index.node`) from source, generating a release build with `cargo --release`. - -Additional [`cargo build`](https://doc.rust-lang.org/cargo/commands/cargo-build.html) arguments may be passed to `npm run build` and similar commands. For example, to enable a [cargo feature](https://doc.rust-lang.org/cargo/reference/features.html): - -``` -npm run build -- --feature=beetle -``` - -#### `npm run debug` - -Similar to `npm run build` but generates a debug build with `cargo`. - -#### `npm run cross` - -Similar to `npm run build` but uses [cross-rs](https://github.com/cross-rs/cross) to cross-compile for another platform. Use the [`CARGO_BUILD_TARGET`](https://doc.rust-lang.org/cargo/reference/config.html#buildtarget) environment variable to select the build target. - -#### `npm test` - -Runs the unit tests by calling `cargo test`. You can learn more about [adding tests to your Rust code](https://doc.rust-lang.org/book/ch11-01-writing-tests.html) from the [Rust book](https://doc.rust-lang.org/book/). - -## Project Layout - -The directory structure of this project is: - -``` -revolt.node/ -├── Cargo.toml -├── README.md -├── src/ -| └── lib.rs -├── index.node -├── package.json -└── target/ -``` - -| Entry | Purpose | -|----------------|------------------------------------------------------------------------------------------------------------------------------------------| -| `Cargo.toml` | The Cargo [manifest file](https://doc.rust-lang.org/cargo/reference/manifest.html), which informs the `cargo` command. | -| `README.md` | This file. | -| `src/` | The directory tree containing the Rust source code for the project. | -| `lib.rs` | Entry point for the Rust source code. | -| `index.node` | The main module, a [Node addon](https://nodejs.org/api/addons.html) generated by the build and pointed to by `"main"` in `package.json`. | -| `package.json` | The npm [manifest file](https://docs.npmjs.com/cli/v7/configuring-npm/package-json), which informs the `npm` command. | -| `target/` | Binary artifacts generated by the Rust build. | - -## Learn More - -Learn more about: - -- [Neon](https://neon-bindings.com). -- [Rust](https://www.rust-lang.org). -- [Node](https://nodejs.org). diff --git a/crates/bindings/node/index.d.ts b/crates/bindings/node/index.d.ts deleted file mode 100644 index 0417ba4d..00000000 --- a/crates/bindings/node/index.d.ts +++ /dev/null @@ -1,84 +0,0 @@ -import { Channel, User } from "revolt-api"; - -/** - * Opaque type for Revolt database - */ -export declare interface Database {} - -/** - * Opaque type for Revolt database - */ -export declare interface OpaqueUser {} - -/** - * Error type from Revolt backend - */ -export declare interface Err { - type: string; - location: string; -} - -/** - * Initialises background tasks and logging, must be called before anything else! - * Can be called multiple times! - */ -export declare function init(); - -/** - * Gets a new handle to the Revolt database - * @returns {Database} Handle - */ -export declare function database(): Database; - -/** - * Fetch user from database - * @param {string} userId User's ID - * @this {Database} - */ -export declare function database_fetch_user(userId: string): OpaqueUser; - -/** - * Fetch user from database - * @param {string} username Username - * @param {string} discriminator Discriminator - * @this {Database} - */ -export declare function database_fetch_user_by_username( - username: string, - discriminator: string -): OpaqueUser; - -/** - * Gets model data as JSON - * @this {OpaqueUser} - */ -export declare function model_data(): User; - -/** - * Gets error if the model failed to fetch - * @this {OpaqueUser} - */ -export declare function model_error(): Err; - -/** - * Open a direct message channel between two users - * @param {string} userA User A ID - * @param {string} userB User B ID - * @returns Existing or newly created channel - */ -export declare function proc_channels_create_dm( - userA: string, - userB: string -): Promise; - -/** - * Suspend a user - * @param {string} user User - * @param {number} duration Duration (in days), set to 0 for indefinite - * @param {string} reason Pipe-separated list of reasons (e.g. reason1|reason2|reason3) - */ -export declare function proc_users_suspend( - user: OpaqueUser, - duration: number, - reason: string -): Promise<{ error: Err }>; diff --git a/crates/bindings/node/package.json b/crates/bindings/node/package.json deleted file mode 100644 index 70768a86..00000000 --- a/crates/bindings/node/package.json +++ /dev/null @@ -1,36 +0,0 @@ -{ - "name": "revolt-nodejs-bindings", - "version": "0.7.15-rev0.0.3", - "description": "Node.js bindings for the Revolt software", - "main": "index.node", - "scripts": { - "test": "cargo test", - "cargo-build": "cargo build --message-format=json > cargo.log", - "cross-build": "cross build --message-format=json > cross.log", - "postcargo-build": "neon dist < cargo.log", - "postcross-build": "neon dist -m /target < cross.log", - "debug": "npm run cargo-build --", - "build": "npm run cargo-build -- --release", - "cross": "npm run cross-build -- --release" - }, - "author": "Paul Makles", - "license": "AGPL-3.0", - "devDependencies": { - "@neon-rs/cli": "0.1.73" - }, - "repository": { - "type": "git", - "url": "git+https://github.com/revoltchat/backend" - }, - "keywords": [ - "revolt", - "chat" - ], - "bugs": { - "url": "https://github.com/revoltchat/backend/issues" - }, - "homepage": "https://github.com/revoltchat/backend#readme", - "dependencies": { - "revolt-api": "^0.7.15" - } -} \ No newline at end of file diff --git a/crates/bindings/node/pnpm-lock.yaml b/crates/bindings/node/pnpm-lock.yaml deleted file mode 100644 index 1d623ad9..00000000 --- a/crates/bindings/node/pnpm-lock.yaml +++ /dev/null @@ -1,117 +0,0 @@ -lockfileVersion: '6.0' - -settings: - autoInstallPeers: true - excludeLinksFromLockfile: false - -dependencies: - revolt-api: - specifier: ^0.7.15 - version: 0.7.15 - -devDependencies: - '@neon-rs/cli': - specifier: 0.1.73 - version: 0.1.73 - -packages: - - /@cargo-messages/android-arm-eabi@0.1.72: - resolution: {integrity: sha512-gGZxIM1mj+Y5x+ULND6ZCNr7f70OJi9wDlycSK8hGONy9wrChN6JAIHryddC5cqcwlYAoQ6IDcDFElnhAYbybA==} - cpu: [arm] - os: [android] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/darwin-arm64@0.1.72: - resolution: {integrity: sha512-EAzN5MLaXPljZKZDO5qR+aBs44eSq2ZbEnS7AI/FziE3MzeXbrGOS3fLba5+7yWPFXJyZolXzePm8N1EBv8ovg==} - cpu: [arm64] - os: [darwin] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/darwin-x64@0.1.72: - resolution: {integrity: sha512-RLo6j8s3nYbjdd1LDct4wamfChyRit7zokUuxtIYCu9XOlltkN5vnj1vwnrPvoqCMZ/7CbbuHFwSTn9A71de/w==} - cpu: [x64] - os: [darwin] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/linux-arm-gnueabihf@0.1.72: - resolution: {integrity: sha512-tHsRshuzfjrX6SDW3jg6al8vMNLTMgczGnVYl5RuBZf/yrAUuwe30KxA9ge6w6mW6Ox797DyBchzAc9OLgTgmQ==} - cpu: [arm] - os: [linux] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/linux-x64-gnu@0.1.72: - resolution: {integrity: sha512-VGtL6CCnUbhsP4aYuBNT5kfrAL7o0qjrxw97a+ax13t+nJd26tVEEIKHMu5drvvS/Nm/hn7sLT8zMnnCv0pvHg==} - cpu: [x64] - os: [linux] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/win32-arm64-msvc@0.1.72: - resolution: {integrity: sha512-V93Cgz39K+yqa3MveNbhh29pYCp8izK5uEavjPoxlNxAbsMCWH+s0verGDdUcfGxjR1H2V7oZ4FszPqR2SqMRQ==} - cpu: [arm64] - os: [win32] - requiresBuild: true - dev: true - optional: true - - /@cargo-messages/win32-x64-msvc@0.1.72: - resolution: {integrity: sha512-knz3uSrO0OSbq3U5VWfCY8FB4NsM43BOWLZ7x4sfaMOC1XWv+IyvDdkLe6DhJx8KUw46KIAimYs9YROrp6l46Q==} - cpu: [x64] - os: [win32] - requiresBuild: true - dev: true - optional: true - - /@neon-rs/cli@0.1.73: - resolution: {integrity: sha512-1kv8S/feB6UQWQQwsnGfkSkEBOtlFDNExnioL81E2BwvUWgjQPaseHgpi2EpWVgsPUgur5eBm4QowmlpWkD4/w==} - hasBin: true - optionalDependencies: - '@cargo-messages/android-arm-eabi': 0.1.72 - '@cargo-messages/darwin-arm64': 0.1.72 - '@cargo-messages/darwin-x64': 0.1.72 - '@cargo-messages/linux-arm-gnueabihf': 0.1.72 - '@cargo-messages/linux-x64-gnu': 0.1.72 - '@cargo-messages/win32-arm64-msvc': 0.1.72 - '@cargo-messages/win32-x64-msvc': 0.1.72 - dev: true - - /axios@0.26.1: - resolution: {integrity: sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==} - dependencies: - follow-redirects: 1.15.6 - transitivePeerDependencies: - - debug - dev: false - - /follow-redirects@1.15.6: - resolution: {integrity: sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA==} - engines: {node: '>=4.0'} - peerDependencies: - debug: '*' - peerDependenciesMeta: - debug: - optional: true - dev: false - - /lodash.defaultsdeep@4.6.1: - resolution: {integrity: sha512-3j8wdDzYuWO3lM3Reg03MuQR957t287Rpcxp1njpEa8oDrikb+FwGdW3n+FELh/A6qib6yPit0j/pv9G/yeAqA==} - dev: false - - /revolt-api@0.7.15: - resolution: {integrity: sha512-rWRnjBFvoXt/RHRxHg9KuP+x1Jk61KdsOpKOczVJg5tIqGDmqp/6QZHw5rJTtG+wCH3Ah3YKwY+MM5NHfg1W3Q==} - dependencies: - axios: 0.26.1 - lodash.defaultsdeep: 4.6.1 - transitivePeerDependencies: - - debug - dev: false diff --git a/crates/bindings/node/src/lib.rs b/crates/bindings/node/src/lib.rs deleted file mode 100644 index 85b39183..00000000 --- a/crates/bindings/node/src/lib.rs +++ /dev/null @@ -1,221 +0,0 @@ -#[macro_use] -extern crate serde; - -use std::sync::OnceLock; - -use neon::prelude::*; -use revolt_database::{Database, DatabaseInfo}; - -fn js_init(mut cx: FunctionContext) -> JsResult { - // static INIT: OnceLock<()> = OnceLock::new(); - // if INIT.get().is_none() { - // INIT.get_or_init(|| { - // async_std::task::block_on(async { - // revolt_config::configure!(api); - - // match DatabaseInfo::Auto.connect().await { - // Ok(db) => { - // let authifier_db = db.clone().to_authifier().await.database; - // revolt_database::tasks::start_workers(db, authifier_db); - // Ok(()) - // } - // Err(err) => Err(err), - // } - // }) - // .or_else(|err| cx.throw_error(err)) - // .unwrap(); - // }); - // } - - Ok(cx.undefined()) -} - -struct DatabaseBinding(Database, Channel); -impl Finalize for DatabaseBinding {} -impl DatabaseBinding { - fn take(&self) -> (Database, Channel) { - (self.0.clone(), self.1.clone()) - } -} - -fn js_database(mut cx: FunctionContext) -> JsResult> { - let db = async_std::task::block_on(DatabaseInfo::Auto.connect()) - .or_else(|err| cx.throw_error(err))?; - - let channel = cx.channel(); - Ok(cx.boxed(DatabaseBinding(db, channel))) -} - -// Implementations for models -#[derive(Clone)] -#[allow(clippy::large_enum_variant)] -enum Model { - User(revolt_database::User), - Error(revolt_result::Error), -} - -impl Model { - fn give(&self) -> Model { - self.clone() - } -} - -impl Finalize for Model {} - -macro_rules! shim_boxed { - ($cx: ident, $name: ident, $model: ident, $( $variable: ident $type: ident $id: expr )+, $cmd: ident, $( $arg: expr, )+) => { - fn $name(mut cx: FunctionContext) -> JsResult { - $( - let $variable = cx.argument::<$type>($id)?.value(&mut cx); - )+ - - let (db, channel) = cx.this::>()?.take(); - let (deferred, promise) = cx.promise(); - - async_std::task::spawn(async move { - let result = db.$cmd($($arg,)+).await; - deferred.settle_with(&channel, move |mut cx| { - Ok(cx.boxed(match result { - Ok(value) => Model::$model(value), - Err(error) => Model::Error(error) - })) - }) - }); - - Ok(promise) - } - - $cx.export_function(stringify!($name), $name)?; - }; -} - -fn js_data(mut cx: FunctionContext) -> JsResult { - match cx.this::>()?.give() { - Model::Error(_) => neon_serde4::to_value(&mut cx, &None::<()>), - Model::User(user) => neon_serde4::to_value(&mut cx, &user), - } - .or_else(|e| cx.throw_error(e.to_string())) -} - -fn js_error(mut cx: FunctionContext) -> JsResult { - let value = match cx.this::>()?.give() { - Model::Error(err) => Some(err), - _ => None, - }; - - neon_serde4::to_value(&mut cx, &value).or_else(|e| cx.throw_error(e.to_string())) -} - -// Basic data implementation -#[derive(Serialize, Deserialize)] -struct ResultBinding { - #[serde(flatten)] - value: Option, - error: Option, -} - -macro_rules! shim { - ($cx: ident, $name: ident, $( $variable: ident $type: ident $id: expr )*, $( $model: ident $modelType: ident $modelId: expr )*, | $db: ident | $closure: expr, $( $arg: expr, )+) => { - fn $name(mut cx: FunctionContext) -> JsResult { - $( - let $variable = cx.argument::<$type>($id)?.value(&mut cx); - )* - - $( - let mut $model = if let Model::$modelType(value) = cx.argument::>($modelId)?.give() { - value - } else { - unreachable!() - }; - )* - - let (db, channel) = cx.this::>()?.take(); - let (deferred, promise) = cx.promise(); - - async_std::task::spawn(async move { - #[allow(clippy::redundant_closure_call)] - let result = (|$db: $crate::Database| $closure)(db.clone()).await; - deferred.settle_with(&channel, move |mut cx| { - neon_serde4::to_value( - &mut cx, - &match result { - Ok(value) => ResultBinding { - value: Some(value), - error: None, - }, - Err(error) => ResultBinding { - value: None, - error: Some(error), - }, - }, - ) - .or_else(|e| cx.throw_error(e.to_string())) - }) - }); - - Ok(promise) - } - - $cx.export_function(stringify!($name), $name)?; - }; -} - -#[neon::main] -fn main(mut cx: ModuleContext) -> NeonResult<()> { - // initialise required background stuff - cx.export_function("init", js_init)?; - - // database & model stuff - cx.export_function("database", js_database)?; - cx.export_function("model_data", js_data)?; - cx.export_function("model_error", js_error)?; - - shim_boxed!( - cx, - database_fetch_user, - User, - user_id JsString 0, - fetch_user, - &user_id, - ); - - shim_boxed!( - cx, - database_fetch_user_by_username, - User, - username JsString 0 - discriminator JsString 1, - fetch_user_by_username, - &username, &discriminator, - ); - - // procedure calls - shim!( - cx, - proc_channels_create_dm, - user_a JsString 0 - user_b JsString 1, - , - |db| async move { - let user_a = db.fetch_user(&user_a).await?; - let user_b = db.fetch_user(&user_b).await?; - revolt_database::Channel::create_dm(&db, &user_a, &user_b).await - }, - &userA, &userB, - ); - - shim!( - cx, - proc_users_suspend, - duration JsNumber 1 - reason JsString 2, - user User 0, - |db| async move { - let duration = duration as usize; - user.suspend(&db, if duration == 0 { None } else { Some(duration) }, Some(reason.split('|').map(|x| x.to_owned()).collect())).await - }, - &user, - ); - - Ok(()) -} diff --git a/crates/bindings/node/test.js b/crates/bindings/node/test.js deleted file mode 100644 index d8f60174..00000000 --- a/crates/bindings/node/test.js +++ /dev/null @@ -1,53 +0,0 @@ -const Internal = require("."); - -// playing around with class wrapper, not practical -class Model { - constructor(model) { - this.model = model; - } - - data() { - return Internal.model_data.bind(this.model)(); - } - - error() { - return Internal.model_error.bind(this.model)(); - } -} - -class User extends Model { - constructor(db, user) { - super(user); - this.db = db; - } -} - -class Database { - constructor() { - this.db = Internal.database(); - } - - async fetchUser(userId) { - return new User( - this, - await Internal.database_fetch_user.bind(this.db)(userId) - ); - } - - async fetchUserByUsername(username, discriminator) { - return new User( - this, - await Internal.database_fetch_user_by_username.bind(this.db)( - username, - discriminator - ) - ); - } -} - -const db = new Database(); -db.fetchUserByUsername("dos", "7624").then((user) => console.info(user.data())); -db.fetchUserByUsername("dos", "1111").then((user) => console.info(user.data())); -db.fetchUserByUsername("dos", "1111").then((user) => - console.info(user.error()) -); diff --git a/crates/bindings/package-lock.json b/crates/bindings/package-lock.json deleted file mode 100644 index 9376d3a9..00000000 --- a/crates/bindings/package-lock.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "name": "bindings", - "lockfileVersion": 3, - "requires": true, - "packages": {} -} diff --git a/crates/bonfire/Cargo.toml b/crates/bonfire/Cargo.toml index be3f6edc..1f38becf 100644 --- a/crates/bonfire/Cargo.toml +++ b/crates/bonfire/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-bonfire" -version = "0.8.4" +version = "0.8.7" license = "AGPL-3.0-or-later" edition = "2021" @@ -36,12 +36,12 @@ async-std = { version = "1.8.0", features = [ ] } # core -authifier = { version = "1.0.10" } +authifier = { version = "1.0.15" } revolt-result = { path = "../core/result" } revolt-models = { path = "../core/models" } revolt-config = { path = "../core/config" } revolt-database = { path = "../core/database" } -revolt-permissions = { version = "0.8.4", path = "../core/permissions" } +revolt-permissions = { version = "0.8.7", path = "../core/permissions" } revolt-presence = { path = "../core/presence", features = ["redis-is-patched"] } # redis diff --git a/crates/bonfire/src/events/impl.rs b/crates/bonfire/src/events/impl.rs index 6605d46d..e2bd1456 100644 --- a/crates/bonfire/src/events/impl.rs +++ b/crates/bonfire/src/events/impl.rs @@ -103,6 +103,18 @@ impl State { let user = self.clone_user(); self.cache.is_bot = user.bot.is_some(); + // Fetch pending policy changes. + let policy_changes = if user.bot.is_some() { + vec![] + } else { + db.fetch_policy_changes() + .await? + .into_iter() + .filter(|policy| policy.created_time > user.last_acknowledged_policy_change) + .map(Into::into) + .collect() + }; + // Find all relationships to the user. let mut user_ids: HashSet = user .relations @@ -178,7 +190,7 @@ impl State { .iter() .find(|e| matches!(e, ReadyPayloadFields::UserSettings(_))) { - Some(db.fetch_user_settings(&user.id, &keys).await?) + Some(db.fetch_user_settings(&user.id, keys).await?) } else { None }; @@ -202,12 +214,11 @@ impl State { .collect(); // Make all users appear from our perspective. - let mut users: Vec = join_all(users - .into_iter() - .map(|other_user| async { - let is_online = online_ids.contains(&other_user.id); - other_user.into_known(&user, is_online).await - })).await; + let mut users: Vec = join_all(users.into_iter().map(|other_user| async { + let is_online = online_ids.contains(&other_user.id); + other_user.into_known(&user, is_online).await + })) + .await; // Make sure we see our own user correctly. users.push(user.into_self(true).await); @@ -273,6 +284,8 @@ impl State { user_settings, channel_unreads: channel_unreads.map(|vec| vec.into_iter().map(Into::into).collect()), + + policy_changes, }) } diff --git a/crates/bonfire/src/websocket.rs b/crates/bonfire/src/websocket.rs index 810befbf..dbebfdbd 100644 --- a/crates/bonfire/src/websocket.rs +++ b/crates/bonfire/src/websocket.rs @@ -3,7 +3,7 @@ use std::{collections::HashSet, net::SocketAddr, sync::Arc}; use async_tungstenite::WebSocketStream; use authifier::AuthifierEvent; use fred::{ - error::{RedisError, RedisErrorKind}, + error::RedisErrorKind, interfaces::{ClientLike, EventInterface, PubsubInterface}, types::RedisConfig, }; diff --git a/crates/core/config/Cargo.toml b/crates/core/config/Cargo.toml index 00c8a00c..7254866f 100644 --- a/crates/core/config/Cargo.toml +++ b/crates/core/config/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-config" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "MIT" authors = ["Paul Makles "] @@ -9,9 +9,10 @@ description = "Revolt Backend: Configuration" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [features] +anyhow = ["dep:sentry-anyhow"] report-macros = ["revolt-result"] test = ["async-std"] -default = ["test"] +default = ["test", "anyhow"] [dependencies] # Utility @@ -32,6 +33,7 @@ pretty_env_logger = "0.4.0" # Sentry sentry = "0.31.5" +sentry-anyhow = { version = "0.38.1", optional = true } # Core -revolt-result = { version = "0.8.4", path = "../result", optional = true } +revolt-result = { version = "0.8.7", path = "../result", optional = true } diff --git a/crates/core/config/Revolt.toml b/crates/core/config/Revolt.toml index 469abe29..e3e8ec97 100644 --- a/crates/core/config/Revolt.toml +++ b/crates/core/config/Revolt.toml @@ -56,6 +56,8 @@ authifier_shield_key = "" voso_legacy_token = "" # Whether services are behind the Cloudflare network trust_cloudflare = false +# easypwned endpoint +easypwned = "" [api.security.captcha] # hCaptcha configuration @@ -279,4 +281,5 @@ events = "" voice_ingress = "" files = "" proxy = "" +pushd = "" crond = "" diff --git a/crates/core/config/src/lib.rs b/crates/core/config/src/lib.rs index 16c39837..d5b1d187 100644 --- a/crates/core/config/src/lib.rs +++ b/crates/core/config/src/lib.rs @@ -7,6 +7,7 @@ use once_cell::sync::Lazy; use serde::Deserialize; pub use sentry::{capture_error, capture_message, Level}; +pub use sentry_anyhow::capture_anyhow; #[cfg(feature = "report-macros")] #[macro_export] @@ -122,6 +123,7 @@ pub struct ApiSmtp { pub reply_to: Option, pub port: Option, pub use_tls: Option, + pub use_starttls: Option, } #[derive(Deserialize, Debug, Clone)] @@ -167,6 +169,7 @@ pub struct ApiSecurity { pub voso_legacy_token: String, pub captcha: ApiSecurityCaptcha, pub trust_cloudflare: bool, + pub easypwned: String, } #[derive(Deserialize, Debug, Clone)] @@ -190,7 +193,7 @@ pub struct LiveKitNode { #[derive(Deserialize, Debug, Clone)] pub struct ApiUsers { - pub early_adopter_cutoff: Option + pub early_adopter_cutoff: Option, } #[derive(Deserialize, Debug, Clone)] @@ -356,6 +359,7 @@ pub struct Sentry { pub voice_ingress: String, pub files: String, pub proxy: String, + pub pushd: String, pub crond: String, } diff --git a/crates/core/database/Cargo.toml b/crates/core/database/Cargo.toml index e6f0eafe..61119d24 100644 --- a/crates/core/database/Cargo.toml +++ b/crates/core/database/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-database" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" authors = ["Paul Makles "] @@ -24,19 +24,19 @@ default = ["mongodb", "async-std-runtime", "tasks"] [dependencies] # Core -revolt-config = { version = "0.8.4", path = "../config", features = [ +revolt-config = { version = "0.8.7", path = "../config", features = [ "report-macros", ] } -revolt-result = { version = "0.8.4", path = "../result" } -revolt-models = { version = "0.8.4", path = "../models", features = [ +revolt-result = { version = "0.8.7", path = "../result" } +revolt-models = { version = "0.8.7", path = "../models", features = [ "validator", ] } -revolt-presence = { version = "0.8.4", path = "../presence" } -revolt-permissions = { version = "0.8.4", path = "../permissions", features = [ +revolt-presence = { version = "0.8.7", path = "../presence" } +revolt-permissions = { version = "0.8.7", path = "../permissions", features = [ "serde", "bson", ] } -revolt-parser = { version = "0.1.0", path = "../parser" } +revolt-parser = { version = "0.8.7", path = "../parser" } # Utility log = "0.4" @@ -97,7 +97,7 @@ web-push = "0.10.0" revolt_a2 = { version = "0.10", default-features = false, features = ["ring"] } # Authifier -authifier = { version = "1.0.10", features = ["rocket_impl"] } +authifier = { version = "1.0.15", features = ["rocket_impl"] } # RabbitMQ amqprs = { version = "1.7.0" } diff --git a/crates/core/database/src/drivers/mod.rs b/crates/core/database/src/drivers/mod.rs index f3ffbede..e0573484 100644 --- a/crates/core/database/src/drivers/mod.rs +++ b/crates/core/database/src/drivers/mod.rs @@ -3,6 +3,7 @@ mod reference; use authifier::config::Captcha; use authifier::config::EmailVerificationConfig; +use authifier::config::PasswordScanning; use authifier::config::ResolveIp; use authifier::config::SMTPSettings; use authifier::config::Shield; @@ -102,6 +103,13 @@ impl Database { let config = config().await; let mut auth_config = authifier::Config { + password_scanning: if config.api.security.easypwned.is_empty() { + Default::default() + } else { + PasswordScanning::EasyPwned { + endpoint: config.api.security.easypwned, + } + }, email_verification: if !config.api.smtp.host.is_empty() { EmailVerificationConfig::Enabled { smtp: SMTPSettings { @@ -118,6 +126,7 @@ impl Database { ), port: config.api.smtp.port, use_tls: config.api.smtp.use_tls, + use_starttls: config.api.smtp.use_starttls, }, expiry: Default::default(), templates: if config.production { @@ -134,6 +143,15 @@ impl Database { url: format!("{}/login/reset/", config.hosts.app), html: Some(include_str!("../../templates/reset.html").into()), }, + reset_existing: Template { + title: "You already have a Revolt account, reset your password." + .into(), + text: include_str!("../../templates/reset-existing.txt").into(), + url: format!("{}/login/reset/", config.hosts.app), + html: Some( + include_str!("../../templates/reset-existing.html").into(), + ), + }, deletion: Template { title: "Confirm account deletion.".into(), text: include_str!("../../templates/deletion.txt").into(), @@ -156,9 +174,16 @@ impl Database { url: format!("{}/login/reset/", config.hosts.app), html: None, }, + reset_existing: Template { + title: "Reset your password.".into(), + text: include_str!("../../templates/reset.whitelabel.txt").into(), + url: format!("{}/login/reset/", config.hosts.app), + html: None, + }, deletion: Template { title: "Confirm account deletion.".into(), - text: include_str!("../../templates/deletion.whitelabel.txt").into(), + text: include_str!("../../templates/deletion.whitelabel.txt") + .into(), url: format!("{}/delete/", config.hosts.app), html: None, }, diff --git a/crates/core/database/src/drivers/reference.rs b/crates/core/database/src/drivers/reference.rs index 6d243666..e02eae64 100644 --- a/crates/core/database/src/drivers/reference.rs +++ b/crates/core/database/src/drivers/reference.rs @@ -4,8 +4,8 @@ use futures::lock::Mutex; use crate::{ Bot, Channel, ChannelCompositeKey, ChannelUnread, Emoji, File, FileHash, Invite, Member, - MemberCompositeKey, Message, RatelimitEvent, Report, Server, ServerBan, Snapshot, User, - UserSettings, Webhook, + MemberCompositeKey, Message, PolicyChange, RatelimitEvent, Report, Server, ServerBan, Snapshot, + User, UserSettings, Webhook, }; database_derived!( @@ -21,6 +21,7 @@ database_derived!( pub file_hashes: Arc>>, pub files: Arc>>, pub messages: Arc>>, + pub policy_changes: Arc>>, pub ratelimit_events: Arc>>, pub user_settings: Arc>>, pub users: Arc>>, diff --git a/crates/core/database/src/events/client.rs b/crates/core/database/src/events/client.rs index 22ef110f..3937b3b3 100644 --- a/crates/core/database/src/events/client.rs +++ b/crates/core/database/src/events/client.rs @@ -3,7 +3,7 @@ use revolt_result::Error; use serde::{Deserialize, Serialize}; use revolt_models::v0::{ - AppendMessage, Channel, ChannelUnread, ChannelVoiceState, Emoji, FieldsChannel, FieldsMember, FieldsMessage, FieldsRole, FieldsServer, FieldsUser, FieldsWebhook, Member, MemberCompositeKey, Message, PartialChannel, PartialMember, PartialMessage, PartialRole, PartialServer, PartialUser, PartialUserVoiceState, PartialWebhook, RemovalIntention, Report, Server, User, UserSettings, UserVoiceState, Webhook + AppendMessage, Channel, ChannelUnread, ChannelVoiceState, Emoji, FieldsChannel, FieldsMember, FieldsMessage, FieldsRole, FieldsServer, FieldsUser, FieldsWebhook, Member, MemberCompositeKey, Message, PartialChannel, PartialMember, PartialMessage, PartialRole, PartialServer, PartialUser, PartialUserVoiceState, PartialWebhook, PolicyChange, RemovalIntention, Report, Server, User, UserSettings, UserVoiceState, Webhook }; use crate::Database; @@ -62,6 +62,8 @@ pub enum EventV1 { user_settings: Option, #[serde(skip_serializing_if = "Option::is_none")] channel_unreads: Option>, + + policy_changes: Vec, }, /// Ping response diff --git a/crates/core/database/src/models/admin_migrations/ops/mongodb/init.rs b/crates/core/database/src/models/admin_migrations/ops/mongodb/init.rs index 00fe26b8..4a422cbb 100644 --- a/crates/core/database/src/models/admin_migrations/ops/mongodb/init.rs +++ b/crates/core/database/src/models/admin_migrations/ops/mongodb/init.rs @@ -64,6 +64,10 @@ pub async fn create_database(db: &MongoDb) { .await .expect("Failed to create user_settings collection."); + db.create_collection("policy_changes") + .await + .expect("Failed to create policy_changes collection."); + db.create_collection("safety_reports") .await .expect("Failed to create safety_reports collection."); diff --git a/crates/core/database/src/models/admin_migrations/ops/mongodb/scripts.rs b/crates/core/database/src/models/admin_migrations/ops/mongodb/scripts.rs index ea65c2af..72b03dbf 100644 --- a/crates/core/database/src/models/admin_migrations/ops/mongodb/scripts.rs +++ b/crates/core/database/src/models/admin_migrations/ops/mongodb/scripts.rs @@ -5,10 +5,11 @@ use crate::{ bson::{doc, from_bson, from_document, to_document, Bson, DateTime, Document}, options::FindOptions, }, - AbstractChannels, AbstractServers, Channel, Invite, MongoDb, DISCRIMINATOR_SEARCH_SPACE, + AbstractChannels, AbstractServers, Channel, Invite, MongoDb, User, DISCRIMINATOR_SEARCH_SPACE, }; -use bson::oid::ObjectId; +use bson::{oid::ObjectId, to_bson}; use futures::StreamExt; +use iso8601_timestamp::Timestamp; use rand::seq::SliceRandom; use revolt_permissions::DEFAULT_WEBHOOK_PERMISSIONS; use revolt_result::{Error, ErrorType}; @@ -21,7 +22,7 @@ struct MigrationInfo { revision: i32, } -pub const LATEST_REVISION: i32 = 33; +pub const LATEST_REVISION: i32 = 43; // MUST BE +1 to last migration pub async fn migrate_database(db: &MongoDb) { let migrations = db.col::("migrations"); @@ -1131,6 +1132,42 @@ pub async fn run_migrations(db: &MongoDb, revision: i32) -> i32 { } if revision <= 32 { + info!( + "Running migration [revision 32 / 12-05-2025]: (Authifier) Add last_seen to sessions." + ); + + let db = authifier::Database::MongoDb(authifier::database::MongoDb(db.db())); + db.run_migration(authifier::Migration::M2025_02_20AddLastSeenToSession) + .await + .unwrap(); + } + + if revision <= 40 { + info!( + "Running migration [revision |> 40 / 30-05-2025]: Set last policy acknowlegement date to now and create policy changes collection." + ); + + db.db() + .create_collection("policy_changes") + .await + .expect("Failed to create policy_changes collection."); + + db.db() + .collection::("users") + .update_many( + doc! {}, + doc! { + "$set": { + "last_acknowledged_policy_change": to_bson(&Timestamp::now_utc()) + .expect("failed to serialise timestamp") + } + }, + ) + .await + .expect("failed to update users"); + } + + if revision <= 41 { info!("Running migration [revision 32 / 26-01-2025]: Add `is_publishing` and `is_receiving` to members"); db.col::("server_members") @@ -1147,7 +1184,7 @@ pub async fn run_migrations(db: &MongoDb, revision: i32) -> i32 { .expect("Failed to update members"); } - if revision <= 33 { + if revision <= 42 { info!("Running migration [revision 33 / 29-04-2025]: Convert all `VoiceChannel`'s into `TextChannel` "); db.col::("channels") diff --git a/crates/core/database/src/models/bots/model.rs b/crates/core/database/src/models/bots/model.rs index 0a796049..24c56bb1 100644 --- a/crates/core/database/src/models/bots/model.rs +++ b/crates/core/database/src/models/bots/model.rs @@ -1,4 +1,3 @@ -use revolt_config::config; use revolt_result::Result; use ulid::Ulid; diff --git a/crates/core/database/src/models/channel_webhooks/model.rs b/crates/core/database/src/models/channel_webhooks/model.rs index b163cbfe..cdf94db4 100644 --- a/crates/core/database/src/models/channel_webhooks/model.rs +++ b/crates/core/database/src/models/channel_webhooks/model.rs @@ -142,7 +142,7 @@ mod tests { ..Default::default() }; - db.insert_webhook(&webhook).await.unwrap(); + webhook.create(&db).await.unwrap(); let mut updated_webhook = webhook.clone(); updated_webhook diff --git a/crates/core/database/src/models/channels/model.rs b/crates/core/database/src/models/channels/model.rs index 797da5af..1c1edafd 100644 --- a/crates/core/database/src/models/channels/model.rs +++ b/crates/core/database/src/models/channels/model.rs @@ -338,13 +338,10 @@ impl Channel { db.insert_channel(&channel).await?; - match &channel { - Channel::DirectMessage { .. } => { - let event = EventV1::ChannelCreate(channel.clone().into()); - event.clone().private(user_a.id.clone()).await; - event.private(user_b.id.clone()).await; - } - _ => {} + if let Channel::DirectMessage { .. } = &channel { + let event = EventV1::ChannelCreate(channel.clone().into()); + event.clone().private(user_a.id.clone()).await; + event.private(user_b.id.clone()).await; }; Ok(channel) diff --git a/crates/core/database/src/models/file_hashes/model.rs b/crates/core/database/src/models/file_hashes/model.rs index 46a249f0..cec7a39d 100644 --- a/crates/core/database/src/models/file_hashes/model.rs +++ b/crates/core/database/src/models/file_hashes/model.rs @@ -28,7 +28,7 @@ auto_derived_partial!( /// Size of this file (in bytes) pub size: isize, }, - "PartialFile" + "PartialFileHash" ); auto_derived!( diff --git a/crates/core/database/src/models/messages/model.rs b/crates/core/database/src/models/messages/model.rs index a5bef95c..458eb927 100644 --- a/crates/core/database/src/models/messages/model.rs +++ b/crates/core/database/src/models/messages/model.rs @@ -5,7 +5,7 @@ use iso8601_timestamp::Timestamp; use revolt_config::{config, FeaturesLimits}; use revolt_models::v0::{ self, BulkMessageResponse, DataMessageSend, Embed, MessageAuthor, MessageFlags, MessageSort, - MessageWebhook, PushNotification, ReplyIntent, SendableEmbed, Text + MessageWebhook, PushNotification, ReplyIntent, SendableEmbed, Text, }; use revolt_permissions::{calculate_channel_permissions, ChannelPermission, PermissionValue}; use revolt_result::{ErrorType, Result}; @@ -288,9 +288,9 @@ impl Message { .map_err(|_| create_error!(InvalidOperation))?; // Check the message is not empty - if (data.content.as_ref().map_or(true, |v| v.is_empty())) - && (data.attachments.as_ref().map_or(true, |v| v.is_empty())) - && (data.embeds.as_ref().map_or(true, |v| v.is_empty())) + if (data.content.as_ref().is_none_or(|v| v.is_empty())) + && (data.attachments.as_ref().is_none_or(|v| v.is_empty())) + && (data.embeds.as_ref().is_none_or(|v| v.is_empty())) { return Err(create_error!(EmptyMessage)); } @@ -384,7 +384,7 @@ impl Message { mut user_mentions, mut role_mentions, mut mentions_everyone, - mut mentions_online + mut mentions_online, } = message_mentions; if allow_mass_mentions && server_id.is_some() && !role_mentions.is_empty() { @@ -492,7 +492,9 @@ impl Message { let valid_members = db.fetch_members(server.as_str(), &mentions_vec[..]).await; if let Ok(valid_members) = valid_members { - let valid_mentions = HashSet::<&String, RandomState>::from_iter(valid_members.iter().map(|m| &m.id.user)); + let valid_mentions = HashSet::<&String, RandomState>::from_iter( + valid_members.iter().map(|m| &m.id.user), + ); user_mentions.retain(|m| valid_mentions.contains(m)); // quick pass, validate mentions are in the server @@ -506,7 +508,8 @@ impl Message { .members_can_see_channel() .await; - user_mentions.retain(|m| *member_channel_view_perms.get(m).unwrap_or(&false)); + user_mentions + .retain(|m| *member_channel_view_perms.get(m).unwrap_or(&false)); } } else { revolt_config::capture_error(&valid_members.unwrap_err()); @@ -520,7 +523,9 @@ impl Message { } if !user_mentions.is_empty() { - message.mentions.replace(user_mentions.into_iter().collect()); + message + .mentions + .replace(user_mentions.into_iter().collect()); } if !role_mentions.is_empty() { @@ -654,7 +659,7 @@ impl Message { pub async fn send( &mut self, db: &Database, - amqp: Option<&AMQP>, // this is optional mostly for tests. + _amqp: Option<&AMQP>, // this is optional mostly for tests. author: MessageAuthor<'_>, user: Option, member: Option, diff --git a/crates/core/database/src/models/mod.rs b/crates/core/database/src/models/mod.rs index 671c7abb..181a30c0 100644 --- a/crates/core/database/src/models/mod.rs +++ b/crates/core/database/src/models/mod.rs @@ -8,6 +8,7 @@ mod emojis; mod file_hashes; mod files; mod messages; +mod policy_changes; mod ratelimit_events; mod safety_reports; mod safety_snapshots; @@ -27,6 +28,7 @@ pub use emojis::*; pub use file_hashes::*; pub use files::*; pub use messages::*; +pub use policy_changes::*; pub use ratelimit_events::*; pub use safety_reports::*; pub use safety_snapshots::*; @@ -51,6 +53,7 @@ pub trait AbstractDatabase: + file_hashes::AbstractAttachmentHashes + files::AbstractAttachments + messages::AbstractMessages + + policy_changes::AbstractPolicyChange + ratelimit_events::AbstractRatelimitEvents + safety_reports::AbstractReport + safety_snapshots::AbstractSnapshot diff --git a/crates/core/database/src/models/policy_changes/mod.rs b/crates/core/database/src/models/policy_changes/mod.rs new file mode 100644 index 00000000..4d801b73 --- /dev/null +++ b/crates/core/database/src/models/policy_changes/mod.rs @@ -0,0 +1,5 @@ +mod model; +mod ops; + +pub use model::*; +pub use ops::*; diff --git a/crates/core/database/src/models/policy_changes/model.rs b/crates/core/database/src/models/policy_changes/model.rs new file mode 100644 index 00000000..54109505 --- /dev/null +++ b/crates/core/database/src/models/policy_changes/model.rs @@ -0,0 +1,20 @@ +use iso8601_timestamp::Timestamp; + +auto_derived!( + /// Platform policy change + pub struct PolicyChange { + /// Unique Id + #[serde(rename = "_id")] + pub id: String, + + /// Time at which this policy was created + pub created_time: Timestamp, + /// Time at which this policy is effective + pub effective_time: Timestamp, + + /// Message shown to users + pub description: String, + /// URL with details about changes + pub url: String, + } +); diff --git a/crates/core/database/src/models/policy_changes/ops.rs b/crates/core/database/src/models/policy_changes/ops.rs new file mode 100644 index 00000000..2692a81f --- /dev/null +++ b/crates/core/database/src/models/policy_changes/ops.rs @@ -0,0 +1,15 @@ +use revolt_result::Result; + +use crate::PolicyChange; + +mod mongodb; +mod reference; + +#[async_trait] +pub trait AbstractPolicyChange: Sync + Send { + /// Fetch all policy changes + async fn fetch_policy_changes(&self) -> Result>; + + /// Acknowledge policy changes + async fn acknowledge_policy_changes(&self, user_id: &str) -> Result<()>; +} diff --git a/crates/core/database/src/models/policy_changes/ops/mongodb.rs b/crates/core/database/src/models/policy_changes/ops/mongodb.rs new file mode 100644 index 00000000..fb70646f --- /dev/null +++ b/crates/core/database/src/models/policy_changes/ops/mongodb.rs @@ -0,0 +1,46 @@ +use bson::to_bson; +use iso8601_timestamp::Timestamp; +use revolt_result::Result; + +use crate::MongoDb; +use crate::PolicyChange; +use crate::User; + +use super::AbstractPolicyChange; + +static COL: &str = "policy_changes"; + +#[async_trait] +impl AbstractPolicyChange for MongoDb { + /// Fetch all policy changes + async fn fetch_policy_changes(&self) -> Result> { + query!(self, find, COL, doc! {}) + } + + /// Acknowledge policy changes + async fn acknowledge_policy_changes(&self, user_id: &str) -> Result<()> { + let latest_policy = self + .fetch_policy_changes() + .await? + .into_iter() + .map(|policy| policy.created_time) + .max() + .unwrap_or(Timestamp::UNIX_EPOCH); + + self.col::("users") + .update_one( + doc! { + "_id": user_id + }, + doc! { + "$set": { + "last_acknowledged_policy_change": to_bson(&latest_policy) + .map_err(|_| create_database_error!("to_bson", "timestamp"))? + } + }, + ) + .await + .map(|_| ()) + .map_err(|_| create_database_error!("update_one", COL)) + } +} diff --git a/crates/core/database/src/models/policy_changes/ops/reference.rs b/crates/core/database/src/models/policy_changes/ops/reference.rs new file mode 100644 index 00000000..e9745e44 --- /dev/null +++ b/crates/core/database/src/models/policy_changes/ops/reference.rs @@ -0,0 +1,31 @@ +use iso8601_timestamp::Timestamp; +use revolt_result::Result; + +use crate::PolicyChange; +use crate::ReferenceDb; + +use super::AbstractPolicyChange; + +#[async_trait] +impl AbstractPolicyChange for ReferenceDb { + /// Fetch all policy changes + async fn fetch_policy_changes(&self) -> Result> { + let policy_changes = self.policy_changes.lock().await; + Ok(policy_changes.values().cloned().collect()) + } + + /// Acknowledge policy changes + async fn acknowledge_policy_changes(&self, user_id: &str) -> Result<()> { + let mut users = self.users.lock().await; + let user = users.get_mut(user_id).expect("user doesn't exist"); + user.last_acknowledged_policy_change = self + .fetch_policy_changes() + .await? + .into_iter() + .map(|policy| policy.created_time) + .max() + .unwrap_or(Timestamp::UNIX_EPOCH); + + Ok(()) + } +} diff --git a/crates/core/database/src/models/safety_snapshots/model.rs b/crates/core/database/src/models/safety_snapshots/model.rs index e82ab388..e277f3a9 100644 --- a/crates/core/database/src/models/safety_snapshots/model.rs +++ b/crates/core/database/src/models/safety_snapshots/model.rs @@ -85,8 +85,8 @@ impl SnapshotContent { Ok(( SnapshotContent::Message { message, - prior_context: prior_context.into_iter().map(Into::into).collect(), - leading_context: leading_context.into_iter().map(Into::into).collect(), + prior_context: prior_context.into_iter().collect(), + leading_context: leading_context.into_iter().collect(), }, files, )) diff --git a/crates/core/database/src/models/server_bans/model.rs b/crates/core/database/src/models/server_bans/model.rs index 46e8a889..51044efe 100644 --- a/crates/core/database/src/models/server_bans/model.rs +++ b/crates/core/database/src/models/server_bans/model.rs @@ -13,6 +13,7 @@ auto_derived!( } ); +#[allow(clippy::disallowed_methods)] impl ServerBan { /// Create ban pub async fn create( diff --git a/crates/core/database/src/models/server_members/model.rs b/crates/core/database/src/models/server_members/model.rs index da33644f..4e8521f1 100644 --- a/crates/core/database/src/models/server_members/model.rs +++ b/crates/core/database/src/models/server_members/model.rs @@ -180,7 +180,7 @@ impl Member { } /// Update member data - pub async fn update<'a>( + pub async fn update( &mut self, db: &Database, partial: PartialMember, diff --git a/crates/core/database/src/models/servers/model.rs b/crates/core/database/src/models/servers/model.rs index 67c4daed..33cfa713 100644 --- a/crates/core/database/src/models/servers/model.rs +++ b/crates/core/database/src/models/servers/model.rs @@ -285,7 +285,7 @@ impl Role { } /// Update server data - pub async fn update<'a>( + pub async fn update( &mut self, db: &Database, server_id: &str, diff --git a/crates/core/database/src/models/users/model.rs b/crates/core/database/src/models/users/model.rs index f52cf5ae..881cee30 100644 --- a/crates/core/database/src/models/users/model.rs +++ b/crates/core/database/src/models/users/model.rs @@ -9,7 +9,7 @@ use once_cell::sync::Lazy; use rand::seq::SliceRandom; use redis_kiss::{get_connection, AsyncCommands}; use revolt_config::{config, FeaturesLimits}; -use revolt_models::v0::{self, UserFlags, UserBadges}; +use revolt_models::v0::{self, UserBadges, UserFlags}; use revolt_presence::filter_online; use revolt_result::{create_error, Result}; use serde_json::json; @@ -58,6 +58,8 @@ auto_derived_partial!( /// Time until user is unsuspended #[serde(skip_serializing_if = "Option::is_none")] pub suspended_until: Option, + /// Last acknowledged policy change + pub last_acknowledged_policy_change: Timestamp, }, "PartialUser" ); @@ -179,6 +181,7 @@ impl Default for User { privileged: Default::default(), bot: Default::default(), suspended_until: Default::default(), + last_acknowledged_policy_change: Timestamp::UNIX_EPOCH, } } } @@ -201,6 +204,7 @@ impl User { id: account_id.into().unwrap_or_else(|| Ulid::new().to_string()), discriminator: User::find_discriminator(db, &username, None).await?, username, + last_acknowledged_policy_change: Timestamp::now_utc(), ..Default::default() }; @@ -350,16 +354,13 @@ impl User { ) -> Result> { let online_ids = filter_online(ids).await; - Ok(join_all( - db - .fetch_users(ids) - .await? - .into_iter() - .map(|user| async { + Ok( + join_all(db.fetch_users(ids).await?.into_iter().map(|user| async { let is_online = online_ids.contains(&user.id); user.into_known(perspective, is_online).await - }) - ).await) + })) + .await, + ) } /// Find a free discriminator for a given username @@ -653,7 +654,7 @@ impl User { } /// Update user data - pub async fn update<'a>( + pub async fn update( &mut self, db: &Database, partial: PartialUser, @@ -831,7 +832,7 @@ impl User { if let Some(cutoff) = config.api.users.early_adopter_cutoff { if Ulid::from_string(&self.id).unwrap().timestamp_ms() < cutoff { - return badges + UserBadges::EarlyAdopter as u32 + return badges + UserBadges::EarlyAdopter as u32; }; }; diff --git a/crates/core/database/src/models/users/schema.rs b/crates/core/database/src/models/users/schema.rs index d887b895..28f5e42e 100644 --- a/crates/core/database/src/models/users/schema.rs +++ b/crates/core/database/src/models/users/schema.rs @@ -6,7 +6,7 @@ use revolt_rocket_okapi::{ use crate::User; -impl<'r> OpenApiFromRequest<'r> for User { +impl OpenApiFromRequest<'_> for User { fn from_request_input( _gen: &mut OpenApiGenerator, _name: String, diff --git a/crates/core/database/src/tasks/ack.rs b/crates/core/database/src/tasks/ack.rs index 1d2aff38..c12e41f3 100644 --- a/crates/core/database/src/tasks/ack.rs +++ b/crates/core/database/src/tasks/ack.rs @@ -3,8 +3,8 @@ use crate::{Database, Message, AMQP}; use deadqueue::limited::Queue; use once_cell::sync::Lazy; +use revolt_config::capture_message; use revolt_models::v0::PushNotification; -use rocket::form::validate::Contains; use std::{ collections::{HashMap, HashSet}, time::Duration, @@ -65,6 +65,7 @@ pub async fn queue_ack(channel: String, user: String, event: AckEvent) { ); } +/// Do not add more than one message per event. pub async fn queue_message(channel: String, event: AckEvent) { Q.try_push(Data { channel, @@ -114,7 +115,7 @@ pub async fn handle_ack_event( } AckEvent::ProcessMessage { messages } => { let mut users: HashSet<&String> = HashSet::new(); - debug!( + info!( "Processing {} messages from channel {}", messages.len(), messages[0].1.channel @@ -125,7 +126,7 @@ pub async fn handle_ack_event( users.extend(recipents.iter()); }); - debug!("Found {} users to notify.", users.len()); + info!("Found {} users to notify.", users.len()); for user in users { let message_ids: Vec = messages @@ -143,7 +144,7 @@ pub async fn handle_ack_event( db.add_mention_to_unread(channel, user, &message_ids) .await?; } - debug!("Added {} mentions for user {}", message_ids.len(), &user); + info!("Added {} mentions for user {}", message_ids.len(), &user); } let mut mass_mentions = vec![]; @@ -232,7 +233,7 @@ pub async fn worker(db: Database, amqp: AMQP) { revolt_config::capture_error(&err); error!("{err:?} for {event:?}. ({user:?}, {channel})"); } else { - debug!("User {user:?} ack in {channel} with {event:?}"); + info!("User {user:?} ack in {channel} with {event:?}"); } } } @@ -247,6 +248,8 @@ pub async fn worker(db: Database, amqp: AMQP) { mut event, }) = Q.try_pop() { + info!("Took next ack from queue, now {} remaining", Q.len()); + let key: (Option, String, u8) = ( user, channel, @@ -261,24 +264,31 @@ pub async fn worker(db: Database, amqp: AMQP) { if let AckEvent::ProcessMessage { messages: existing } = &mut task.data.event { - // add the new message to the list of messages to be processed. - existing.append(new_data); + if let Some(new_event) = new_data.pop() { + // if the message contains a mass mention, do not delay it any further. + if new_event.1.contains_mass_push_mention() { + // add the new message to the list of messages to be processed. + existing.push(new_event); + task.run_immediately(); + continue; + } - // if the message contains a mass mention, do not delay it any further. - if new_data[0].1.contains_mass_push_mention() { - task.run_immediately(); - continue; - } + existing.push(new_event); - // put a cap on the amount of messages that can be queued, for particularly active channels - if (existing.length() as u16) - < revolt_config::config() - .await - .features - .advanced - .process_message_delay_limit - { - task.delay(); + // put a cap on the amount of messages that can be queued, for particularly active channels + if (existing.length() as u16) + < revolt_config::config() + .await + .features + .advanced + .process_message_delay_limit + { + task.delay(); + } + } else { + let err_msg = format!("Got zero-length message event: {event:?}"); + capture_message(&err_msg, revolt_config::Level::Warning); + info!("{err_msg}") } } else { panic!("Somehow got an ack message in the add mention arm"); diff --git a/crates/core/database/src/util/bridge/v0.rs b/crates/core/database/src/util/bridge/v0.rs index ab6246e4..6e658245 100644 --- a/crates/core/database/src/util/bridge/v0.rs +++ b/crates/core/database/src/util/bridge/v0.rs @@ -1,7 +1,8 @@ +use iso8601_timestamp::Timestamp; use revolt_models::v0::*; use revolt_permissions::{calculate_user_permissions, UserPermission}; -use crate::{util::permissions::DatabasePermissionQuery, Database, FileUsedFor}; +use crate::{util::permissions::DatabasePermissionQuery, Database}; impl crate::Bot { pub fn into_public_bot(self, user: crate::User) -> PublicBot { @@ -496,7 +497,7 @@ impl crate::Message { reactions: self.reactions, interactions: self.interactions.into(), masquerade: self.masquerade.map(Into::into), - flags: self.flags.map(|flags| flags as u32).unwrap_or_default(), + flags: self.flags.unwrap_or_default(), pinned: self.pinned, } } @@ -525,7 +526,7 @@ impl From for PartialMessage { reactions: value.reactions, interactions: value.interactions.map(Into::into), masquerade: value.masquerade.map(Into::into), - flags: value.flags.map(|flags| flags as u32), + flags: value.flags, pinned: value.pinned, } } @@ -606,6 +607,17 @@ impl From for crate::Masquerade { } } +impl From for PolicyChange { + fn from(value: crate::PolicyChange) -> Self { + PolicyChange { + created_time: value.created_time, + effective_time: value.effective_time, + description: value.description, + url: value.url, + } + } +} + impl From for Report { fn from(value: crate::Report) -> Self { Report { @@ -1209,6 +1221,7 @@ impl From for crate::User { privileged: value.privileged, bot: value.bot.map(Into::into), suspended_until: None, + last_acknowledged_policy_change: Timestamp::UNIX_EPOCH, } } } diff --git a/crates/core/database/src/util/bulk_permissions.rs b/crates/core/database/src/util/bulk_permissions.rs index 40260745..99dda7e6 100644 --- a/crates/core/database/src/util/bulk_permissions.rs +++ b/crates/core/database/src/util/bulk_permissions.rs @@ -87,7 +87,7 @@ impl<'z> BulkDatabasePermissionQuery<'z> { } } - pub fn channel(self, channel: &'z Channel) -> BulkDatabasePermissionQuery { + pub fn channel(self, channel: &'z Channel) -> BulkDatabasePermissionQuery<'z> { BulkDatabasePermissionQuery { channel: Some(channel.clone()), ..self @@ -109,7 +109,7 @@ impl<'z> BulkDatabasePermissionQuery<'z> { } } - pub fn members(self, members: &'z [Member]) -> BulkDatabasePermissionQuery { + pub fn members(self, members: &'z [Member]) -> BulkDatabasePermissionQuery<'z> { BulkDatabasePermissionQuery { members: Some(members.to_owned()), cached_member_perms: None, @@ -120,7 +120,7 @@ impl<'z> BulkDatabasePermissionQuery<'z> { } } - pub fn users(self, users: &'z [User]) -> BulkDatabasePermissionQuery { + pub fn users(self, users: &'z [User]) -> BulkDatabasePermissionQuery<'z> { BulkDatabasePermissionQuery { users: Some(users.to_owned()), cached_member_perms: None, diff --git a/crates/core/database/src/util/permissions.rs b/crates/core/database/src/util/permissions.rs index e3254e66..f5414396 100644 --- a/crates/core/database/src/util/permissions.rs +++ b/crates/core/database/src/util/permissions.rs @@ -308,16 +308,14 @@ impl PermissionQuery for DatabasePermissionQuery<'_> { /// Are we a recipient of this channel? async fn are_we_part_of_the_channel(&mut self) -> bool { - if let Some(channel) = &self.channel { - match channel { - Cow::Borrowed(Channel::DirectMessage { recipients, .. }) - | Cow::Owned(Channel::DirectMessage { recipients, .. }) - | Cow::Borrowed(Channel::Group { recipients, .. }) - | Cow::Owned(Channel::Group { recipients, .. }) => { - recipients.contains(&self.perspective.id) - } - _ => false, - } + if let Some( + Cow::Borrowed(Channel::DirectMessage { recipients, .. }) + | Cow::Owned(Channel::DirectMessage { recipients, .. }) + | Cow::Borrowed(Channel::Group { recipients, .. }) + | Cow::Owned(Channel::Group { recipients, .. }), + ) = &self.channel + { + recipients.contains(&self.perspective.id) } else { false } @@ -424,7 +422,7 @@ impl<'a> DatabasePermissionQuery<'a> { } /// Use user - pub fn user(self, user: &'a User) -> DatabasePermissionQuery { + pub fn user(self, user: &'a User) -> DatabasePermissionQuery<'a> { DatabasePermissionQuery { user: Some(Cow::Borrowed(user)), ..self @@ -432,7 +430,7 @@ impl<'a> DatabasePermissionQuery<'a> { } /// Use channel - pub fn channel(self, channel: &'a Channel) -> DatabasePermissionQuery { + pub fn channel(self, channel: &'a Channel) -> DatabasePermissionQuery<'a> { DatabasePermissionQuery { channel: Some(Cow::Borrowed(channel)), ..self @@ -440,7 +438,7 @@ impl<'a> DatabasePermissionQuery<'a> { } /// Use server - pub fn server(self, server: &'a Server) -> DatabasePermissionQuery { + pub fn server(self, server: &'a Server) -> DatabasePermissionQuery<'a> { DatabasePermissionQuery { server: Some(Cow::Borrowed(server)), ..self @@ -448,7 +446,7 @@ impl<'a> DatabasePermissionQuery<'a> { } /// Use member - pub fn member(self, member: &'a Member) -> DatabasePermissionQuery { + pub fn member(self, member: &'a Member) -> DatabasePermissionQuery<'a> { DatabasePermissionQuery { member: Some(Cow::Borrowed(member)), ..self diff --git a/crates/core/database/templates/reset-existing.html b/crates/core/database/templates/reset-existing.html new file mode 100644 index 00000000..00ef782b --- /dev/null +++ b/crates/core/database/templates/reset-existing.html @@ -0,0 +1,188 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/crates/core/database/templates/reset-existing.original.html b/crates/core/database/templates/reset-existing.original.html new file mode 100644 index 00000000..1273a69c --- /dev/null +++ b/crates/core/database/templates/reset-existing.original.html @@ -0,0 +1,41 @@ + + + + + + +
+ +
+

Password Reset

+

+ You tried to create a new account with or try to re-verify this email + but there is already an existing verified account under this email. +

+

+ If you wish, you can now proceed to reset the password on it, click + below to continue. +

+ Reset +
+
+ This email is intended for {{email}}
+ Sent from Revolt
+ Made in Europe +
+
+ Revolt Platforms Ltd. is a company incorporated and registered under the + laws of England and Wales.
+ Registered Company Number: 16260658
+ Registered Office:
+ Suite 5703 Unit 3A, 34-35 Hatton Garden,
+ Holborn, United Kingdom, EC1N 8DX +
+
+ + diff --git a/crates/core/database/templates/reset-existing.txt b/crates/core/database/templates/reset-existing.txt new file mode 100644 index 00000000..8c8fc9ed --- /dev/null +++ b/crates/core/database/templates/reset-existing.txt @@ -0,0 +1,19 @@ +You tried to create a new account with or try +to re-verify this email but there is already +an existing verified account under this email. + +If you wish, you can now proceed to reset the +password on it, click below to continue. + +Please navigate to: {{url}} + +This email is intended for {{email}} +Sent by Revolt +Made in Europe + +Revolt Platforms Ltd. is a company incorporated and registered under the laws of England and Wales. + +Registration Number: 16260658 +Registered Office: +Suite 5703 Unit 3A, 34-35 Hatton Garden, +Holborn, United Kingdom, EC1N 8DX diff --git a/crates/core/files/Cargo.toml b/crates/core/files/Cargo.toml index e8303136..4dfadeed 100644 --- a/crates/core/files/Cargo.toml +++ b/crates/core/files/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-files" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" authors = ["Paul Makles "] @@ -20,10 +20,10 @@ typenum = "1.17.0" aws-config = "1.5.5" aws-sdk-s3 = { version = "1.46.0", features = ["behavior-version-latest"] } -revolt-config = { version = "0.8.4", path = "../config", features = [ +revolt-config = { version = "0.8.7", path = "../config", features = [ "report-macros", ] } -revolt-result = { version = "0.8.4", path = "../result" } +revolt-result = { version = "0.8.7", path = "../result" } # image processing jxl-oxide = "0.8.1" diff --git a/crates/core/models/Cargo.toml b/crates/core/models/Cargo.toml index c2c667be..6c9dcf80 100644 --- a/crates/core/models/Cargo.toml +++ b/crates/core/models/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-models" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "MIT" authors = ["Paul Makles "] @@ -20,8 +20,8 @@ default = ["serde", "partials", "rocket"] [dependencies] # Core -revolt-config = { version = "0.8.4", path = "../config" } -revolt-permissions = { version = "0.8.4", path = "../permissions" } +revolt-config = { version = "0.8.7", path = "../config" } +revolt-permissions = { version = "0.8.7", path = "../permissions" } # Utility regex = "1.11" diff --git a/crates/core/models/src/v0/messages.rs b/crates/core/models/src/v0/messages.rs index aaf9dc78..442d4e5b 100644 --- a/crates/core/models/src/v0/messages.rs +++ b/crates/core/models/src/v0/messages.rs @@ -401,7 +401,7 @@ impl Interactions { } } -impl<'a> MessageAuthor<'a> { +impl MessageAuthor<'_> { pub fn id(&self) -> &str { match self { MessageAuthor::User(user) => &user.id, diff --git a/crates/core/models/src/v0/mod.rs b/crates/core/models/src/v0/mod.rs index 78540e32..0468493b 100644 --- a/crates/core/models/src/v0/mod.rs +++ b/crates/core/models/src/v0/mod.rs @@ -7,6 +7,7 @@ mod embeds; mod emojis; mod files; mod messages; +mod policy_changes; mod safety_reports; mod server_bans; mod server_members; @@ -23,6 +24,7 @@ pub use embeds::*; pub use emojis::*; pub use files::*; pub use messages::*; +pub use policy_changes::*; pub use safety_reports::*; pub use server_bans::*; pub use server_members::*; diff --git a/crates/core/models/src/v0/policy_changes.rs b/crates/core/models/src/v0/policy_changes.rs new file mode 100644 index 00000000..267618de --- /dev/null +++ b/crates/core/models/src/v0/policy_changes.rs @@ -0,0 +1,16 @@ +use iso8601_timestamp::Timestamp; + +auto_derived!( + /// Platform policy change + pub struct PolicyChange { + /// Time at which this policy was created + pub created_time: Timestamp, + /// Time at which this policy is effective + pub effective_time: Timestamp, + + /// Message shown to users + pub description: String, + /// URL with details about changes + pub url: String, + } +); diff --git a/crates/core/parser/Cargo.toml b/crates/core/parser/Cargo.toml index f9b0c700..3c0a15b5 100644 --- a/crates/core/parser/Cargo.toml +++ b/crates/core/parser/Cargo.toml @@ -1,7 +1,9 @@ [package] name = "revolt-parser" -version = "0.1.0" +version = "0.8.7" edition = "2021" +license = "AGPL-3.0-or-later" +description = "Revolt Backend: Message Parser" [dependencies] -logos = { version = "*" } \ No newline at end of file +logos = { version = "0.15" } diff --git a/crates/core/permissions/Cargo.toml b/crates/core/permissions/Cargo.toml index f2ffb04c..c4eb7262 100644 --- a/crates/core/permissions/Cargo.toml +++ b/crates/core/permissions/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-permissions" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "MIT" authors = ["Paul Makles "] @@ -21,7 +21,7 @@ async-std = { version = "1.8.0", features = ["attributes"] } [dependencies] # Core -revolt-result = { version = "0.8.4", path = "../result" } +revolt-result = { version = "0.8.7", path = "../result" } # Utility auto_ops = "0.3.0" diff --git a/crates/core/presence/Cargo.toml b/crates/core/presence/Cargo.toml index 3470514f..7ecb776a 100644 --- a/crates/core/presence/Cargo.toml +++ b/crates/core/presence/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-presence" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" authors = ["Paul Makles "] diff --git a/crates/core/result/Cargo.toml b/crates/core/result/Cargo.toml index b62d3dbf..816f5baa 100644 --- a/crates/core/result/Cargo.toml +++ b/crates/core/result/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-result" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "MIT" authors = ["Paul Makles "] diff --git a/crates/daemons/crond/Cargo.toml b/crates/daemons/crond/Cargo.toml index d394df0d..413a810e 100644 --- a/crates/daemons/crond/Cargo.toml +++ b/crates/daemons/crond/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-crond" -version = "0.8.4" +version = "0.8.7" license = "AGPL-3.0-or-later" authors = ["Paul Makles "] edition = "2021" @@ -16,7 +16,7 @@ log = "0.4" tokio = { version = "1" } # Core -revolt-database = { version = "0.8.4", path = "../../core/database" } -revolt-result = { version = "0.8.4", path = "../../core/result" } -revolt-config = { version = "0.8.4", path = "../../core/config" } -revolt-files = { version = "0.8.4", path = "../../core/files" } +revolt-database = { version = "0.8.7", path = "../../core/database" } +revolt-result = { version = "0.8.7", path = "../../core/result" } +revolt-config = { version = "0.8.7", path = "../../core/config" } +revolt-files = { version = "0.8.7", path = "../../core/files" } diff --git a/crates/daemons/pushd/Cargo.toml b/crates/daemons/pushd/Cargo.toml index 441fa87f..7800c4fd 100644 --- a/crates/daemons/pushd/Cargo.toml +++ b/crates/daemons/pushd/Cargo.toml @@ -1,19 +1,24 @@ [package] name = "revolt-pushd" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" [dependencies] -revolt-config = { version = "0.8.4", path = "../../core/config" } -revolt-database = { version = "0.8.4", path = "../../core/database" } -revolt-models = { version = "0.8.4", path = "../../core/models", features = [ +revolt-result = { version = "0.8.7", path = "../../core/result" } +revolt-config = { version = "0.8.7", path = "../../core/config", features = [ + "report-macros", +] } +revolt-database = { version = "0.8.7", path = "../../core/database" } +revolt-models = { version = "0.8.7", path = "../../core/models", features = [ "validator", ] } -revolt-presence = { version = "0.8.1", path = "../../core/presence", features = [ +revolt-presence = { version = "0.8.7", path = "../../core/presence", features = [ "redis-is-patched", ] } +anyhow = { version = "1.0.98" } + amqprs = { version = "1.7.0" } fcm_v1 = "0.3.0" web-push = "0.10.0" @@ -23,7 +28,7 @@ tokio = "1.39.2" async-trait = "0.1.81" ulid = "1.0.0" -authifier = "1.0.10" +authifier = "1.0.15" log = "0.4.11" pretty_env_logger = "0.4.0" diff --git a/crates/daemons/pushd/src/consumers/inbound/fr_accepted.rs b/crates/daemons/pushd/src/consumers/inbound/fr_accepted.rs index ff084a83..d525138c 100644 --- a/crates/daemons/pushd/src/consumers/inbound/fr_accepted.rs +++ b/crates/daemons/pushd/src/consumers/inbound/fr_accepted.rs @@ -7,6 +7,7 @@ use amqprs::{ consumer::AsyncConsumer, BasicProperties, Deliver, }; +use anyhow::Result; use async_trait::async_trait; use log::debug; use revolt_database::{events::rabbit::*, Database}; @@ -54,21 +55,16 @@ impl FRAcceptedConsumer { channel: None, } } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for FRAcceptedConsumer { - /// This consumer handles delegating messages into their respective platform queues. - async fn consume( + async fn consume_event( &mut self, - channel: &Channel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &Channel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: FRAcceptedPayload = serde_json::from_str(content.as_str()).unwrap(); + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: FRAcceptedPayload = serde_json::from_str(content.as_str())?; debug!("Received FR accept event"); @@ -111,11 +107,34 @@ impl AsyncConsumer for FRAcceptedConsumer { .insert("endpoint".to_string(), sub.endpoint.clone()); } - let payload = serde_json::to_string(&sendable).unwrap(); + let payload = serde_json::to_string(&sendable)?; publish_message(self, payload.into(), args).await; } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for FRAcceptedConsumer { + /// This consumer handles delegating messages into their respective platform queues. + async fn consume( + &mut self, + channel: &Channel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process friend request accepted event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/inbound/fr_received.rs b/crates/daemons/pushd/src/consumers/inbound/fr_received.rs index c52dfec1..f64bc92b 100644 --- a/crates/daemons/pushd/src/consumers/inbound/fr_received.rs +++ b/crates/daemons/pushd/src/consumers/inbound/fr_received.rs @@ -7,6 +7,7 @@ use amqprs::{ consumer::AsyncConsumer, BasicProperties, Deliver, }; +use anyhow::Result; use async_trait::async_trait; use log::debug; use revolt_database::{events::rabbit::*, Database}; @@ -54,21 +55,16 @@ impl FRReceivedConsumer { channel: None, } } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for FRReceivedConsumer { - /// This consumer handles delegating messages into their respective platform queues. - async fn consume( + async fn consume_event( &mut self, - channel: &Channel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &Channel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: FRReceivedPayload = serde_json::from_str(content.as_str()).unwrap(); + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: FRReceivedPayload = serde_json::from_str(content.as_str())?; debug!("Received FR received event"); @@ -111,11 +107,34 @@ impl AsyncConsumer for FRReceivedConsumer { .insert("endpoint".to_string(), sub.endpoint.clone()); } - let payload = serde_json::to_string(&sendable).unwrap(); + let payload = serde_json::to_string(&sendable)?; publish_message(self, payload.into(), args).await; } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for FRReceivedConsumer { + /// This consumer handles delegating messages into their respective platform queues. + async fn consume( + &mut self, + channel: &Channel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process friend request received event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/inbound/generic.rs b/crates/daemons/pushd/src/consumers/inbound/generic.rs index 58070f66..aa3950d7 100644 --- a/crates/daemons/pushd/src/consumers/inbound/generic.rs +++ b/crates/daemons/pushd/src/consumers/inbound/generic.rs @@ -7,6 +7,7 @@ use amqprs::{ consumer::AsyncConsumer, BasicProperties, Deliver, }; +use anyhow::Result; use async_trait::async_trait; use log::debug; use revolt_database::{events::rabbit::*, Database}; @@ -54,21 +55,16 @@ impl GenericConsumer { channel: None, } } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for GenericConsumer { - /// This consumer handles delegating messages into their respective platform queues. - async fn consume( + async fn consume_event( &mut self, - channel: &Channel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &Channel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: MessageSentPayload = serde_json::from_str(content.as_str()).unwrap(); + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: MessageSentPayload = serde_json::from_str(content.as_str())?; debug!("Received message event on origin"); @@ -117,11 +113,34 @@ impl AsyncConsumer for GenericConsumer { .insert("endpoint".to_string(), sub.endpoint.clone()); } - let payload = serde_json::to_string(&sendable).unwrap(); + let payload = serde_json::to_string(&sendable)?; publish_message(self, payload.into(), args).await; } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for GenericConsumer { + /// This consumer handles delegating messages into their respective platform queues. + async fn consume( + &mut self, + channel: &Channel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process generic event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/inbound/mass_mention.rs b/crates/daemons/pushd/src/consumers/inbound/mass_mention.rs index a44dcb1e..bf5dd453 100644 --- a/crates/daemons/pushd/src/consumers/inbound/mass_mention.rs +++ b/crates/daemons/pushd/src/consumers/inbound/mass_mention.rs @@ -10,6 +10,7 @@ use amqprs::{ consumer::AsyncConsumer, BasicProperties, Deliver, }; +use anyhow::Result; use async_trait::async_trait; use revolt_database::{ events::rabbit::*, util::bulk_permissions::BulkDatabasePermissionQuery, Database, Member, @@ -61,7 +62,11 @@ impl MassMessageConsumer { } } - async fn fire_notification_for_users(&mut self, push: &PushNotification, users: &[String]) { + async fn fire_notification_for_users( + &mut self, + push: &PushNotification, + users: &[String], + ) -> Result<()> { if let Ok(sessions) = self .authifier_db .find_sessions_with_subscription(users) @@ -105,29 +110,26 @@ impl MassMessageConsumer { .insert("endpoint".to_string(), sub.endpoint.clone()); } - let payload = serde_json::to_string(&sendable).unwrap(); + let payload = serde_json::to_string(&sendable)?; publish_message(self, payload.into(), args).await; } } } - } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for MassMessageConsumer { - /// This consumer handles adding mentions for all the users affected by a mass mention ping, and then sends out push notifications - async fn consume( + Ok(()) + } + + async fn consume_event( &mut self, - channel: &Channel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &Channel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { + ) -> Result<()> { let config = revolt_config::config().await; - let content = String::from_utf8(content).unwrap(); - let payload: MassMessageSentPayload = serde_json::from_str(content.as_str()).unwrap(); + let content = String::from_utf8(content)?; + let payload: MassMessageSentPayload = serde_json::from_str(content.as_str())?; debug!("Received mass message event"); @@ -159,8 +161,7 @@ impl AsyncConsumer for MassMessageConsumer { let mut db_query = self .db .fetch_all_members_chunked(&payload.server_id) - .await - .expect("Failed to fetch members from database"); + .await?; let mut exhausted = false; let ack_chnl = vec![push.channel.id().to_string()]; @@ -203,7 +204,8 @@ impl AsyncConsumer for MassMessageConsumer { target_users, online_users ); - self.fire_notification_for_users(&push, &target_users).await; + self.fire_notification_for_users(&push, &target_users) + .await?; if exhausted { break; @@ -211,19 +213,11 @@ impl AsyncConsumer for MassMessageConsumer { } } else if let Some(roles) = &push.message.role_mentions { // role mentions - let _role_members = self + let mut role_members = self .db .fetch_all_members_with_roles_chunked(&payload.server_id, roles) - .await; + .await?; - debug!("role members: {:?}", _role_members); - - if _role_members.is_err() { - revolt_config::capture_error(&_role_members.err().unwrap()); - return; - } - - let mut role_members = _role_members.unwrap(); let mut chunk = vec![]; let mut exhausted = false; @@ -266,10 +260,33 @@ impl AsyncConsumer for MassMessageConsumer { debug!("targets: {:?}", targets); - self.fire_notification_for_users(&push, &targets).await; + self.fire_notification_for_users(&push, &targets).await?; } } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for MassMessageConsumer { + /// This consumer handles adding mentions for all the users affected by a mass mention ping, and then sends out push notifications + async fn consume( + &mut self, + channel: &Channel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process mass message event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/inbound/message.rs b/crates/daemons/pushd/src/consumers/inbound/message.rs index 99e61cbd..6b9d00fe 100644 --- a/crates/daemons/pushd/src/consumers/inbound/message.rs +++ b/crates/daemons/pushd/src/consumers/inbound/message.rs @@ -7,6 +7,7 @@ use amqprs::{ consumer::AsyncConsumer, BasicProperties, Deliver, }; +use anyhow::Result; use async_trait::async_trait; use log::debug; use revolt_database::{events::rabbit::*, Database}; @@ -54,21 +55,16 @@ impl MessageConsumer { channel: None, } } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for MessageConsumer { - /// This consumer handles delegating messages into their respective platform queues. - async fn consume( + async fn consume_event( &mut self, - channel: &Channel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &Channel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: MessageSentPayload = serde_json::from_str(content.as_str()).unwrap(); + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: MessageSentPayload = serde_json::from_str(content.as_str())?; debug!("Received message event on origin"); @@ -117,11 +113,34 @@ impl AsyncConsumer for MessageConsumer { .insert("endpoint".to_string(), sub.endpoint.clone()); } - let payload = serde_json::to_string(&sendable).unwrap(); + let payload = serde_json::to_string(&sendable)?; publish_message(self, payload.into(), args).await; } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for MessageConsumer { + /// This consumer handles delegating messages into their respective platform queues. + async fn consume( + &mut self, + channel: &Channel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process message event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/outbound/apn.rs b/crates/daemons/pushd/src/consumers/outbound/apn.rs index 72382632..cf8cea17 100644 --- a/crates/daemons/pushd/src/consumers/outbound/apn.rs +++ b/crates/daemons/pushd/src/consumers/outbound/apn.rs @@ -1,6 +1,7 @@ use std::{borrow::Cow, collections::BTreeMap, io::Cursor}; use amqprs::{channel::Channel as AmqpChannel, consumer::AsyncConsumer, BasicProperties, Deliver}; +use anyhow::{anyhow, Result}; use async_trait::async_trait; use base64::{ engine::{self}, @@ -123,20 +124,16 @@ impl ApnsOutboundConsumer { Ok(ApnsOutboundConsumer { db, client }) } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for ApnsOutboundConsumer { - async fn consume( + async fn consume_event( &mut self, - channel: &AmqpChannel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &AmqpChannel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: PayloadToService = serde_json::from_str(content.as_str()).unwrap(); + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: PayloadToService = serde_json::from_str(content.as_str())?; let payload_options = NotificationOptions { apns_id: None, @@ -160,7 +157,7 @@ impl AsyncConsumer for ApnsOutboundConsumer { alert.from_user.username, alert.from_user.discriminator ))) .clone() - .unwrap(), + .ok_or_else(|| anyhow!("missing name"))?, )]; let apn_payload = Payload { @@ -206,7 +203,7 @@ impl AsyncConsumer for ApnsOutboundConsumer { alert.accepted_user.username, alert.accepted_user.discriminator ))) .clone() - .unwrap(), + .ok_or_else(|| anyhow!("missing name"))?, )]; let apn_payload = Payload { @@ -356,5 +353,27 @@ impl AsyncConsumer for ApnsOutboundConsumer { } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for ApnsOutboundConsumer { + async fn consume( + &mut self, + channel: &AmqpChannel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process APN event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/outbound/fcm.rs b/crates/daemons/pushd/src/consumers/outbound/fcm.rs index a22708d8..10e174d4 100644 --- a/crates/daemons/pushd/src/consumers/outbound/fcm.rs +++ b/crates/daemons/pushd/src/consumers/outbound/fcm.rs @@ -2,6 +2,7 @@ use std::{collections::HashMap, time::Duration}; use amqprs::{channel::Channel as AmqpChannel, consumer::AsyncConsumer, BasicProperties, Deliver}; +use anyhow::{anyhow, bail, Result}; use async_trait::async_trait; use fcm_v1::{ android::AndroidConfig, @@ -65,22 +66,16 @@ impl FcmOutboundConsumer { ), }) } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for FcmOutboundConsumer { - async fn consume( + async fn consume_event( &mut self, - channel: &AmqpChannel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &AmqpChannel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: PayloadToService = serde_json::from_str(content.as_str()).unwrap(); - - let config = revolt_config::config().await; + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: PayloadToService = serde_json::from_str(content.as_str())?; #[allow(clippy::needless_late_init)] let resp: Result; @@ -95,7 +90,7 @@ impl AsyncConsumer for FcmOutboundConsumer { alert.from_user.username, alert.from_user.discriminator ))) .clone() - .unwrap(); + .ok_or_else(|| anyhow!("missing name"))?; let mut data = HashMap::new(); data.insert( @@ -123,7 +118,7 @@ impl AsyncConsumer for FcmOutboundConsumer { alert.accepted_user.username, alert.accepted_user.discriminator ))) .clone() - .unwrap(); + .ok_or_else(|| anyhow!("missing name"))?; let mut data: HashMap = HashMap::new(); data.insert( @@ -176,7 +171,7 @@ impl AsyncConsumer for FcmOutboundConsumer { } PayloadKind::BadgeUpdate(_) => { - panic!("FCM cannot handle badge updates, and they should not be sent here.") + bail!("FCM cannot handle badge updates and they should not be sent here."); } } @@ -196,5 +191,27 @@ impl AsyncConsumer for FcmOutboundConsumer { } } } + + Ok(()) + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for FcmOutboundConsumer { + async fn consume( + &mut self, + channel: &AmqpChannel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process FCM event: {err:?}"); + } } } diff --git a/crates/daemons/pushd/src/consumers/outbound/vapid.rs b/crates/daemons/pushd/src/consumers/outbound/vapid.rs index fb735d5e..92ce6e56 100644 --- a/crates/daemons/pushd/src/consumers/outbound/vapid.rs +++ b/crates/daemons/pushd/src/consumers/outbound/vapid.rs @@ -2,13 +2,13 @@ use std::collections::HashMap; use amqprs::{channel::Channel as AmqpChannel, consumer::AsyncConsumer, BasicProperties, Deliver}; +use anyhow::{anyhow, bail, Result}; use async_trait::async_trait; use base64::{ engine::{self}, Engine as _, }; use revolt_database::{events::rabbit::*, Database}; -// use revolt_models::v0::{Channel, PushNotification}; use web_push::{ ContentEncoding, IsahcWebPushClient, SubscriptionInfo, SubscriptionKeys, VapidSignatureBuilder, WebPushClient, WebPushError, WebPushMessageBuilder, @@ -21,11 +21,11 @@ pub struct VapidOutboundConsumer { } impl VapidOutboundConsumer { - pub async fn new(db: Database) -> Result { + pub async fn new(db: Database) -> Result { let config = revolt_config::config().await; if config.pushd.vapid.private_key.is_empty() | config.pushd.vapid.public_key.is_empty() { - return Err("No Vapid keys present"); + bail!("no Vapid keys present"); } let web_push_private_key = engine::general_purpose::URL_SAFE_NO_PAD @@ -38,28 +38,30 @@ impl VapidOutboundConsumer { pkey: web_push_private_key, }) } -} -#[allow(unused_variables)] -#[async_trait] -impl AsyncConsumer for VapidOutboundConsumer { - async fn consume( + async fn consume_event( &mut self, - channel: &AmqpChannel, - deliver: Deliver, - basic_properties: BasicProperties, + _channel: &AmqpChannel, + _deliver: Deliver, + _basic_properties: BasicProperties, content: Vec, - ) { - let content = String::from_utf8(content).unwrap(); - let payload: PayloadToService = serde_json::from_str(content.as_str()).unwrap(); - - let config = revolt_config::config().await; + ) -> Result<()> { + let content = String::from_utf8(content)?; + let payload: PayloadToService = serde_json::from_str(content.as_str())?; let subscription = SubscriptionInfo { - endpoint: payload.extras.get("endpoint").unwrap().clone(), + endpoint: payload + .extras + .get("endpoint") + .ok_or_else(|| anyhow!("missing endpoint"))? + .clone(), keys: SubscriptionKeys { auth: payload.token, - p256dh: payload.extras.get("p256dh").unwrap().clone(), + p256dh: payload + .extras + .get("p256dh") + .ok_or_else(|| anyhow!("missing p256dh"))? + .clone(), }, }; @@ -76,12 +78,12 @@ impl AsyncConsumer for VapidOutboundConsumer { alert.from_user.username, alert.from_user.discriminator ))) .clone() - .unwrap(); + .ok_or_else(|| anyhow!("missing name"))?; let mut body = HashMap::new(); body.insert("body", format!("{} sent you a friend request", name)); - payload_body = serde_json::to_string(&body).unwrap(); + payload_body = serde_json::to_string(&body)?; } PayloadKind::FRAccepted(alert) => { let name = alert @@ -92,21 +94,21 @@ impl AsyncConsumer for VapidOutboundConsumer { alert.accepted_user.username, alert.accepted_user.discriminator ))) .clone() - .unwrap(); + .ok_or_else(|| anyhow!("missing name"))?; let mut body = HashMap::new(); body.insert("body", format!("{} accepted your friend request", name)); - payload_body = serde_json::to_string(&body).unwrap(); + payload_body = serde_json::to_string(&body)?; } PayloadKind::Generic(alert) => { - payload_body = serde_json::to_string(&alert).unwrap(); + payload_body = serde_json::to_string(&alert)?; } PayloadKind::MessageNotification(alert) => { - payload_body = serde_json::to_string(&alert).unwrap(); + payload_body = serde_json::to_string(&alert)?; } PayloadKind::BadgeUpdate(_) => { - panic!("Vapid cannot handle badge updates, and they should not be sent here.") + bail!("Vapid cannot handle badge updates and they should not be sent here."); } } @@ -122,28 +124,40 @@ impl AsyncConsumer for VapidOutboundConsumer { Ok(msg) => { if let Err(err) = self.client.send(msg).await { if err == WebPushError::Unauthorized { - if let Err(err) = self - .db + self.db .remove_push_subscription_by_session_id(&payload.session_id) - .await - { - revolt_config::capture_error(&err); - } + .await?; } } + + Ok(()) } - Err(err) => { - revolt_config::capture_error(&err); - } + Err(err) => Err(err.into()), } } - Err(err) => { - revolt_config::capture_error(&err); - } + Err(err) => Err(err.into()), }, - Err(err) => { - revolt_config::capture_error(&err); - } + Err(err) => Err(err.into()), + } + } +} + +#[allow(unused_variables)] +#[async_trait] +impl AsyncConsumer for VapidOutboundConsumer { + async fn consume( + &mut self, + channel: &AmqpChannel, + deliver: Deliver, + basic_properties: BasicProperties, + content: Vec, + ) { + if let Err(err) = self + .consume_event(channel, deliver, basic_properties, content) + .await + { + revolt_config::capture_anyhow(&err); + eprintln!("Failed to process Vapid event: {err:?}"); } } } diff --git a/crates/daemons/pushd/src/main.rs b/crates/daemons/pushd/src/main.rs index 1560b049..78845a63 100644 --- a/crates/daemons/pushd/src/main.rs +++ b/crates/daemons/pushd/src/main.rs @@ -24,8 +24,8 @@ use consumers::{ #[tokio::main(flavor = "multi_thread", worker_threads = 2)] async fn main() { - let config = config().await; - pretty_env_logger::init(); + // Configure logging and environment + revolt_config::configure!(pushd); // Setup database let db = revolt_database::DatabaseInfo::Auto.connect().await.unwrap(); @@ -52,6 +52,8 @@ async fn main() { // This'll require some interesting shimming if we need to add more events once this is in prod (different payloads between prod and test), // but that sounds like a problem for future us. + let config = config().await; + // inbound: generic connections.push( make_queue_and_consume( diff --git a/crates/delta/Cargo.toml b/crates/delta/Cargo.toml index 10e85d9a..9663c410 100644 --- a/crates/delta/Cargo.toml +++ b/crates/delta/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-delta" -version = "0.8.4" +version = "0.8.7" license = "AGPL-3.0-or-later" authors = ["Paul Makles "] edition = "2018" @@ -52,10 +52,11 @@ async-std = { version = "1.8.0", features = [ lettre = "0.10.0-alpha.4" # web + rocket = { version = "0.5.1", default-features = false, features = ["json"] } rocket_cors = { git = "https://github.com/lawliet89/rocket_cors", rev = "072d90359b23e9b291df6b672c07c93de9c46011" } rocket_empty = { version = "0.1.1", features = ["schema"] } -rocket_authifier = { version = "1.0.10" } +rocket_authifier = { version = "1.0.15" } rocket_prometheus = "0.10.0-rc.3" # spec generation @@ -66,7 +67,7 @@ revolt_rocket_okapi = { version = "0.10.0", features = ["swagger"] } amqprs = { version = "1.7.0" } # core -authifier = "1.0.10" +authifier = "1.0.15" revolt-config = { path = "../core/config" } revolt-database = { path = "../core/database", features = [ "rocket-impl", diff --git a/crates/delta/src/routes/channels/members_fetch.rs b/crates/delta/src/routes/channels/members_fetch.rs index 64a14a9b..4a6688bf 100644 --- a/crates/delta/src/routes/channels/members_fetch.rs +++ b/crates/delta/src/routes/channels/members_fetch.rs @@ -1,4 +1,3 @@ -use futures::future::join_all; use revolt_database::{ util::{permissions::DatabasePermissionQuery, reference::Reference}, Channel, Database, User, diff --git a/crates/delta/src/routes/channels/message_bulk_delete.rs b/crates/delta/src/routes/channels/message_bulk_delete.rs index 6cb2b37a..446b1e26 100644 --- a/crates/delta/src/routes/channels/message_bulk_delete.rs +++ b/crates/delta/src/routes/channels/message_bulk_delete.rs @@ -8,7 +8,6 @@ use revolt_permissions::{calculate_channel_permissions, ChannelPermission}; use revolt_result::{create_error, Result}; use rocket::{serde::json::Json, State}; use rocket_empty::EmptyResponse; -use serde::Deserialize; use validator::Validate; /// # Bulk Delete Messages diff --git a/crates/delta/src/routes/channels/message_edit.rs b/crates/delta/src/routes/channels/message_edit.rs index 3662ee63..2b5d24f7 100644 --- a/crates/delta/src/routes/channels/message_edit.rs +++ b/crates/delta/src/routes/channels/message_edit.rs @@ -1,5 +1,4 @@ use iso8601_timestamp::Timestamp; -use revolt_config::config; use revolt_database::{ tasks, util::{permissions::DatabasePermissionQuery, reference::Reference}, diff --git a/crates/delta/src/routes/channels/permissions_set.rs b/crates/delta/src/routes/channels/permissions_set.rs index e3564540..d5ba55cf 100644 --- a/crates/delta/src/routes/channels/permissions_set.rs +++ b/crates/delta/src/routes/channels/permissions_set.rs @@ -5,7 +5,6 @@ use revolt_models::v0; use revolt_permissions::{calculate_channel_permissions, ChannelPermission, Override}; use revolt_result::{create_error, Result}; use rocket::{serde::json::Json, State}; -use serde::Deserialize; /// # Set Role Permission /// diff --git a/crates/delta/src/routes/customisation/emoji_delete.rs b/crates/delta/src/routes/customisation/emoji_delete.rs index 53cbb837..05d89eb0 100644 --- a/crates/delta/src/routes/customisation/emoji_delete.rs +++ b/crates/delta/src/routes/customisation/emoji_delete.rs @@ -3,7 +3,7 @@ use revolt_database::{ Database, EmojiParent, User, }; use revolt_permissions::{calculate_server_permissions, ChannelPermission}; -use revolt_result::{create_error, Result}; +use revolt_result::Result; use rocket::State; use rocket_empty::EmptyResponse; @@ -18,7 +18,6 @@ pub async fn delete_emoji( user: User, emoji_id: Reference, ) -> Result { - // Fetch the emoji let emoji = emoji_id.as_emoji(db).await?; diff --git a/crates/delta/src/routes/mod.rs b/crates/delta/src/routes/mod.rs index 5107e7c2..9643a365 100644 --- a/crates/delta/src/routes/mod.rs +++ b/crates/delta/src/routes/mod.rs @@ -1,4 +1,4 @@ -use revolt_config::{config, Settings}; +use revolt_config::Settings; use revolt_rocket_okapi::{revolt_okapi::openapi3::OpenApi, settings::OpenApiSettings}; pub use rocket::http::Status; pub use rocket::response::Redirect; @@ -9,6 +9,7 @@ mod channels; mod customisation; mod invites; mod onboard; +mod policy; mod push; mod root; mod safety; @@ -36,6 +37,7 @@ pub fn mount(config: Settings, mut rocket: Rocket) -> Rocket { "/auth/session" => rocket_authifier::routes::session::routes(), "/auth/mfa" => rocket_authifier::routes::mfa::routes(), "/onboard" => onboard::routes(), + "/policy" => policy::routes(), "/push" => push::routes(), "/sync" => sync::routes(), "/webhooks" => webhooks::routes() @@ -56,6 +58,7 @@ pub fn mount(config: Settings, mut rocket: Rocket) -> Rocket { "/auth/session" => rocket_authifier::routes::session::routes(), "/auth/mfa" => rocket_authifier::routes::mfa::routes(), "/onboard" => onboard::routes(), + "/policy" => policy::routes(), "/push" => push::routes(), "/sync" => sync::routes() }; diff --git a/crates/delta/src/routes/policy/acknowledge_policy_changes.rs b/crates/delta/src/routes/policy/acknowledge_policy_changes.rs new file mode 100644 index 00000000..062dc32c --- /dev/null +++ b/crates/delta/src/routes/policy/acknowledge_policy_changes.rs @@ -0,0 +1,17 @@ +use revolt_database::{events::client::EventV1, Database, Report, Snapshot, SnapshotContent, User}; +use revolt_models::v0::{ReportStatus, ReportedContent}; +use revolt_result::{create_error, Result}; +use serde::Deserialize; +use ulid::Ulid; +use validator::Validate; + +use rocket::{serde::json::Json, State}; + +/// # Acknowledge Policy Changes +/// +/// Accept/acknowledge changes to platform policy. +#[openapi(tag = "Policy")] +#[post("/acknowledge")] +pub async fn acknowledge_policy_changes(db: &State, user: User) -> Result<()> { + db.acknowledge_policy_changes(&user.id).await +} diff --git a/crates/delta/src/routes/policy/mod.rs b/crates/delta/src/routes/policy/mod.rs new file mode 100644 index 00000000..77831b1f --- /dev/null +++ b/crates/delta/src/routes/policy/mod.rs @@ -0,0 +1,11 @@ +use revolt_rocket_okapi::revolt_okapi::openapi3::OpenApi; +use rocket::Route; + +mod acknowledge_policy_changes; + +pub fn routes() -> (Vec, OpenApi) { + openapi_get_routes_spec![ + // Policy + acknowledge_policy_changes::acknowledge_policy_changes, + ] +} diff --git a/crates/delta/src/routes/servers/ban_create.rs b/crates/delta/src/routes/servers/ban_create.rs index 26881a30..6e530b1a 100644 --- a/crates/delta/src/routes/servers/ban_create.rs +++ b/crates/delta/src/routes/servers/ban_create.rs @@ -5,9 +5,7 @@ use revolt_database::{ }; use revolt_models::v0; -use revolt_permissions::{ - calculate_server_permissions, ChannelPermission, -}; +use revolt_permissions::{calculate_server_permissions, ChannelPermission}; use revolt_result::{create_error, Result}; use rocket::{serde::json::Json, State}; use validator::Validate; diff --git a/crates/delta/src/routes/users/fetch_user_flags.rs b/crates/delta/src/routes/users/fetch_user_flags.rs index 39c731d0..92377a57 100644 --- a/crates/delta/src/routes/users/fetch_user_flags.rs +++ b/crates/delta/src/routes/users/fetch_user_flags.rs @@ -2,7 +2,6 @@ use revolt_database::{util::reference::Reference, Database}; use revolt_models::v0; use revolt_result::Result; use rocket::{serde::json::Json, State}; -use serde::Serialize; /// # Fetch User Flags /// diff --git a/crates/delta/src/routes/webhooks/webhook_execute_github.rs b/crates/delta/src/routes/webhooks/webhook_execute_github.rs index 6d9c8b60..ae7ff40c 100644 --- a/crates/delta/src/routes/webhooks/webhook_execute_github.rs +++ b/crates/delta/src/routes/webhooks/webhook_execute_github.rs @@ -588,6 +588,7 @@ pub enum PullRequestEvent { #[derive(Debug)] #[allow(clippy::large_enum_variant)] pub enum BaseEvent { + #[allow(dead_code)] Star(StarEvent), Ping, Push(PushEvent), @@ -829,7 +830,7 @@ pub async fn webhook_execute_github( }) .collect::>() .join("\n"), - 1000 + 1000, ); SendableEmbed { diff --git a/crates/services/autumn/Cargo.toml b/crates/services/autumn/Cargo.toml index dc242413..36446c01 100644 --- a/crates/services/autumn/Cargo.toml +++ b/crates/services/autumn/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-autumn" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" @@ -43,12 +43,12 @@ tracing = "0.1" tracing-subscriber = { version = "0.3", features = ["env-filter"] } # Core crates -revolt-files = { version = "0.8.4", path = "../../core/files" } -revolt-config = { version = "0.8.4", path = "../../core/config" } -revolt-database = { version = "0.8.4", path = "../../core/database", features = [ +revolt-files = { version = "0.8.7", path = "../../core/files" } +revolt-config = { version = "0.8.7", path = "../../core/config" } +revolt-database = { version = "0.8.7", path = "../../core/database", features = [ "axum-impl", ] } -revolt-result = { version = "0.8.4", path = "../../core/result", features = [ +revolt-result = { version = "0.8.7", path = "../../core/result", features = [ "utoipa", "axum", ] } diff --git a/crates/services/january/Cargo.toml b/crates/services/january/Cargo.toml index 01b6f402..3566d2a0 100644 --- a/crates/services/january/Cargo.toml +++ b/crates/services/january/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "revolt-january" -version = "0.8.4" +version = "0.8.7" edition = "2021" license = "AGPL-3.0-or-later" @@ -32,13 +32,13 @@ tracing = "0.1" tracing-subscriber = { version = "0.3", features = ["env-filter"] } # Core crates -revolt-config = { version = "0.8.4", path = "../../core/config" } -revolt-models = { version = "0.8.4", path = "../../core/models" } -revolt-result = { version = "0.8.4", path = "../../core/result", features = [ +revolt-config = { version = "0.8.7", path = "../../core/config" } +revolt-models = { version = "0.8.7", path = "../../core/models" } +revolt-result = { version = "0.8.7", path = "../../core/result", features = [ "utoipa", "axum", ] } -revolt-files = { version = "0.8.4", path = "../../core/files" } +revolt-files = { version = "0.8.7", path = "../../core/files" } # Axum / web server axum = { version = "0.7.5" } diff --git a/justfile b/justfile index e093afde..e7bd0f00 100644 --- a/justfile +++ b/justfile @@ -1,4 +1,5 @@ publish: + cargo publish --package revolt-parser cargo publish --package revolt-config cargo publish --package revolt-result cargo publish --package revolt-files diff --git a/scripts/build-image-layer.sh b/scripts/build-image-layer.sh index 064ee756..0a0fa32b 100644 --- a/scripts/build-image-layer.sh +++ b/scripts/build-image-layer.sh @@ -22,13 +22,13 @@ tools() { deps() { mkdir -p \ - crates/bindings/node/src \ crates/bonfire/src \ crates/delta/src \ crates/core/config/src \ crates/core/database/src \ crates/core/files/src \ crates/core/models/src \ + crates/core/parser/src \ crates/core/permissions/src \ crates/core/presence/src \ crates/core/result/src \ @@ -44,19 +44,19 @@ deps() { tee crates/daemons/crond/src/main.rs | tee crates/daemons/pushd/src/main.rs echo '' | - tee crates/bindings/node/src/lib.rs | tee crates/core/config/src/lib.rs | tee crates/core/database/src/lib.rs | tee crates/core/files/src/lib.rs | tee crates/core/models/src/lib.rs | + tee crates/core/parser/src/lib.rs | tee crates/core/permissions/src/lib.rs | tee crates/core/presence/src/lib.rs | tee crates/core/result/src/lib.rs if [ -z "$TARGETARCH" ]; then - cargo build --locked --release + cargo build -j 10 --locked --release else - cargo build --locked --release --target "${BUILD_TARGET}" + cargo build -j 10 --locked --release --target "${BUILD_TARGET}" fi } @@ -69,14 +69,15 @@ apps() { crates/core/config/src/lib.rs \ crates/core/database/src/lib.rs \ crates/core/models/src/lib.rs \ + crates/core/parser/src/lib.rs \ crates/core/permissions/src/lib.rs \ crates/core/presence/src/lib.rs \ crates/core/result/src/lib.rs if [ -z "$TARGETARCH" ]; then - cargo build --locked --release + cargo build -j 10 --locked --release else - cargo build --locked --release --target "${BUILD_TARGET}" + cargo build -j 10 --locked --release --target "${BUILD_TARGET}" mv target _target && mv _target/"${BUILD_TARGET}" target fi }