Compare commits

..

8 Commits

Author SHA1 Message Date
Mark Sinclair 317806005a Add rollup config to output CommonJS bundle 2023-01-17 16:32:05 +00:00
Mark Sinclair 5723078413 wasm-client: add method to validate a recipient's address 2023-01-17 14:34:16 +00:00
Mark Sinclair 9777da0964 Update SDK docs and images 2023-01-17 11:47:59 +00:00
Mark Sinclair bee8638572 WASM client: fix tests 2023-01-17 11:33:59 +00:00
Mark Sinclair be7504b036 Add Parcel 2.0 example 2023-01-17 10:39:43 +00:00
Mark Sinclair cf342108c3 Suppress errors in build script 2023-01-17 10:39:43 +00:00
Mark Sinclair 69f5a0d6ba Use rollup to bundle the web worker script to support more downstream bundlers
The WASM bundle is embedded as a base64 encoded resource and loaded synchronously, because this is the only mechanism widely supported to load WASM inside a web worker currently. Hopefully in the future this can be changed to pure modules.
2023-01-17 10:39:43 +00:00
Mark Sinclair 548dfed713 WASM Client: simplify sending of custom messages by always setting headers and a mime-type for the content 2023-01-17 10:39:43 +00:00
1174 changed files with 18019 additions and 47093 deletions
+7 -7
View File
@@ -35,20 +35,20 @@ jobs:
with: with:
name: report name: report
path: .github/workflows/support-files/notifications path: .github/workflows/support-files/notifications
- name: install npm - name: Keybase - Node Install
uses: actions/setup-node@v3
with:
node-version: 16
- name: Matrix - Node Install
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
env: env:
NYM_NOTIFICATION_KIND: security NYM_NOTIFICATION_KIND: security
NYM_PROJECT_NAME: "Daily security report" NYM_PROJECT_NAME: "Daily security report"
GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}" GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "security"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM_AUDIT }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}" MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}" MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}" MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
+58
View File
@@ -0,0 +1,58 @@
name: Daily security audit
on: workflow_dispatch
jobs:
cargo-deny:
runs-on: ubuntu-20.04
steps:
- name: Checkout repository code
uses: actions/checkout@v2
- name: Install rust toolchain
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: Install cargo deny
run: cargo install --locked cargo-deny
- name: Run cargo deny
run: |
find . -name Cargo.toml -exec cargo deny --manifest-path {} check \
advisories -A advisory-not-detected --hide-inclusion-graph \; &> \
>(uniq &> .github/workflows/support-files/notifications/deny.message )
- uses: actions/upload-artifact@v3
with:
name: report
path: .github/workflows/support-files/notifications/deny.message
notification:
needs: cargo-deny
runs-on: custom-runner-linux
steps:
- name: Check out repository code
uses: actions/checkout@v2
- name: Download report from previous job
uses: actions/download-artifact@v3
with:
name: report
path: .github/workflows/support-files/notifications
- uses: actions/setup-node@v3
with:
node-version: 16
- name: Keybase - Node Install
run: npm install
working-directory: .github/workflows/support-files
- name: Keybase - Send Notification
env:
NYM_NOTIFICATION_KIND: security
NYM_PROJECT_NAME: "Daily security report"
GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "security"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
uses: docker://keybaseio/client:stable-node
with:
args: .github/workflows/support-files/notifications/entry_point.sh
@@ -1,113 +0,0 @@
name: Build and upload binaries to CI
on:
workflow_dispatch:
push:
paths:
- 'clients/**'
- 'common/**'
- 'contracts/**'
- 'explorer-api/**'
- 'gateway/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
- 'nym-api/**'
- 'nym-outfox/**'
- 'tools/nym-cli/**'
- 'tools/ts-rs-cli/**'
pull_request:
paths:
- 'clients/**'
- 'common/**'
- 'contracts/**'
- 'explorer-api/**'
- 'gateway/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
- 'nym-api/**'
- 'nym-outfox/**'
- 'tools/nym-cli/**'
- 'tools/ts-rs-cli/**'
env:
NETWORK: mainnet
jobs:
publish-nym:
strategy:
fail-fast: false
matrix:
platform: [ubuntu-20.04]
runs-on: ${{ matrix.platform }}
steps:
- uses: actions/checkout@v3
- name: Prepare build output directory
shell: bash
env:
OUTPUT_DIR: ci-builds/${{ github.ref_name }}
run: |
rm -rf ci-builds || true
mkdir -p $OUTPUT_DIR
echo $OUTPUT_DIR
- name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: Build all binaries
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --release --all
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
target: wasm32-unknown-unknown
override: true
components: rustfmt, clippy
- name: Build release contracts
run: make wasm
- name: Prepare build output
shell: bash
env:
OUTPUT_DIR: ci-builds/${{ github.ref_name }}
run: |
cp target/release/nym-client $OUTPUT_DIR
cp target/release/nym-gateway $OUTPUT_DIR
cp target/release/nym-mixnode $OUTPUT_DIR
cp target/release/nym-socks5-client $OUTPUT_DIR
cp target/release/nym-api $OUTPUT_DIR
cp target/release/nym-network-requester $OUTPUT_DIR
cp target/release/nym-network-statistics $OUTPUT_DIR
cp target/release/nym-cli $OUTPUT_DIR
cp target/release/credential $OUTPUT_DIR
cp contracts/target/wasm32-unknown-unknown/release/mixnet_contract.wasm $OUTPUT_DIR
cp contracts/target/wasm32-unknown-unknown/release/vesting_contract.wasm $OUTPUT_DIR
- name: Deploy branch to CI www
continue-on-error: true
uses: easingthemes/ssh-deploy@main
env:
SSH_PRIVATE_KEY: ${{ secrets.CI_WWW_SSH_PRIVATE_KEY }}
ARGS: "-avzr"
SOURCE: "ci-builds/"
REMOTE_HOST: ${{ secrets.CI_WWW_REMOTE_HOST }}
REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }}
TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/builds/
EXCLUDE: "/dist/, /node_modules/"
@@ -1,59 +0,0 @@
name: Build and upload binaries to artifact storage
on:
workflow_dispatch:
inputs:
add_tokio_unstable:
description: 'True to add RUSTFLAGS="--cfg tokio_unstable"'
required: true
default: false
type: boolean
env:
NETWORK: mainnet
jobs:
publish-nym:
strategy:
fail-fast: false
matrix:
platform: [ubuntu-20.04]
runs-on: ${{ matrix.platform }}
steps:
- uses: actions/checkout@v3
- name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Sets env vars for tokio if set in manual dispatch inputs
run: |
echo 'RUSTFLAGS="--cfg tokio_unstable"' >> $GITHUB_ENV
if: github.event_name == 'workflow_dispatch' && inputs.add_tokio_unstable == true
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: Build all binaries
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --release
- name: Upload Artifact
uses: actions/upload-artifact@v3
with:
name: nym-binaries-artifacts
path: |
target/release/nym-client
target/release/nym-gateway
target/release/nym-mixnode
target/release/nym-socks5-client
target/release/nym-api
target/release/nym-network-requester
target/release/nym-network-statistics
target/release/nym-cli
retention-days: 30
+6 -3
View File
@@ -12,7 +12,6 @@ jobs:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Install rsync - name: Install rsync
run: sudo apt-get install rsync run: sudo apt-get install rsync
continue-on-error: true
- uses: rlespinasse/github-slug-action@v3.x - uses: rlespinasse/github-slug-action@v3.x
- uses: actions/setup-node@v3 - uses: actions/setup-node@v3
with: with:
@@ -43,10 +42,10 @@ jobs:
REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }} REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }}
TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/ts-${{ env.GITHUB_REF_SLUG }}-example TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/ts-${{ env.GITHUB_REF_SLUG }}-example
EXCLUDE: "/dist/, /node_modules/" EXCLUDE: "/dist/, /node_modules/"
- name: Matrix - Node Install - name: Keybase - Node Install
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
env: env:
NYM_NOTIFICATION_KIND: ts-packages NYM_NOTIFICATION_KIND: ts-packages
NYM_PROJECT_NAME: "ts-packages" NYM_PROJECT_NAME: "ts-packages"
@@ -54,6 +53,10 @@ jobs:
NYM_CI_WWW_LOCATION: "ts-${{ env.GITHUB_REF_SLUG }}" NYM_CI_WWW_LOCATION: "ts-${{ env.GITHUB_REF_SLUG }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-ts-packages"
IS_SUCCESS: "${{ job.status == 'success' }}" IS_SUCCESS: "${{ job.status == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
+28 -37
View File
@@ -2,33 +2,11 @@ name: Continuous integration
on: on:
push: push:
paths: paths-ignore:
- 'clients/**' - 'explorer/**'
- 'common/**'
- 'explorer-api/**'
- 'gateway/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
- 'nym-api/**'
- 'nym-outfox/**'
- 'tools/nym-cli/**'
- 'tools/ts-rs-cli/**'
pull_request: pull_request:
paths: paths-ignore:
- 'clients/**' - 'explorer/**'
- 'common/**'
- 'explorer-api/**'
- 'gateway/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
- 'nym-api/**'
- 'nym-outfox/**'
- 'tools/nym-cli/**'
- 'tools/ts-rs-cli/**'
jobs: jobs:
build: build:
@@ -39,7 +17,6 @@ jobs:
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v2 uses: actions/checkout@v2
@@ -64,34 +41,48 @@ jobs:
command: build command: build
args: --workspace args: --workspace
- name: Build all examples
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --examples
- name: Run all tests - name: Run all tests
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --workspace args: --workspace --all-features
- name: Run expensive tests - name: Run expensive tests
if: github.ref == 'refs/heads/develop' || github.event.pull_request.base.ref == 'develop' || github.event.pull_request.base.ref == 'master' if: github.ref == 'refs/heads/develop' || github.event.pull_request.base.ref == 'develop' || github.event.pull_request.base.ref == 'master'
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --workspace -- --ignored args: --workspace --all-features -- --ignored
- uses: actions-rs/clippy-check@v1 - uses: actions-rs/clippy-check@v1
name: Clippy checks name: Clippy checks
continue-on-error: true continue-on-error: true
with: with:
token: ${{ secrets.GITHUB_TOKEN }} token: ${{ secrets.GITHUB_TOKEN }}
args: --workspace args: --workspace --all-features
- name: Run clippy - name: Run clippy
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: clippy command: clippy
args: --workspace --all-targets -- -D warnings args: --workspace -- -D warnings
# COCONUT stuff
- name: Build all binaries with coconut enabled
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --features=coconut
- name: Run all tests with coconut enabled
uses: actions-rs/cargo@v1
with:
command: test
args: --workspace --features=coconut
- name: Run clippy with coconut enabled
uses: actions-rs/cargo@v1
with:
command: clippy
args: --all-targets --features=coconut -- -D warnings
@@ -1,61 +0,0 @@
name: check-merge-conflicts
# Check that the latest release branch merges into master and develop without
# any conflicts that git is not able to resolve
on:
workflow_dispatch:
schedule:
- cron: '5 6 * * *'
jobs:
get_release:
runs-on: ubuntu-latest
outputs:
output1: ${{ steps.step2.outputs.latest_release }}
steps:
- name: Check out repository code
uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Set output variable to latest release branch
id: step2
run: echo "latest_release=$(git branch -r | grep -E 'release/v[0-9]+\.[0-9]+\.[0-9]+$' | sort -V | tail -n 1)" >> $GITHUB_OUTPUT
check-merge-release-into-master:
name: Check that the release branch merges into master
needs: get_release
runs-on: ubuntu-latest
steps:
- name: Checkout repo
uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Setup git user
run: |
git config --global user.name "ci"
git config --global user.email "ci@localhost"
- name: Check merge release branch into master
run: |
./.github/workflows/support-files/git-merge-check.sh origin/master $branch1
env:
branch1: ${{needs.get_release.outputs.output1}}
check-merge-release-into-develop:
name: Check that the release branch merges into develop
needs: get_release
runs-on: ubuntu-latest
steps:
- name: Checkout repo
uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Setup git user
run: |
git config --global user.name "ci"
git config --global user.email "ci@localhost"
- name: Check merge release branch into develop
run: |
./.github/workflows/support-files/git-merge-check.sh origin/develop $branch1
env:
branch1: ${{needs.get_release.outputs.output1}}
-56
View File
@@ -1,56 +0,0 @@
name: Run config checks on all binaries
on:
workflow_dispatch:
release:
types: [created]
push:
paths:
- 'clients/**'
- 'common/**'
- 'contracts/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
pull_request:
paths:
- 'clients/**'
- 'common/**'
- 'gateway/**'
- 'integrations/**'
- 'mixnode/**'
- 'sdk/rust/nym-sdk/**'
- 'service-providers/**'
env:
NETWORK: mainnet
jobs:
publish-nym:
strategy:
fail-fast: false
matrix:
platform: [custom-runner-linux]
runs-on: ${{ matrix.platform }}
steps:
- uses: actions/checkout@v3
- name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install jq vim libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: Branch name
run: echo running on branch ${GITHUB_REF##*/}
- name: Run tests against binaries
run: ./build_and_run.sh ${{ github.head_ref || github.ref_name }}
working-directory: tests/
-138
View File
@@ -1,138 +0,0 @@
name: Nym Connect - Android APK Build
on:
workflow_dispatch:
push:
branches:
- "release/nc-android-v[0-9].[0-9].[0-9]*"
jobs:
build:
name: Build APK
runs-on: custom-runner-linux
env:
ANDROID_HOME: ${{ github.workspace }}/android-sdk
NDK_VERSION: 25.1.8937393
NDK_HOME: ${{ github.workspace }}/android-sdk/ndk/25.1.8937393
SDK_PLATFORM_VERSION: android-33
SDK_BUILDTOOLS_VERSION: 33.0.1
steps:
- name: Install Dependencies (Linux)
# https://next--tauri.netlify.app/next/guides/getting-started/prerequisites/linux/#1-system-dependencies
run: |
sudo apt-get update
sudo apt-get -y install \
build-essential \
unzip \
curl \
wget \
libssl-dev \
squashfs-tools \
librsvg2-dev
- name: Checkout
uses: actions/checkout@v3
- name: Install Java
uses: actions/setup-java@v3
with:
distribution: "temurin"
java-version: "17"
- name: Install Android SDK manager
# https://developer.android.com/studio/command-line/sdkmanager
run: |
curl -sS https://dl.google.com/android/repository/commandlinetools-linux-9477386_latest.zip -o cmdline-tools.zip
unzip cmdline-tools.zip
mkdir -p $ANDROID_HOME/cmdline-tools/latest
mv cmdline-tools/* $ANDROID_HOME/cmdline-tools/latest
rm -rf cmdline-tools
- name: Install Android S/NDK
run: |
echo y | $ANDROID_HOME/cmdline-tools/latest/bin/sdkmanager --licenses
echo y | $ANDROID_HOME/cmdline-tools/latest/bin/sdkmanager \
"platforms;$SDK_PLATFORM_VERSION" \
"platform-tools" \
"ndk;$NDK_VERSION" \
"build-tools;$SDK_BUILDTOOLS_VERSION"
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
# TODO this step takes a considerable amount of time
# We could avoid to compile from source tauri-cli and use instead
# pre-compiled binary provided by the node package `@tauri-apps/cli`
# But when using the later the build fails for some reason
# so keep installing and using tauri-cli
- name: Install tauri cli
run: cargo install tauri-cli --version "^2.0.0-alpha.2"
- name: Install rust android targets
run: |
rustup target add aarch64-linux-android \
armv7-linux-androideabi \
i686-linux-android \
x86_64-linux-android
- name: Setup Nodejs
uses: actions/setup-node@v3
with:
node-version: 18
- name: Install yarn
run: |
npm i -g yarn
yarn --version
- name: Build frontend code
run: |
yarn install --frozen-lockfile
yarn build
yarn workspace @nym/nym-connect-mobile webpack:prod
- name: Build APK
working-directory: nym-connect/mobile
env:
# NODE_TAURI_CLI=${{ github.workspace }}/nym-connect/mobile/node_modules/.bin/tauri
ANDROID_SDK_ROOT: ${{ env.ANDROID_HOME }}
WRY_ANDROID_PACKAGE: net.nymtech.nym_connect
WRY_ANDROID_LIBRARY: nym_connect
# TODO build with release profile (--release), it will requires
# to sign the APK. For now build with debug profile to avoid that
# TODO build using `yarn tauri`, provide NODE_TAURI_CLI, see TODO notes above
run: cargo tauri android build --debug --apk --split-per-abi -t aarch64
# TODO add the version number to APK name
- name: Rename APK artifact
run: |
mkdir apk/
mv nym-connect/mobile/src-tauri/gen/android/nym_connect/app/build/outputs/apk/arm64/debug/app-arm64-debug.apk \
apk/nym-connect-arm64-debug.apk
mv nym-connect/mobile/src-tauri/gen/android/nym_connect/app/build/outputs/apk/x86_64/debug/app-x86_64-debug.apk \
apk/nym-connect-x86_64-debug.apk
- name: Upload APK artifact
uses: actions/upload-artifact@v3
with:
name: nc-apk-debug
path: |
apk/nym-connect-arm64-debug.apk
apk/nym-connect-x86_64-debug.apk
# publish:
# name: Publish APK
# needs: build
# runs-on: ubuntu-latest
# steps:
# - name: Checkout
# uses: actions/checkout@v3
# - name: Download binary artifact
# uses: actions/download-artifact@v3
# with:
# name: nc-apk-debug
# path: apk
# # TODO add a step to upload the APK somewhere
# - name: Publish
# uses: ???
-72
View File
@@ -1,72 +0,0 @@
name: Nym Connect - mobile (Rust)
on:
push:
paths:
- "nym-connect/mobile/src-tauri/**"
- "nym-connect/mobile/src-tauri/Cargo.toml"
- "!nym-connect/mobile/src-tauri/gen/**"
- "clients/client-core/**"
- "clients/socks5/**"
- "common/**"
- "gateway/gateway-requests/**"
- "contracts/vesting/**"
- "nym-api/nym-api-requests/**"
pull_request:
paths:
- "nym-connect/mobile/src-tauri/**"
- "nym-connect/mobile/src-tauri/Cargo.toml"
- "!nym-connect/mobile/src-tauri/gen/**"
- "clients/client-core/**"
- "clients/socks5/**"
- "common/**"
- "gateway/gateway-requests/**"
- "contracts/vesting/**"
- "nym-api/nym-api-requests/**"
jobs:
build:
#runs-on: [self-hosted, custom-linux]
runs-on: ubuntu-22.04
#env:
#RUSTC_WRAPPER: /home/ubuntu/.cargo/bin/sccache
#defaults:
#run:
#working-directory: nym-connect/mobile/src-tauri/
steps:
- name: Install Dependencies (Linux)
run: |
sudo apt-get update
sudo apt-get -y install \
libwebkit2gtk-4.1-dev \
build-essential \
curl \
wget \
libssl-dev \
libgtk-3-dev \
squashfs-tools \
libayatana-appindicator3-dev \
librsvg2-dev \
libsoup-3.0-dev \
libjavascriptcoregtk-4.1-dev
- name: Checkout
uses: actions/checkout@v3
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@master
with:
toolchain: stable
components: clippy, rustfmt
- name: Check formatting
run: cargo fmt --manifest-path nym-connect/mobile/src-tauri/Cargo.toml -- --check
- name: Build all binaries
run: cargo build --manifest-path nym-connect/mobile/src-tauri/Cargo.toml
- name: Run all tests
run: cargo test --manifest-path nym-connect/mobile/src-tauri/Cargo.toml
- name: Clippy
run: cargo clippy --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --all-targets -- -D warnings
@@ -1,36 +1,18 @@
name: Nym Connect - desktop (Rust) name: Nym Connect (rust)
on: on:
push: push:
paths: paths-ignore:
- "nym-connect/desktop/src-tauri/**" - 'explorer/**'
- "nym-connect/desktop/src-tauri/Cargo.toml"
- "clients/client-core/**"
- "clients/socks5/**"
- "common/**"
- "gateway/gateway-requests/**"
- "contracts/vesting/**"
- "nym-api/nym-api-requests/**"
pull_request:
paths:
- "nym-connect/desktop/src-tauri/**"
- "nym-connect/desktop/src-tauri/Cargo.toml"
- "clients/client-core/**"
- "clients/socks5/**"
- "common/**"
- "gateway/gateway-requests/**"
- "contracts/vesting/**"
- "nym-api/nym-api-requests/**"
jobs: jobs:
build: build:
runs-on: [self-hosted, custom-linux] runs-on: [ self-hosted, custom-linux ]
env: env:
RUSTC_WRAPPER: /home/ubuntu/.cargo/bin/sccache RUSTC_WRAPPER: /home/ubuntu/.cargo/bin/sccache
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev squashfs-tools libayatana-appindicator3-dev run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev squashfs-tools libayatana-appindicator3-dev
continue-on-error: true
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v2 uses: actions/checkout@v2
@@ -47,29 +29,29 @@ jobs:
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: build command: build
args: --manifest-path nym-connect/desktop/Cargo.toml --workspace args: --manifest-path nym-connect/Cargo.toml --workspace
- name: Run all tests - name: Run all tests
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --manifest-path nym-connect/desktop/Cargo.toml --workspace args: --manifest-path nym-connect/Cargo.toml --workspace
- name: Check formatting - name: Check formatting
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: fmt command: fmt
args: --manifest-path nym-connect/desktop/Cargo.toml --all -- --check args: --manifest-path nym-connect/Cargo.toml --all -- --check
- uses: actions-rs/clippy-check@v1 - uses: actions-rs/clippy-check@v1
name: Clippy checks name: Clippy checks
continue-on-error: true continue-on-error: true
with: with:
token: ${{ secrets.GITHUB_TOKEN }} token: ${{ secrets.GITHUB_TOKEN }}
args: --manifest-path nym-connect/desktop/Cargo.toml --workspace --all-features args: --manifest-path nym-connect/Cargo.toml --workspace --all-features
- name: Run clippy - name: Run clippy
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: clippy command: clippy
args: --manifest-path nym-connect/desktop/Cargo.toml --workspace --all-features -- -D warnings args: --manifest-path nym-connect/Cargo.toml --workspace --all-features -- -D warnings
+8 -2
View File
@@ -6,11 +6,17 @@ on:
jobs: jobs:
build: build:
if: ${{ startsWith(github.ref, 'refs/tags/nym-contracts-') && github.event_name == 'release' }} runs-on: ubuntu-20.04
runs-on: [self-hosted, custom-runner-linux]
steps: steps:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Check the release tag starts with `nym-contracts-`
if: startsWith(github.ref, 'refs/tags/nym-contracts-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-contracts-...')
- name: Install Rust stable - name: Install Rust stable
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
with: with:
+3 -5
View File
@@ -2,13 +2,11 @@ name: Contracts
on: on:
push: push:
paths: paths-ignore:
- 'contracts/**' - 'explorer/**'
- 'common/**'
pull_request: pull_request:
paths-ignore: paths-ignore:
- 'contracts/**' - 'explorer/**'
- 'common/**'
jobs: jobs:
matrix_prep: matrix_prep:
+1 -2
View File
@@ -10,7 +10,6 @@ env:
jobs: jobs:
publish-nym: publish-nym:
if: ${{ startsWith(github.ref, 'refs/tags/nym-explorer-api-') && (github.event_name == 'release' || github.event_name == 'workflow_dispatch') }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@@ -22,9 +21,9 @@ jobs:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Check the release tag starts with `nym-explorer-api-` - name: Check the release tag starts with `nym-explorer-api-`
if: startsWith(github.ref, 'refs/tags/nym-explorer-api-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3 uses: actions/github-script@v3
with: with:
script: | script: |
+6 -3
View File
@@ -17,7 +17,6 @@ jobs:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Install rsync - name: Install rsync
run: sudo apt-get install rsync run: sudo apt-get install rsync
continue-on-error: true
- uses: rlespinasse/github-slug-action@v3.x - uses: rlespinasse/github-slug-action@v3.x
- uses: actions/setup-node@v3 - uses: actions/setup-node@v3
with: with:
@@ -57,10 +56,10 @@ jobs:
REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }} REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }}
TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/ne-sb-${{ env.GITHUB_REF_SLUG }} TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/ne-sb-${{ env.GITHUB_REF_SLUG }}
EXCLUDE: "/dist/, /node_modules/" EXCLUDE: "/dist/, /node_modules/"
- name: Matrix - Node Install - name: Keybase - Node Install
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
env: env:
NYM_NOTIFICATION_KIND: network-explorer NYM_NOTIFICATION_KIND: network-explorer
NYM_PROJECT_NAME: "Network Explorer" NYM_PROJECT_NAME: "Network Explorer"
@@ -69,6 +68,10 @@ jobs:
NYM_CI_WWW_LOCATION_STORYBOOK: "ne-sb-${{ env.GITHUB_REF_SLUG }}" NYM_CI_WWW_LOCATION_STORYBOOK: "ne-sb-${{ env.GITHUB_REF_SLUG }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-network-explorer"
IS_SUCCESS: "${{ job.status == 'success' }}" IS_SUCCESS: "${{ job.status == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
+56 -38
View File
@@ -10,7 +10,7 @@ jobs:
matrix: ${{ steps.set-matrix.outputs.matrix }} matrix: ${{ steps.set-matrix.outputs.matrix }}
steps: steps:
# creates the matrix strategy from nightly_build_matrix_includes.json # creates the matrix strategy from nightly_build_matrix_includes.json
- uses: actions/checkout@v3 - uses: actions/checkout@v2
- id: set-matrix - id: set-matrix
uses: JoshuaTheMiller/conditional-build-matrix@main uses: JoshuaTheMiller/conditional-build-matrix@main
with: with:
@@ -25,11 +25,10 @@ jobs:
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
if: matrix.os == 'ubuntu-20.04' if: matrix.os == 'ubuntu-20.04'
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v3 uses: actions/checkout@v2
- name: Install rust toolchain - name: Install rust toolchain
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
@@ -39,33 +38,15 @@ jobs:
override: true override: true
components: rustfmt, clippy components: rustfmt, clippy
- name: Check formatting
uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
- name: Build all binaries - name: Build all binaries
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: build command: build
args: --workspace args: --workspace
- name: Reclaim some disk space - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Build all examples
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --examples
- name: Reclaim some disk space
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }}
with: with:
command: clean command: clean
@@ -75,9 +56,9 @@ jobs:
command: test command: test
args: --workspace args: --workspace
- name: Reclaim some disk space - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} if: ${{ matrix.os == 'windows-latest' }}
with: with:
command: clean command: clean
@@ -86,11 +67,17 @@ jobs:
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --workspace -- --ignored args: --workspace --all-features -- --ignored
- name: Reclaim some disk space - name: Check formatting
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} with:
command: fmt
args: --all -- --check
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with: with:
command: clean command: clean
@@ -99,7 +86,7 @@ jobs:
continue-on-error: true continue-on-error: true
with: with:
token: ${{ secrets.GITHUB_TOKEN }} token: ${{ secrets.GITHUB_TOKEN }}
args: --workspace args: --all-features
- name: Run clippy - name: Run clippy
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -114,6 +101,38 @@ jobs:
with: with:
command: clean command: clean
# COCONUT stuff
- name: Build all binaries with coconut enabled
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run all tests with coconut enabled
uses: actions-rs/cargo@v1
with:
command: test
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run clippy with coconut enabled
uses: actions-rs/cargo@v1
if: ${{ matrix.rust != 'nightly' }}
with:
command: clippy
args: --workspace --all-targets --features=coconut -- -D warnings
# nym-wallet (the rust part) # nym-wallet (the rust part)
- name: Build nym-wallet rust code - name: Build nym-wallet rust code
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -147,17 +166,12 @@ jobs:
- name: Collect jobs status - name: Collect jobs status
uses: technote-space/workflow-conclusion-action@v2 uses: technote-space/workflow-conclusion-action@v2
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v3 uses: actions/checkout@v2
- name: install npm - name: Keybase - Node Install
uses: actions/setup-node@v3
if: env.WORKFLOW_CONCLUSION == 'failure'
with:
node-version: 16
- name: Matrix - Node Install
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
env: env:
NYM_NOTIFICATION_KIND: nightly NYM_NOTIFICATION_KIND: nightly
@@ -165,9 +179,13 @@ jobs:
GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}" GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-nightly"
IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}" IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM_NIGHTLY }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}" MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}" MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}" MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
+54 -36
View File
@@ -28,7 +28,7 @@ jobs:
run: git fetch --all run: git fetch --all
- name: Set output variable to latest release branch - name: Set output variable to latest release branch
id: step2 id: step2
run: echo "latest_release=$(git branch -r | grep -E 'release/v[0-9]+\.[0-9]+\.[0-9]+$' | sort -V | tail -n 1 | sed 's/ origin\///')" >> $GITHUB_OUTPUT run: echo "latest_release=$(git branch -r | grep -E 'release/v[0-9]+\.[0-9]+\.[0-9]+' | tail -n 1 | sed 's/ origin\///')" >> $GITHUB_OUTPUT
build: build:
needs: [get_release,matrix_prep] needs: [get_release,matrix_prep]
strategy: strategy:
@@ -38,7 +38,6 @@ jobs:
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
if: matrix.os == 'ubuntu-20.04' if: matrix.os == 'ubuntu-20.04'
- name: Check out latest release branch - name: Check out latest release branch
@@ -54,33 +53,15 @@ jobs:
override: true override: true
components: rustfmt, clippy components: rustfmt, clippy
- name: Check formatting
uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
- name: Build all binaries - name: Build all binaries
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: build command: build
args: --workspace args: --workspace
- name: Reclaim some disk space - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Build all examples
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --examples
- name: Reclaim some disk space
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }}
with: with:
command: clean command: clean
@@ -90,9 +71,9 @@ jobs:
command: test command: test
args: --workspace args: --workspace
- name: Reclaim some disk space - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} if: ${{ matrix.os == 'windows-latest' }}
with: with:
command: clean command: clean
@@ -101,11 +82,17 @@ jobs:
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --workspace -- --ignored args: --workspace --all-features -- --ignored
- name: Reclaim some disk space - name: Check formatting
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} with:
command: fmt
args: --all -- --check
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with: with:
command: clean command: clean
@@ -114,7 +101,7 @@ jobs:
continue-on-error: true continue-on-error: true
with: with:
token: ${{ secrets.GITHUB_TOKEN }} token: ${{ secrets.GITHUB_TOKEN }}
args: --workspace args: --all-features
- name: Run clippy - name: Run clippy
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -129,6 +116,38 @@ jobs:
with: with:
command: clean command: clean
# COCONUT stuff
- name: Build all binaries with coconut enabled
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run all tests with coconut enabled
uses: actions-rs/cargo@v1
with:
command: test
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run clippy with coconut enabled
uses: actions-rs/cargo@v1
if: ${{ matrix.rust != 'nightly' }}
with:
command: clippy
args: --workspace --all-targets --features=coconut -- -D warnings
# nym-wallet (the rust part) # nym-wallet (the rust part)
- name: Build nym-wallet rust code - name: Build nym-wallet rust code
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -163,16 +182,11 @@ jobs:
uses: technote-space/workflow-conclusion-action@v2 uses: technote-space/workflow-conclusion-action@v2
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v3 uses: actions/checkout@v3
- name: install npm - name: Keybase - Node Install
uses: actions/setup-node@v3
if: env.WORKFLOW_CONCLUSION == 'failure'
with:
node-version: 16
- name: Matrix - Node Install
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
env: env:
NYM_NOTIFICATION_KIND: nightly NYM_NOTIFICATION_KIND: nightly
@@ -180,9 +194,13 @@ jobs:
GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}" GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH_NAME: "${{needs.get_release.outputs.output1}}" GIT_BRANCH_NAME: "${{needs.get_release.outputs.output1}}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-nightly-release"
IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}" IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM_NIGHTLY }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}" MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}" MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}" MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
+49 -31
View File
@@ -28,7 +28,7 @@ jobs:
run: git fetch --all run: git fetch --all
- name: Set output variable to latest release branch - name: Set output variable to latest release branch
id: step2 id: step2
run: echo "latest_release=$(git branch -r | grep -E 'release/v[0-9]+\.[0-9]+\.[0-9]+$' | sort -V | tail -n 2 | head -n 1 | sed 's/ origin\///')" >> $GITHUB_OUTPUT run: echo "latest_release=$(git branch -r | grep -E 'release/v[0-9]+\.[0-9]+\.[0-9]+' | tail -n 2 | head -n 1 | sed 's/ origin\///')" >> $GITHUB_OUTPUT
build: build:
needs: [get_release,matrix_prep] needs: [get_release,matrix_prep]
strategy: strategy:
@@ -38,7 +38,6 @@ jobs:
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
if: matrix.os == 'ubuntu-20.04' if: matrix.os == 'ubuntu-20.04'
- name: Check out latest release branch - name: Check out latest release branch
@@ -54,12 +53,6 @@ jobs:
override: true override: true
components: rustfmt, clippy components: rustfmt, clippy
- name: Check formatting
uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
- name: Build all binaries - name: Build all binaries
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
@@ -72,18 +65,6 @@ jobs:
with: with:
command: clean command: clean
- name: Build all examples
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --examples
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run all tests - name: Run all tests
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
@@ -92,7 +73,7 @@ jobs:
- name: Reclaim some disk space (because Windows is being annoying) - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' || matrix.os == 'ubuntu-20.04' }} if: ${{ matrix.os == 'windows-latest' }}
with: with:
command: clean command: clean
@@ -101,7 +82,13 @@ jobs:
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
with: with:
command: test command: test
args: --workspace -- --ignored args: --workspace --all-features -- --ignored
- name: Check formatting
uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
- name: Reclaim some disk space (because Windows is being annoying) - name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -114,7 +101,7 @@ jobs:
continue-on-error: true continue-on-error: true
with: with:
token: ${{ secrets.GITHUB_TOKEN }} token: ${{ secrets.GITHUB_TOKEN }}
args: --workspace args: --all-features
- name: Run clippy - name: Run clippy
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -129,6 +116,38 @@ jobs:
with: with:
command: clean command: clean
# COCONUT stuff
- name: Build all binaries with coconut enabled
uses: actions-rs/cargo@v1
with:
command: build
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run all tests with coconut enabled
uses: actions-rs/cargo@v1
with:
command: test
args: --workspace --features=coconut
- name: Reclaim some disk space (because Windows is being annoying)
uses: actions-rs/cargo@v1
if: ${{ matrix.os == 'windows-latest' }}
with:
command: clean
- name: Run clippy with coconut enabled
uses: actions-rs/cargo@v1
if: ${{ matrix.rust != 'nightly' }}
with:
command: clippy
args: --workspace --all-targets --features=coconut -- -D warnings
# nym-wallet (the rust part) # nym-wallet (the rust part)
- name: Build nym-wallet rust code - name: Build nym-wallet rust code
uses: actions-rs/cargo@v1 uses: actions-rs/cargo@v1
@@ -163,16 +182,11 @@ jobs:
uses: technote-space/workflow-conclusion-action@v2 uses: technote-space/workflow-conclusion-action@v2
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v3 uses: actions/checkout@v3
- name: install npm - name: Keybase - Node Install
uses: actions/setup-node@v3
if: env.WORKFLOW_CONCLUSION == 'failure'
with:
node-version: 16
- name: Matrix - Node Install
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
if: env.WORKFLOW_CONCLUSION == 'failure' if: env.WORKFLOW_CONCLUSION == 'failure'
env: env:
NYM_NOTIFICATION_KIND: nightly NYM_NOTIFICATION_KIND: nightly
@@ -180,9 +194,13 @@ jobs:
GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}" GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH_NAME: "${{needs.get_release.outputs.output1}}" GIT_BRANCH_NAME: "${{needs.get_release.outputs.output1}}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-nightly-release"
IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}" IS_SUCCESS: "${{ env.WORKFLOW_CONCLUSION == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM_NIGHTLY }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}" MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}" MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}" MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
+1 -1
View File
@@ -10,7 +10,6 @@ env:
jobs: jobs:
publish-nym-cli: publish-nym-cli:
if: ${{ startsWith(github.ref, 'refs/tags/nym-cli-') && (github.event_name == 'release' || github.event_name == 'workflow_dispatch') }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@@ -21,6 +20,7 @@ jobs:
- uses: actions/checkout@v3 - uses: actions/checkout@v3
- name: Check the release tag starts with `nym-cli-` - name: Check the release tag starts with `nym-cli-`
if: startsWith(github.ref, 'refs/tags/nym-cli-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3 uses: actions/github-script@v3
with: with:
script: | script: |
+14 -13
View File
@@ -1,4 +1,4 @@
name: Publish Nym Connect - desktop (MacOS) name: Publish Nym Connect (MacOS)
on: on:
workflow_dispatch: workflow_dispatch:
release: release:
@@ -6,33 +6,34 @@ on:
defaults: defaults:
run: run:
working-directory: nym-connect/desktop working-directory: nym-connect
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ (startsWith(github.ref, 'refs/tags/nym-connect-') && github.event_name == 'release') || github.event_name == 'workflow_dispatch' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
platform: [custom-runner-mac-m1] platform: [macos-latest]
runs-on: ${{ matrix.platform }} runs-on: ${{ matrix.platform }}
steps: steps:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Check the release tag starts with `nym-connect-`
if: startsWith(github.ref, 'refs/tags/nym-connect-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-connect-...')
- name: Node v16 - name: Node v16
uses: actions/setup-node@v3 uses: actions/setup-node@v3
with: with:
node-version: 16 node-version: 16
- name: Setup yarn
run: npm install -g yarn
- name: Install Rust stable - name: Install Rust stable
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
with: with:
toolchain: stable toolchain: stable
- name: Install the Apple developer certificate for code signing - name: Install the Apple developer certificate for code signing
env: env:
APPLE_CERTIFICATE: ${{ secrets.APPLE_CERTIFICATE }} APPLE_CERTIFICATE: ${{ secrets.APPLE_CERTIFICATE }}
@@ -44,7 +45,7 @@ jobs:
KEYCHAIN_PATH=$RUNNER_TEMP/app-signing.keychain-db KEYCHAIN_PATH=$RUNNER_TEMP/app-signing.keychain-db
# import certificate and provisioning profile from secrets # import certificate and provisioning profile from secrets
echo -n "$APPLE_CERTIFICATE" | base64 --decode --output=$CERTIFICATE_PATH echo -n "$APPLE_CERTIFICATE" | base64 --decode --output $CERTIFICATE_PATH
# create temporary keychain # create temporary keychain
security create-keychain -p "$KEYCHAIN_PASSWORD" $KEYCHAIN_PATH security create-keychain -p "$KEYCHAIN_PASSWORD" $KEYCHAIN_PATH
@@ -78,7 +79,7 @@ jobs:
uses: actions/upload-artifact@v3 uses: actions/upload-artifact@v3
with: with:
name: nym-connect_1.0.0_x64.dmg name: nym-connect_1.0.0_x64.dmg
path: nym-connect/desktop/target/release/bundle/dmg/nym-connect_1.0.0_x64.dmg path: nym-connect/target/release/bundle/dmg/nym-connect_1.0.0_x64.dmg
retention-days: 30 retention-days: 30
- name: Clean up keychain - name: Clean up keychain
@@ -91,5 +92,5 @@ jobs:
if: github.event_name == 'release' if: github.event_name == 'release'
with: with:
files: | files: |
nym-connect/desktop/target/release/bundle/dmg/*.dmg nym-connect/target/release/bundle/dmg/*.dmg
nym-connect/desktop/target/release/bundle/macos/*.app.tar.gz* nym-connect/target/release/bundle/macos/*.app.tar.gz*
@@ -1,4 +1,4 @@
name: Publish Nym Connect - desktop (Ubuntu) name: Publish Nym Connect (Ubuntu)
on: on:
workflow_dispatch: workflow_dispatch:
release: release:
@@ -6,15 +6,14 @@ on:
defaults: defaults:
run: run:
working-directory: nym-connect/desktop working-directory: nym-connect
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ startsWith(github.ref, 'refs/tags/nym-connect-') && github.event_name == 'release' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
platform: [custom-runner-linux] platform: [ubuntu-20.04]
runs-on: ${{ matrix.platform }} runs-on: ${{ matrix.platform }}
steps: steps:
@@ -24,13 +23,17 @@ jobs:
run: > run: >
sudo apt-get update && sudo apt-get update &&
sudo apt-get install -y webkit2gtk-4.0 libayatana-appindicator3-dev sudo apt-get install -y webkit2gtk-4.0 libayatana-appindicator3-dev
continue-on-error: true - name: Check the release tag starts with `nym-connect-`
if: startsWith(github.ref, 'refs/tags/nym-connect-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-connect-...')
- name: Node v16 - name: Node v16
uses: actions/setup-node@v3 uses: actions/setup-node@v3
with: with:
node-version: 16 node-version: 16
- name: Install Rust stable - name: Install Rust stable
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
with: with:
@@ -53,7 +56,7 @@ jobs:
uses: actions/upload-artifact@v3 uses: actions/upload-artifact@v3
with: with:
name: nym-connect.AppImage.tar.gz name: nym-connect.AppImage.tar.gz
path: nym-connect/desktop/target/release/bundle/appimage/nym-connect_1.0.0_amd64.AppImage path: nym-connect/target/release/bundle/appimage/nym-connect_1.0.0_amd64.AppImage
retention-days: 30 retention-days: 30
- name: Upload to release based on tag name - name: Upload to release based on tag name
@@ -61,5 +64,5 @@ jobs:
if: github.event_name == 'release' if: github.event_name == 'release'
with: with:
files: | files: |
nym-connect/desktop/target/release/bundle/appimage/*.AppImage nym-connect/target/release/bundle/appimage/*.AppImage
nym-connect/desktop/target/release/bundle/appimage/*.AppImage.tar.gz* nym-connect/target/release/bundle/appimage/*.AppImage.tar.gz*
@@ -1,4 +1,4 @@
name: Publish Nym Connect - desktop (Windows 10) name: Publish Nym Connect (Windows 10)
on: on:
workflow_dispatch: workflow_dispatch:
release: release:
@@ -6,11 +6,10 @@ on:
defaults: defaults:
run: run:
working-directory: nym-connect/desktop working-directory: nym-connect
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ (startsWith(github.ref, 'refs/tags/nym-connect-') && github.event_name == 'release') || github.event_name == 'workflow_dispatch' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@@ -28,6 +27,13 @@ jobs:
- uses: actions/checkout@v3 - uses: actions/checkout@v3
- name: Check the release tag starts with `nym-connect-`
if: startsWith(github.ref, 'refs/tags/nym-connect-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-connect-...')
- name: Import signing certificate - name: Import signing certificate
env: env:
WINDOWS_CERTIFICATE: ${{ secrets.WINDOWS_CERTIFICATE }} WINDOWS_CERTIFICATE: ${{ secrets.WINDOWS_CERTIFICATE }}
@@ -56,7 +62,7 @@ jobs:
encodedString: ${{ secrets.WALLET_ADMIN_ADDRESS }} encodedString: ${{ secrets.WALLET_ADMIN_ADDRESS }}
- name: Install app dependencies - name: Install app dependencies
run: yarn --network-timeout 100000 run: yarn
- name: Build and sign it - name: Build and sign it
env: env:
@@ -72,7 +78,7 @@ jobs:
uses: actions/upload-artifact@v3 uses: actions/upload-artifact@v3
with: with:
name: nym-connect_1.0.0_x64_en-US.msi name: nym-connect_1.0.0_x64_en-US.msi
path: nym-connect/desktop/target/release/bundle/msi/nym-connect_1.0.0_x64_en-US.msi path: nym-connect/target/release/bundle/msi/nym-connect_1.0.0_x64_en-US.msi
retention-days: 30 retention-days: 30
- name: Upload to release based on tag name - name: Upload to release based on tag name
@@ -80,5 +86,5 @@ jobs:
if: github.event_name == 'release' if: github.event_name == 'release'
with: with:
files: | files: |
nym-connect/desktop/target/release/bundle/msi/*.msi nym-connect/target/release/bundle/msi/*.msi
nym-connect/desktop/target/release/bundle/msi/*.msi.zip* nym-connect/target/release/bundle/msi/*.msi.zip*
@@ -1,13 +1,13 @@
name: CI for nym-connect - Desktop name: CI for nym-connect
on: on:
push: push:
paths: paths:
- 'nym-connect/desktop/**' - 'nym-connect/**'
defaults: defaults:
run: run:
working-directory: nym-connect/desktop working-directory: nym-connect
jobs: jobs:
build: build:
@@ -16,7 +16,6 @@ jobs:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Install rsync - name: Install rsync
run: sudo apt-get install rsync run: sudo apt-get install rsync
continue-on-error: true
- uses: rlespinasse/github-slug-action@v3.x - uses: rlespinasse/github-slug-action@v3.x
- uses: actions/setup-node@v3 - uses: actions/setup-node@v3
with: with:
@@ -34,15 +33,15 @@ jobs:
env: env:
SSH_PRIVATE_KEY: ${{ secrets.CI_WWW_SSH_PRIVATE_KEY }} SSH_PRIVATE_KEY: ${{ secrets.CI_WWW_SSH_PRIVATE_KEY }}
ARGS: "-rltgoDzvO --delete" ARGS: "-rltgoDzvO --delete"
SOURCE: "nym-connect/desktop/storybook-static/" SOURCE: "nym-connect/storybook-static/"
REMOTE_HOST: ${{ secrets.CI_WWW_REMOTE_HOST }} REMOTE_HOST: ${{ secrets.CI_WWW_REMOTE_HOST }}
REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }} REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }}
TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/nym-connect-${{ env.GITHUB_REF_SLUG }} TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/nym-connect-${{ env.GITHUB_REF_SLUG }}
EXCLUDE: "/dist/, /node_modules/" EXCLUDE: "/dist/, /node_modules/"
- name: Matrix - Node Install - name: Keybase - Node Install
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
env: env:
NYM_NOTIFICATION_KIND: nym-connect NYM_NOTIFICATION_KIND: nym-connect
NYM_PROJECT_NAME: "nym-connect" NYM_PROJECT_NAME: "nym-connect"
@@ -50,6 +49,10 @@ jobs:
NYM_CI_WWW_LOCATION: "nym-connect-${{ env.GITHUB_REF_SLUG }}" NYM_CI_WWW_LOCATION: "nym-connect-${{ env.GITHUB_REF_SLUG }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-nym-connect"
IS_SUCCESS: "${{ job.status == 'success' }}" IS_SUCCESS: "${{ job.status == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
+10 -7
View File
@@ -16,11 +16,10 @@ env:
jobs: jobs:
publish-nym: publish-nym:
if: ${{ startsWith(github.ref, 'refs/tags/nym-binaries-') && github.event_name == 'release' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
platform: [custom-runner-linux] platform: [ubuntu-20.04]
runs-on: ${{ matrix.platform }} runs-on: ${{ matrix.platform }}
steps: steps:
@@ -28,7 +27,13 @@ jobs:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev libudev-dev squashfs-tools
continue-on-error: true
- name: Check the release tag starts with `nym-binaries-`
if: startsWith(github.ref, 'refs/tags/nym-binaries-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-binaries-...')
- name: Sets env vars for tokio if set in manual dispatch inputs - name: Sets env vars for tokio if set in manual dispatch inputs
run: | run: |
@@ -51,12 +56,11 @@ jobs:
with: with:
name: my-artifact name: my-artifact
path: | path: |
target/release/explorer-api
target/release/nym-client target/release/nym-client
target/release/nym-gateway target/release/nym-gateway
target/release/nym-mixnode target/release/nym-mixnode
target/release/nym-socks5-client target/release/nym-socks5-client
target/release/nym-api target/release/nym-validator-api
target/release/nym-network-requester target/release/nym-network-requester
target/release/nym-network-statistics target/release/nym-network-statistics
target/release/nym-cli target/release/nym-cli
@@ -67,12 +71,11 @@ jobs:
if: github.event_name == 'release' if: github.event_name == 'release'
with: with:
files: | files: |
target/release/explorer-api
target/release/nym-client target/release/nym-client
target/release/nym-gateway target/release/nym-gateway
target/release/nym-mixnode target/release/nym-mixnode
target/release/nym-socks5-client target/release/nym-socks5-client
target/release/nym-api target/release/nym-validator-api
target/release/nym-network-requester target/release/nym-network-requester
target/release/nym-network-statistics target/release/nym-network-statistics
target/release/nym-cli target/release/nym-cli
@@ -10,7 +10,6 @@ defaults:
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ startsWith(github.ref, 'refs/tags/nym-wallet-') && github.event_name == 'release' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@@ -20,6 +19,13 @@ jobs:
steps: steps:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Check the release tag starts with `nym-wallet-`
if: startsWith(github.ref, 'refs/tags/nym-wallet-') == false && github.event_name != 'workflow_dispatch'
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-wallet-...')
- name: Node v16 - name: Node v16
uses: actions/setup-node@v3 uses: actions/setup-node@v3
with: with:
@@ -9,11 +9,10 @@ defaults:
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ startsWith(github.ref, 'refs/tags/nym-wallet-') && github.event_name == 'release' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
platform: [custom-runner-linux] platform: [ubuntu-20.04]
runs-on: ${{ matrix.platform }} runs-on: ${{ matrix.platform }}
steps: steps:
@@ -23,13 +22,17 @@ jobs:
run: > run: >
sudo apt-get update && sudo apt-get update &&
sudo apt-get install -y webkit2gtk-4.0 sudo apt-get install -y webkit2gtk-4.0
continue-on-error: true - name: Check the release tag starts with `nym-wallet-`
if: startsWith(github.ref, 'refs/tags/nym-wallet-') == false
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-wallet-...')
- name: Node v16 - name: Node v16
uses: actions/setup-node@v3 uses: actions/setup-node@v3
with: with:
node-version: 16 node-version: 16
- name: Install Rust stable - name: Install Rust stable
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
with: with:
@@ -1,6 +1,5 @@
name: Publish Nym Wallet (Windows 10) name: Publish Nym Wallet (Windows 10)
on: on:
workflow_dispatch:
release: release:
types: [created] types: [created]
@@ -10,7 +9,6 @@ defaults:
jobs: jobs:
publish-tauri: publish-tauri:
if: ${{ (startsWith(github.ref, 'refs/tags/nym-wallet-') && github.event_name == 'release') || github.event_name == 'workflow_dispatch' }}
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@@ -28,6 +26,13 @@ jobs:
- uses: actions/checkout@v3 - uses: actions/checkout@v3
- name: Check the release tag starts with `nym-wallet-`
if: startsWith(github.ref, 'refs/tags/nym-wallet-') == false
uses: actions/github-script@v3
with:
script: |
core.setFailed('Release tag did not start with nym-wallet-...')
- name: Import signing certificate - name: Import signing certificate
env: env:
WINDOWS_CERTIFICATE: ${{ secrets.WINDOWS_CERTIFICATE }} WINDOWS_CERTIFICATE: ${{ secrets.WINDOWS_CERTIFICATE }}
@@ -56,7 +61,7 @@ jobs:
encodedString: ${{ secrets.WALLET_ADMIN_ADDRESS }} encodedString: ${{ secrets.WALLET_ADMIN_ADDRESS }}
- name: Install app dependencies - name: Install app dependencies
run: yarn --network-timeout 100000 run: yarn
- name: Build and sign it - name: Build and sign it
env: env:
@@ -68,16 +73,8 @@ jobs:
TAURI_KEY_PASSWORD: ${{ secrets.TAURI_KEY_PASSWORD }} TAURI_KEY_PASSWORD: ${{ secrets.TAURI_KEY_PASSWORD }}
run: yarn build run: yarn build
- name: Upload Artifact
uses: actions/upload-artifact@v3
with:
name: nym-wallet_1.0.0_x64_en-US.msi
path: nym-wallet/target/release/bundle/msi/nym-wallet_1.*.msi
retention-days: 30
- name: Upload to release based on tag name - name: Upload to release based on tag name
uses: softprops/action-gh-release@v1 uses: softprops/action-gh-release@v1
if: github.event_name == 'release'
with: with:
files: | files: |
nym-wallet/target/release/bundle/msi/*.msi nym-wallet/target/release/bundle/msi/*.msi
+6 -3
View File
@@ -12,7 +12,6 @@ jobs:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- name: Install rsync - name: Install rsync
run: sudo apt-get install rsync run: sudo apt-get install rsync
continue-on-error: true
- uses: rlespinasse/github-slug-action@v3.x - uses: rlespinasse/github-slug-action@v3.x
- uses: actions/setup-node@v3 - uses: actions/setup-node@v3
with: with:
@@ -35,10 +34,10 @@ jobs:
REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }} REMOTE_USER: ${{ secrets.CI_WWW_REMOTE_USER }}
TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/wallet-${{ env.GITHUB_REF_SLUG }} TARGET: ${{ secrets.CI_WWW_REMOTE_TARGET }}/wallet-${{ env.GITHUB_REF_SLUG }}
EXCLUDE: "/dist/, /node_modules/" EXCLUDE: "/dist/, /node_modules/"
- name: Matrix - Node Install - name: Keybase - Node Install
run: npm install run: npm install
working-directory: .github/workflows/support-files working-directory: .github/workflows/support-files
- name: Matrix - Send Notification - name: Keybase - Send Notification
env: env:
NYM_NOTIFICATION_KIND: nym-wallet NYM_NOTIFICATION_KIND: nym-wallet
NYM_PROJECT_NAME: "nym-wallet" NYM_PROJECT_NAME: "nym-wallet"
@@ -46,6 +45,10 @@ jobs:
NYM_CI_WWW_LOCATION: "wallet-${{ env.GITHUB_REF_SLUG }}" NYM_CI_WWW_LOCATION: "wallet-${{ env.GITHUB_REF_SLUG }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}" GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
KEYBASE_NYM_CHANNEL: "ci-nym-wallet"
IS_SUCCESS: "${{ job.status == 'success' }}" IS_SUCCESS: "${{ job.status == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}" MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
-1
View File
@@ -26,7 +26,6 @@ jobs:
libappindicator3-dev libappindicator3-dev
webkit2gtk-driver webkit2gtk-driver
xvfb xvfb
continue-on-error: true
- name: Install minimal stable - name: Install minimal stable
uses: actions-rs/toolchain@v1 uses: actions-rs/toolchain@v1
-36
View File
@@ -1,36 +0,0 @@
name: CI for Nym API Tests
on:
workflow_dispatch:
push:
paths:
- "nym-api/**"
defaults:
run:
working-directory: nym-api/tests
jobs:
test:
name: nym-api tests
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Install npm
run: npm install
- name: Node v18
uses: actions/setup-node@v3
with:
node-version: 18.1.0
- name: Install yarn
run: yarn install
- name: Run yarn
run: yarn
- name: Run tests
run: yarn test:qa
working-directory: nym-api/tests
@@ -1,3 +1,7 @@
KEYBASE_NYM_CHANNEL=
KEYBASE_NYMBOT_USERNAME=
KEYBASE_NYMBOT_PAPERKEY=
MATRIX_SERVER= MATRIX_SERVER=
MATRIX_ROOM= MATRIX_ROOM=
MATRIX_ROOM_OF_SHAME= MATRIX_ROOM_OF_SHAME=
+7 -8
View File
@@ -4,7 +4,7 @@ This is a collection of scripts and files to support GitHub Actions.
## Sending Notifications ## Sending Notifications
These scripts send CI notifications to Matrix by creating messages from templates and env vars passed from GitHub Actions. These scripts send CI notifications to Keybase by creating messages from templates and env vars passed from GitHub Actions.
### Adding notifications to a GitHub Action ### Adding notifications to a GitHub Action
@@ -19,11 +19,10 @@ jobs:
env: env:
NYM_NOTIFICATION_KIND: "my-component" NYM_NOTIFICATION_KIND: "my-component"
GIT_BRANCH: "${GITHUB_REF##*/}" GIT_BRANCH: "${GITHUB_REF##*/}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}" KEYBASE_NYMBOT_USERNAME: "${{ secrets.KEYBASE_NYMBOT_USERNAME }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}" KEYBASE_NYMBOT_PAPERKEY: "${{ secrets.KEYBASE_NYMBOT_PAPERKEY }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}" KEYBASE_NYMBOT_TEAM: "${{ secrets.KEYBASE_NYMBOT_TEAM }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}" KEYBASE_NYM_CHANNEL: "ci-network-explorer"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
IS_SUCCESS: "${{ job.status == 'success' }}" IS_SUCCESS: "${{ job.status == 'success' }}"
uses: docker://keybaseio/client:stable-node uses: docker://keybaseio/client:stable-node
with: with:
@@ -35,7 +34,7 @@ Notifications are run by adding the snippet above to a GitHub Action, and:
1. Installing node packages needed at run time 1. Installing node packages needed at run time
2. Set the env vars as required: 2. Set the env vars as required:
- `NYM_NOTIFICATION_KIND` matches the directory in `.github/workflows/support-files/${NYM_NOTIFICATION_KIND}` to provide the templates and extra scripting in `index.js` - `NYM_NOTIFICATION_KIND` matches the directory in `.github/workflows/support-files/${NYM_NOTIFICATION_KIND}` to provide the templates and extra scripting in `index.js`
- Matrix credentials, room and other env vars for the status of the build and repo - Keybase credentials, channel and other env vars for the status of the build and repo
3. Replacing the default entry point shell script on the `keybaseio/client:stable-node` docker image to run `.github/workflows/support-files/notifications/entry_point.sh` 3. Replacing the default entry point shell script on the `keybaseio/client:stable-node` docker image to run `.github/workflows/support-files/notifications/entry_point.sh`
### Running locally ### Running locally
@@ -44,7 +43,7 @@ You will need:
- Node 16 LTS - Node 16 LTS
- npm - npm
Copy `.github/workflows/support-files/.env.example` to `.github/workflows/support-files/.env` and valid Matrix credentials. Copy `.github/workflows/support-files/.env.example` to `.github/workflows/support-files/.env` and valid Keybase credentials.
Then run `npm install` to get dependencies. Then run `npm install` to get dependencies.
@@ -1,62 +0,0 @@
#!/usr/bin/env bash
#
# Basic usage:
# ./git-merge-check origin/develop origin/release/v1.1.9
#
set -x
set -o nounset
set -o pipefail
# Start from branch ...
branch1=$1
# ... and try to merge in
branch2=$2
echo "Checking if $branch2 merges without conflicts into $branch1..."
git checkout -q $branch1 || exit 1
# There are two options here as far as I see on what we should check for. Either
#
# (A) check for CONFLICT in any file except whitelist (such as .lock files)
# (B) check for "Automatic merge failed"
#
# Both of these options have drawbacks.
#
# The first (A) has the problem in that maybe we don't want to fail if the
# changes can be automatically merged (duh), but at least we are not pestered
# about constant lock file changes.
# The second (B) has the problem that it's difficult to filter out automatic
# merge fails for files we don't care about (.lock files).
#
# The ideal solution would be to check for automatic merge fails for files
# except those on a whitelist (e.g. lock files).
# For now I choose to use (B) here, because I hope it might be less noisy
# Alternative A
#output=$(git merge --no-commit --no-ff $branch2 | grep -v .lock)
#merge_failed=$(echo $output | grep -v "CONFLICT")
#return_code=$?
# Alternative B
output=$(git merge --no-commit --no-ff $branch2)
merge_failed=$(echo $output | grep -v "Automatic merge failed")
return_code=$?
# Restore
git merge --abort
git checkout -q -
if [ $return_code -eq 0 ]; then
echo "Merge check success"
else
echo "Merge check failed"
fi
exit $return_code
@@ -1,14 +1,9 @@
🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> 🔴 **FAILURE** :cry: > 🔴 **FAILURE** :cry:
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message: Commit message:
``` ```
@@ -1,16 +1,10 @@
🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩 🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩
> :rocket: {{ env.NYM_PROJECT_NAME }} ➡️➡️➡️➡️➡️ **View output:** https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}/ > :rocket: {{ env.NYM_PROJECT_NAME }} ➡️➡️➡️➡️➡️ **View output:** https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}/
>
> `storybook`: https://{{ env.NYM_CI_WWW_LOCATION_STORYBOOK }}.{{ env.NYM_CI_WWW_BASE }} > `storybook`: https://{{ env.NYM_CI_WWW_LOCATION_STORYBOOK }}.{{ env.NYM_CI_WWW_BASE }}
>
> ✅ **SUCCESS** > ✅ **SUCCESS**
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}: Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}:
``` ```
@@ -151,7 +151,7 @@ async function getMessageBody(context) {
return `${icon} ${job.conclusion}: ${job.name} - ${job.html_url}`; return `${icon} ${job.conclusion}: ${job.name} - ${job.html_url}`;
}) })
// and join with newlines for display in the template // and join with newlines for display in the template
.join('\n\n'); .join('\n');
return template({ ...context, jobResults }); return template({ ...context, jobResults });
} }
@@ -1,15 +1,9 @@
🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> 🔴 **FAILURE** :cry: > 🔴 **FAILURE** :cry:
>
> `when` {{ timestamp }} > `when` {{ timestamp }}
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
{{ jobResults }} {{ jobResults }}
@@ -1,15 +1,9 @@
🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩 🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> ✅ **SUCCESS** > ✅ **SUCCESS**
>
> `when` {{ timestamp }} > `when` {{ timestamp }}
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
{{ jobResults }} {{ jobResults }}
@@ -1,5 +1,6 @@
require('dotenv').config(); require('dotenv').config();
const Bot = require('keybase-bot');
const { sendMatrixMessage } = require('./send_message_to_matrix'); const { sendMatrixMessage } = require('./send_message_to_matrix');
let context = { let context = {
@@ -23,6 +24,21 @@ function validateContext() {
'Please set env var NYM_PROJECT_NAME with the project name for displaying in notification messages', 'Please set env var NYM_PROJECT_NAME with the project name for displaying in notification messages',
); );
} }
if (!context.env.KEYBASE_NYM_CHANNEL) {
throw new Error(
'Please set env var KEYBASE_NYM_CHANNEL with the channel name for the notification message',
);
}
if (!context.env.KEYBASE_NYMBOT_USERNAME) {
throw new Error(
'Username is not defined. Please set env var KEYBASE_NYMBOT_USERNAME',
);
}
if (!context.env.KEYBASE_NYMBOT_PAPERKEY) {
throw new Error(
'Paperkey is not defined. Please set env var KEYBASE_NYMBOT_PAPERKEY',
);
}
if (context.env.MATRIX_ROOM) { if (context.env.MATRIX_ROOM) {
if (!context.env.MATRIX_SERVER) { if (!context.env.MATRIX_SERVER) {
throw new Error( throw new Error(
@@ -68,6 +84,12 @@ function createTemplateContext() {
context.kind = context.env.NYM_NOTIFICATION_KIND; context.kind = context.env.NYM_NOTIFICATION_KIND;
context.keybase = {
channel: context.env.KEYBASE_NYM_CHANNEL,
username: context.env.KEYBASE_NYMBOT_USERNAME,
paperkey: context.env.KEYBASE_NYMBOT_PAPERKEY,
};
if (!context.env.GIT_BRANCH_NAME) { if (!context.env.GIT_BRANCH_NAME) {
context.env.GIT_BRANCH_NAME = context.env.GITHUB_REF.split('/') context.env.GIT_BRANCH_NAME = context.env.GITHUB_REF.split('/')
.slice(2) .slice(2)
@@ -77,6 +99,40 @@ function createTemplateContext() {
context.status = process.env.IS_SUCCESS === 'true' ? 'success' : 'failure'; context.status = process.env.IS_SUCCESS === 'true' ? 'success' : 'failure';
} }
async function sendKeybaseMessage(messageBody) {
const bot = new Bot();
try {
console.log(
`Initialising keybase with user "${
context.keybase.username
}" and key: "${'*'.repeat(context.keybase.paperkey.length)}"...`,
);
await bot.init(context.keybase.username, context.keybase.paperkey, {
verbose: false,
});
const channel = {
name: context.env.KEYBASE_NYMBOT_TEAM || 'nymtech_bot',
membersType: 'team',
topicName: context.keybase.channel,
topic_type: 'CHAT',
};
const message = {
body: messageBody,
};
console.log(`Sending to ${channel.name}#${channel.topicName}...`);
await bot.chat.send(channel, message);
console.log('Message sent!');
} catch (error) {
console.error(error);
process.exitCode = -1;
} finally {
await bot.deinit();
}
}
/** /**
* Uses the `kind` set in the context to process the context and generate a notification message * Uses the `kind` set in the context to process the context and generate a notification message
* @returns {Promise<string>} A string notification message body * @returns {Promise<string>} A string notification message body
@@ -113,6 +169,7 @@ async function main() {
console.log(messageBody); console.log(messageBody);
console.log('-----------------------------------------'); console.log('-----------------------------------------');
} }
await sendKeybaseMessage(messageBody);
if(context.env.MATRIX_ROOM) { if(context.env.MATRIX_ROOM) {
await sendMatrixMessage(context, messageBody, context.env.MATRIX_ROOM) await sendMatrixMessage(context, messageBody, context.env.MATRIX_ROOM)
} }
@@ -5,7 +5,12 @@ const localStorage = new LocalStorage('./scratch');
const { const {
LocalStorageCryptoStore, LocalStorageCryptoStore,
} = require('matrix-js-sdk/lib/crypto/store/localStorage-crypto-store'); } = require('matrix-js-sdk/lib/crypto/store/localStorage-crypto-store');
var showdown = require('showdown');
const vfile = require('to-vfile');
const unified = require('unified');
const remarkParse = require('remark-parse');
const remarkHtml = require('remark-html');
const emoji = require('remark-emoji');
// hide all matrix client output // hide all matrix client output
console.error = (error) => console.log('❌ error: ', error); console.error = (error) => console.log('❌ error: ', error);
@@ -54,9 +59,17 @@ function createClient(context, room, message) {
return client; return client;
} }
async function markdownToHtml(messageAsMarkdown) {
const file = await unified()
.use(emoji)
.use(remarkParse)
.use(remarkHtml)
.process(await vfile({ path: 'test.md', contents: messageAsMarkdown}));
return String(file);
}
async function sendMatrixMessage(contextArg, messageAsMarkdown, roomId) { async function sendMatrixMessage(contextArg, messageAsMarkdown, roomId) {
const converter = new showdown.Converter(); const messageAsHtml = await markdownToHtml(messageAsMarkdown);
const messageAsHtml = converter.makeHtml(messageAsMarkdown);
const client = createClient(contextArg, roomId, messageAsHtml); const client = createClient(contextArg, roomId, messageAsHtml);
await client.initCrypto(); await client.initCrypto();
await client.startClient({ initialSyncLimit: 1 }); await client.startClient({ initialSyncLimit: 1 });
@@ -1,14 +1,9 @@
🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> 🔴 **FAILURE** :cry: > 🔴 **FAILURE** :cry:
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message: Commit message:
``` ```
@@ -1,14 +1,9 @@
🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩 🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩
> :rocket: {{ env.NYM_PROJECT_NAME }} ➡️➡️➡️➡️➡️ **View storybook:** https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}/ > :rocket: {{ env.NYM_PROJECT_NAME }} ➡️➡️➡️➡️➡️ **View storybook:** https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}/
>
> ✅ **SUCCESS** > ✅ **SUCCESS**
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}: Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}:
``` ```
@@ -1,14 +1,9 @@
🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> 🔴 **FAILURE** :cry: > 🔴 **FAILURE** :cry:
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message: Commit message:
``` ```
@@ -1,18 +1,13 @@
🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩 🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> ✅ **SUCCESS** > ✅ **SUCCESS**
>
> ➡️➡️➡️➡️➡️ **View output:** > ➡️➡️➡️➡️➡️ **View output:**
>
> `storybook`: https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }} > `storybook`: https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}: Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}:
``` ```
+3 -3
View File
@@ -1,6 +1,6 @@
{ {
"name": "send-matrix-message", "name": "send-keybase-message",
"description": "Sends a notification message with the matrix sdk", "description": "Sends a notification message with the keybase package that fails when piped into the keybase CLI",
"version": "1.0.0", "version": "1.0.0",
"private": true, "private": true,
"scripts": { "scripts": {
@@ -10,6 +10,7 @@
"dependencies": { "dependencies": {
"dotenv": "^16.0.0", "dotenv": "^16.0.0",
"handlebars": "^4.7.7", "handlebars": "^4.7.7",
"keybase-bot": "^3.6.1",
"matrix-js-sdk": "^9.3.0", "matrix-js-sdk": "^9.3.0",
"node-localstorage": "^2.1.6", "node-localstorage": "^2.1.6",
"octokit": "^1.7.1", "octokit": "^1.7.1",
@@ -17,7 +18,6 @@
"remark-emoji": "^2.2.0", "remark-emoji": "^2.2.0",
"remark-html": "^13.0.2", "remark-html": "^13.0.2",
"remark-parse": "^9.0.0", "remark-parse": "^9.0.0",
"showdown": "^2.1.0",
"to-vfile": "^6.1.0", "to-vfile": "^6.1.0",
"unified": "^9.2.2" "unified": "^9.2.2"
}, },
@@ -1,14 +1,9 @@
🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥 🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥🟥
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> 🔴 **FAILURE** :cry: > 🔴 **FAILURE** :cry:
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message: Commit message:
``` ```
@@ -1,20 +1,14 @@
🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩 🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩🟩
> :rocket: {{ env.NYM_PROJECT_NAME }} > :rocket: {{ env.NYM_PROJECT_NAME }}
>
> ✅ **SUCCESS** > ✅ **SUCCESS**
>
> ➡️➡️➡️➡️➡️ **View output:** > ➡️➡️➡️➡️➡️ **View output:**
>
> `storybook`: https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }} > `storybook`: https://{{ env.NYM_CI_WWW_LOCATION }}.{{ env.NYM_CI_WWW_BASE }}
>
> `example`: https://{{ env.NYM_CI_WWW_LOCATION }}-example.{{ env.NYM_CI_WWW_BASE }} > `example`: https://{{ env.NYM_CI_WWW_LOCATION }}-example.{{ env.NYM_CI_WWW_BASE }}
>
> `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }} > `branch` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/tree/{{ env.GIT_BRANCH_NAME }}
>
> `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }} > `commit` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/commit/{{ env.GITHUB_SHA }}
>
> `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }} > `build ` {{ env.GITHUB_SERVER_URL }}/{{ env.GITHUB_REPOSITORY }}/actions/runs/{{ env.GITHUB_RUN_ID }}
>
Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}: Commit message by `{{ env.GITHUB_ACTOR }}` at {{ timestamp }}:
``` ```
-46
View File
@@ -1,46 +0,0 @@
name: tag-and-release
on:
workflow_dispatch:
inputs:
nym_binaries_version:
description: 'Version of the nym-binaries tag'
required: false
type: string
nym_wallet_version:
description: 'Version of the nym-wallet tag'
required: false
type: string
nym_connect_version:
description: 'Version of the nym-connect tag'
required: false
type: string
jobs:
tag-components:
uses: nymtech/reusable-workflows/.github/workflows/tag-components.yml@master
with:
nym_binaries_version: ${{ input.nym_binaries_version }}
nym_wallet_version: ${{ input.nym_wallet_version }}
nym_connect_version: ${{ input.nym_connect_version }}
create-nym-binaries-release:
if: ${{ input.nym_binaries_version }}
uses: nymtech/reusable-workflows/.github/workflows/create-binaries-release.yml@master
with:
version: ${{ input.nym_binaries_version }}
needs: ["tag-components"]
create-nym-wallet-release:
if: ${{ input.nym_wallet_version }}
uses: nymtech/reusable-workflows/.github/workflows/create-wallet-release.yml@master
with:
version: ${{ input.nym_wallet_version }}
needs: ["tag-components"]
create-nym-connect-release:
if: ${{ input.nym_connect_version }}
uses: nymtech/reusable-workflows/.github/workflows/create-connect-release.yml@master
with:
version: ${{ input.nym_connect_version }}
needs: ["tag-components"]
-64
View File
@@ -1,64 +0,0 @@
name: CI for linting Typescript
on:
push:
paths:
- 'ts-packages/**'
- 'sdk/typescript/**'
- 'nym-connect/desktop/src/**'
- 'nym-connect/desktop/package.json'
- 'nym-connect/mobile/src/**'
- 'nym-connect/mobile/package.json'
- 'nym-wallet/src/**'
- 'nym-wallet/package.json'
pull_request:
paths:
- 'ts-packages/**'
- 'sdk/typescript/**'
- 'nym-connect/desktop/src/**'
- 'nym-connect/desktop/package.json'
- 'nym-connect/mobile/src/**'
- 'nym-connect/mobile/package.json'
- 'nym-wallet/src/**'
- 'nym-wallet/package.json'
jobs:
build:
runs-on: custom-runner-linux
steps:
- uses: actions/checkout@v2
- name: Install rsync
run: sudo apt-get install rsync
continue-on-error: true
- uses: rlespinasse/github-slug-action@v3.x
- uses: actions/setup-node@v3
with:
node-version: 16
- name: Setup yarn
run: npm install -g yarn
- name: Install
run: yarn
- name: Build packages
run: yarn build
- name: Lint
run: yarn lint && yarn tsc
- name: Matrix - Node Install
run: npm install
working-directory: .github/workflows/support-files
- name: Matrix - Send Notification
env:
NYM_NOTIFICATION_KIND: ts-packages
NYM_PROJECT_NAME: "ts-packages"
NYM_CI_WWW_BASE: "${{ secrets.NYM_CI_WWW_BASE }}"
NYM_CI_WWW_LOCATION: "ts-${{ env.GITHUB_REF_SLUG }}"
GIT_COMMIT_MESSAGE: "${{ github.event.head_commit.message }}"
GIT_BRANCH: "${GITHUB_REF##*/}"
IS_SUCCESS: "${{ job.status == 'success' }}"
MATRIX_SERVER: "${{ secrets.MATRIX_SERVER }}"
MATRIX_ROOM: "${{ secrets.MATRIX_ROOM }}"
MATRIX_USER_ID: "${{ secrets.MATRIX_USER_ID }}"
MATRIX_TOKEN: "${{ secrets.MATRIX_TOKEN }}"
MATRIX_DEVICE_ID: "${{ secrets.MATRIX_DEVICE_ID }}"
uses: docker://keybaseio/client:stable-node
with:
args: .github/workflows/support-files/notifications/entry_point.sh
@@ -1,95 +0,0 @@
name: update-versions-and-changelog
on:
workflow_dispatch:
inputs:
release_version:
description: "Release version, usually the milestone title"
required: true
type: string
milestone_id:
description: "Milestone ID, check the URL when you're on the specific milestone page"
required: true
type: string
env:
CI_BOT_AUTHOR: "Nym bot"
CI_BOT_EMAIL: "nym-bot@users.noreply.github.com"
jobs:
update-versions:
runs-on: ubuntu-22.04
steps:
- name: checkout-source
uses: actions/checkout@v3
with:
ref: "release/${{ inputs.release_version }}"
path: "nym"
- name: checkout-ci-tools-repo
uses: actions/checkout@v3
with:
repository: "nymtech/ci-tools"
ref: "master"
path: "ci-tools"
token: "${{ secrets.ACCESS_TOKEN_PRIVATE_REPOS }}"
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: install-version-bumper
run: "cargo install --path ."
working-directory: "ci-tools/version-bumper"
- name: run-version-bumper
run: "version-bumper bump binaries --nym-repo-directory nym"
- name: push-changes-to-branch
run: |
git config --global user.name "${{ env.CI_BOT_AUTHOR }}"
git config --global user.email "${{ env.CI_BOT_EMAIL }}"
git checkout -b release/${{ inputs.release_version }}-preparation
git commit -am "chore: version bump in preparation for release"
git push -u origin release/${{ inputs.release_version }}-preparation
working-directory: "nym"
update-changelog:
runs-on: ubuntu-22.04
needs: [update-versions]
steps:
- name: checkout-source
uses: actions/checkout@v3
with:
ref: "release/${{ inputs.release_version }}"
path: "nym"
- name: checkout-ci-tools-repo
uses: actions/checkout@v3
with:
repository: "nymtech/ci-tools"
ref: "master"
path: "ci-tools"
token: "${{ secrets.ACCESS_TOKEN_PRIVATE_REPOS }}"
- name: Install Rust stable
uses: actions-rs/toolchain@v1
with:
toolchain: stable
- name: install-changelog-updater
run: "cargo install --path ."
working-directory: "ci-tools/changelog-updater"
- name: run-changelog-updater
run: "changelog-updater mix ${{ inputs.milestone_id }} release/${{ inputs.release_version }}"
- name: push-changes-to-branch
run: |
git config --global user.name "${{ env.CI_BOT_AUTHOR }}"
git config --global user.email "${{ env.CI_BOT_EMAIL }}"
git checkout release/${{ inputs.release_version }}-preparation
git commit -am "chore: update changelog preparation for release"
git push
working-directory: "nym"
+4 -11
View File
@@ -2,17 +2,11 @@ name: Nym Wallet (rust)
on: on:
push: push:
paths: paths-ignore:
- 'nym-wallet/**' - 'explorer/**'
- 'common/**'
- 'contracts/vesting/**'
- 'nym-api/nym-api-requests/**'
pull_request: pull_request:
paths: paths-ignore:
- 'nym-wallet/**' - 'explorer/**'
- 'common/**'
- 'contracts/vesting/**'
- 'nym-api/nym-api-requests/**'
jobs: jobs:
build: build:
@@ -22,7 +16,6 @@ jobs:
steps: steps:
- name: Install Dependencies (Linux) - name: Install Dependencies (Linux)
run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev squashfs-tools run: sudo apt-get update && sudo apt-get -y install libwebkit2gtk-4.0-dev build-essential curl wget libssl-dev libgtk-3-dev squashfs-tools
continue-on-error: true
- name: Check out repository code - name: Check out repository code
uses: actions/checkout@v2 uses: actions/checkout@v2
+12 -7
View File
@@ -2,13 +2,8 @@ name: Wasm Client
on: on:
pull_request: pull_request:
paths: paths-ignore:
- 'clients/webassembly/**' - 'explorer/**'
- 'clients/client-core/**'
- 'common/**'
- 'contracts/**'
- 'gateway/gateway-requests/**'
- 'nym-api/nym-api-requests/**'
jobs: jobs:
wasm: wasm:
@@ -29,6 +24,16 @@ jobs:
command: build command: build
args: --manifest-path clients/webassembly/Cargo.toml --target wasm32-unknown-unknown args: --manifest-path clients/webassembly/Cargo.toml --target wasm32-unknown-unknown
- uses: actions-rs/cargo@v1
with:
command: build
args: --manifest-path clients/webassembly/Cargo.toml --target wasm32-unknown-unknown --features=coconut
- uses: actions-rs/cargo@v1
with:
command: test
args: --manifest-path clients/webassembly/Cargo.toml
- uses: actions-rs/cargo@v1 - uses: actions-rs/cargo@v1
with: with:
command: fmt command: fmt
-1
View File
@@ -42,4 +42,3 @@ envs/qwerty.env
Cargo.lock Cargo.lock
nym-connect/Cargo.lock nym-connect/Cargo.lock
.parcel-cache .parcel-cache
**/.DS_Store
+2 -98
View File
@@ -4,122 +4,26 @@ Post 1.0.0 release, the changelog format is based on [Keep a Changelog](https://
## [Unreleased] ## [Unreleased]
## [v1.1.10] (2023-02-21)
- Verloc listener causing mixnode unexpected shutdown ([#3038])
- rust-sdk - update API following implementation experience with the network-requester ([#3001])
- Prevent coconut deposits in incompatible states ([#2991])
- Support unavailable signer within threshold ([#2987])
- Implement DKG re-sharing ([#2935])
- contracts: add nym prefix to mixnet and vesting contract packages ([#2855])
- Introduce common interface for all service providers to allow obtaining information such as whether they're online, what binary version they're running, etc. ([#2758])
- Add client functionality to nym-network-requester ([#1900])
- nym-api: uptime rework ([#3053])
- ci: update typescript-lint.yml ([#3035])
- contracts: add nym prefix to mixnet and vesting contract packages ([#2855])
[#3038]: https://github.com/nymtech/nym/issues/3038
[#3001]: https://github.com/nymtech/nym/issues/3001
[#2991]: https://github.com/nymtech/nym/issues/2991
[#2987]: https://github.com/nymtech/nym/issues/2987
[#2935]: https://github.com/nymtech/nym/issues/2935
[#2855]: https://github.com/nymtech/nym/pull/2855
[#2758]: https://github.com/nymtech/nym/issues/2758
[#1900]: https://github.com/nymtech/nym/issues/1900
[#3053]: https://github.com/nymtech/nym/pull/3053
[#3035]: https://github.com/nymtech/nym/pull/3035
[#2855]: https://github.com/nymtech/nym/pull/2855
## [v1.1.9] (2023-02-07)
### Added
- Remove Coconut feature flag ([#2793])
- Separate `nym-api` endpoints with values of "total-supply" and "circulating-supply" in `nym` ([#2964])
### Changed
- native-client: is now capable of listening for requests on sockets different than `127.0.0.1` ([#2912]). This can be specified via `--host` flag during `init` or `run`. Alternatively a custom `host` can be set in `config.toml` file under `socket` section.
- mixnode, gateway: fix unexpected shutdown on corrupted connection ([#2963])
[#2793]: https://github.com/nymtech/nym/issues/2793
[#2912]: https://github.com/nymtech/nym/issues/2912
[#2964]: https://github.com/nymtech/nym/issues/2964
[#2963]: https://github.com/nymtech/nym/issues/3017
## [v1.1.8] (2023-01-31)
### Added
- Rust SDK - Support SURBS (anonymous send + storage) ([#2754])
- dkg rerun from scratch and dkg-specific epochs ([#2810])
- Rename `'initial_supply'` field to `'total_supply'` in the circulating supply endpoint ([#2931])
- Circulating supply api endpoint (read the note inside before testing/deploying) ([#1902])
### Changed
- nym-api: an `--id` flag is now always explicitly required ([#2873])
[#2754]: https://github.com/nymtech/nym/issues/2754
[#2810]: https://github.com/nymtech/nym/issues/2810
[#2931]: https://github.com/nymtech/nym/issues/2931
[#1902]: https://github.com/nymtech/nym/issues/1902
[#2873]: https://github.com/nymtech/nym/issues/2873
## [v1.1.7] (2023-01-24)
### Added
- Gateways now shut down gracefully ([#2019]).
- Rust SDK - Initial version for nym-client ([#2669]).
- Introduce vesting contract query for addresses of all vesting accounts (required for the circulating supply calculation) ([#2778]).
- Add threshold value to the contract storage ([#1893])
### Changed
- Refactor vesting account storage (and in particular, ACCOUNTS saving) ([#2795]).
- Move from manual advancing DKG state to an automatic process ([#2670]).
### Fixed
- Gateways now shut down gracefully ([#2019]).
[#2019]: https://github.com/nymtech/nym/issues/2019
[#2669]: https://github.com/nymtech/nym/issues/2669
[#2795]: https://github.com/nymtech/nym/issues/2795
[#2778]: https://github.com/nymtech/nym/issues/2778
[#2670]: https://github.com/nymtech/nym/issues/2670
[#1893]: https://github.com/nymtech/nym/issues/1893
## [v1.1.6] (2023-01-17)
### Added ### Added
- nym-sdk: added initial version of a Rust client sdk - nym-sdk: added initial version of a Rust client sdk
- nym-api: added `/circulating-supply` endpoint ([#2814]) - nym-api: added `/circulating-supply` endpoint ([#2814])
- nym-api: add endpoint listing detailed gateway info by @octol in https://github.com/nymtech/nym/pull/2833
### Changed ### Changed
- streamline override_config functions -> there's a lot of duplicate if statements everywhere ([#2774])
- clean-up nym-api startup arguments/flags to use clap 3 and its macro-derived arguments ([#2772])
- renamed all references to validator_api to nym_api - renamed all references to validator_api to nym_api
- renamed all references to nymd to nyxd ([#2696]) - renamed all references to nymd to nyxd
- all-binaries: standarised argument names (note: old names should still be accepted) ([#2762] - all-binaries: standarised argument names (note: old names should still be accepted) ([#2762]
### Fixed ### Fixed
- nym-api: should now correctly use `rewarding.enabled` config flag ([#2753]) - nym-api: should now correctly use `rewarding.enabled` config flag ([#2753])
[#2696]: https://github.com/nymtech/nym/pull/2696
[#2753]: https://github.com/nymtech/nym/pull/2753 [#2753]: https://github.com/nymtech/nym/pull/2753
[#2762]: https://github.com/nymtech/nym/pull/2762 [#2762]: https://github.com/nymtech/nym/pull/2762
[#2814]: https://github.com/nymtech/nym/pull/2814 [#2814]: https://github.com/nymtech/nym/pull/2814
[#2772]: https://github.com/nymtech/nym/pull/2772
[#2774]: https://github.com/nymtech/nym/pull/2774
## [v1.1.5] (2023-01-10) ## [v1.1.5] (2022-01-10)
### Added ### Added
Generated
+1375 -1558
View File
File diff suppressed because it is too large Load Diff
+6 -29
View File
@@ -23,28 +23,28 @@ members = [
"clients/native/websocket-requests", "clients/native/websocket-requests",
"clients/socks5", "clients/socks5",
"common/bandwidth-claim-contract", "common/bandwidth-claim-contract",
"common/bin-common",
"common/client-libs/gateway-client", "common/client-libs/gateway-client",
"common/client-libs/mixnet-client", "common/client-libs/mixnet-client",
"common/client-libs/validator-client", "common/client-libs/validator-client",
"common/client-connections",
"common/coconut-interface", "common/coconut-interface",
"common/commands", "common/commands",
"common/config", "common/config",
"common/build-information",
"common/cosmwasm-smart-contracts/coconut-bandwidth-contract", "common/cosmwasm-smart-contracts/coconut-bandwidth-contract",
"common/cosmwasm-smart-contracts/coconut-dkg", "common/cosmwasm-smart-contracts/coconut-dkg",
"common/cosmwasm-smart-contracts/contracts-common", "common/cosmwasm-smart-contracts/contracts-common",
"common/cosmwasm-smart-contracts/group-contract",
"common/cosmwasm-smart-contracts/mixnet-contract", "common/cosmwasm-smart-contracts/mixnet-contract",
"common/cosmwasm-smart-contracts/multisig-contract", "common/cosmwasm-smart-contracts/multisig-contract",
"common/cosmwasm-smart-contracts/vesting-contract", "common/cosmwasm-smart-contracts/vesting-contract",
"common/mobile-storage",
"common/credential-storage", "common/credential-storage",
"common/credentials", "common/credentials",
"common/crypto", "common/crypto",
"common/dkg", "common/crypto/dkg",
"common/execute", "common/execute",
"common/inclusion-probability", "common/inclusion-probability",
"common/ledger", "common/ledger",
"common/logging",
"common/mixnode-common", "common/mixnode-common",
"common/network-defaults", "common/network-defaults",
"common/nonexhaustive-delayqueue", "common/nonexhaustive-delayqueue",
@@ -67,13 +67,13 @@ members = [
"common/topology", "common/topology",
"common/types", "common/types",
"common/wasm-utils", "common/wasm-utils",
"common/completions",
"explorer-api", "explorer-api",
"gateway", "gateway",
"gateway/gateway-requests", "gateway/gateway-requests",
"integrations/bity", "integrations/bity",
"mixnode", "mixnode",
"sdk/rust/nym-sdk", "sdk/rust/nym-sdk",
"service-providers/common",
"service-providers/network-requester", "service-providers/network-requester",
"service-providers/network-statistics", "service-providers/network-statistics",
"nym-api", "nym-api",
@@ -94,27 +94,4 @@ default-members = [
"explorer-api", "explorer-api",
] ]
exclude = ["explorer", "contracts", "clients/webassembly", "nym-wallet", "nym-connect/mobile/src-tauri", "nym-connect/desktop"] exclude = ["explorer", "contracts", "clients/webassembly", "nym-wallet", "nym-connect"]
[workspace.package]
authors = ["Nym Technologies SA"]
repository = "https://github.com/nymtech/nym"
homepage = "https://nymtech.net"
documentation = "https://nymtech.net"
edition = "2021"
license = "Apache-2.0"
[workspace.dependencies]
async-trait = "0.1.63"
cfg-if = "1.0.0"
dotenv = "0.15.0"
lazy_static = "1.4.0"
log = "0.4"
once_cell = "1.7.2"
rand = "0.8.5"
serde = "1.0.152"
serde_json = "1.0.91"
tap = "1.0.1"
thiserror = "1.0.38"
tokio = "1.24.1"
url = "2.2"
+24 -38
View File
@@ -2,12 +2,12 @@ test: clippy-all cargo-test wasm fmt
test-all: test cargo-test-expensive test-all: test cargo-test-expensive
no-clippy: build cargo-test wasm fmt no-clippy: build cargo-test wasm fmt
happy: fmt clippy-happy test happy: fmt clippy-happy test
clippy-all: clippy-main clippy-main-examples clippy-all-contracts clippy-all-wallet clippy-all-connect clippy-all-connect-mobile clippy-all-wasm-client clippy-all: clippy-main clippy-coconut clippy-all-contracts clippy-all-wallet clippy-all-connect clippy-all-wasm-client
clippy-happy: clippy-happy-main clippy-happy-contracts clippy-happy-wallet clippy-happy-connect clippy-happy-connect-mobile clippy-happy: clippy-happy-main clippy-happy-contracts clippy-happy-wallet clippy-happy-connect
cargo-test: test-main test-contracts test-wallet test-connect test-connect-mobile cargo-test: test-main test-contracts test-wallet test-connect test-coconut test-wasm-client
cargo-test-expensive: test-main-expensive test-contracts-expensive test-wallet-expensive test-connect-expensive cargo-test-expensive: test-main-expensive test-contracts-expensive test-wallet-expensive test-connect-expensive test-coconut-expensive
build: build-contracts build-wallet build-main build-main-examples build-connect build-connect-mobile build-wasm-client build: build-contracts build-wallet build-main build-connect build-wasm-client
fmt: fmt-main fmt-contracts fmt-wallet fmt-connect fmt-connect-mobile fmt-wasm-client fmt: fmt-main fmt-contracts fmt-wallet fmt-connect fmt-wasm-client
clippy-happy-main: clippy-happy-main:
cargo clippy cargo clippy
@@ -19,16 +19,13 @@ clippy-happy-wallet:
cargo clippy --manifest-path nym-wallet/Cargo.toml cargo clippy --manifest-path nym-wallet/Cargo.toml
clippy-happy-connect: clippy-happy-connect:
cargo clippy --manifest-path nym-connect/desktop/Cargo.toml cargo clippy --manifest-path nym-connect/Cargo.toml
clippy-happy-connect-mobile:
cargo clippy --manifest-path nym-connect/mobile/src-tauri/Cargo.toml
clippy-main: clippy-main:
cargo clippy --workspace -- -D warnings cargo clippy --workspace -- -D warnings
clippy-main-examples: clippy-coconut:
cargo clippy --workspace --examples -- -D warnings cargo clippy --workspace --features coconut -- -D warnings
clippy-wasm: clippy-wasm:
cargo clippy --manifest-path clients/webassembly/Cargo.toml --target wasm32-unknown-unknown --workspace -- -D warnings cargo clippy --manifest-path clients/webassembly/Cargo.toml --target wasm32-unknown-unknown --workspace -- -D warnings
@@ -41,10 +38,7 @@ clippy-all-wallet:
cargo clippy --workspace --manifest-path nym-wallet/Cargo.toml --all-features -- -D warnings cargo clippy --workspace --manifest-path nym-wallet/Cargo.toml --all-features -- -D warnings
clippy-all-connect: clippy-all-connect:
cargo clippy --workspace --manifest-path nym-connect/desktop/Cargo.toml --all-features -- -D warnings cargo clippy --workspace --manifest-path nym-connect/Cargo.toml --all-features -- -D warnings
clippy-all-connect-mobile:
cargo clippy --workspace --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --all-features -- -D warnings
clippy-all-wasm-client: clippy-all-wasm-client:
cargo clippy --workspace --manifest-path clients/webassembly/Cargo.toml --all-features --target wasm32-unknown-unknown -- -D warnings cargo clippy --workspace --manifest-path clients/webassembly/Cargo.toml --all-features --target wasm32-unknown-unknown -- -D warnings
@@ -52,9 +46,16 @@ clippy-all-wasm-client:
test-main: test-main:
cargo test --workspace cargo test --workspace
test-coconut:
cargo test --workspace --features coconut
test-main-expensive: test-main-expensive:
cargo test --workspace -- --ignored cargo test --workspace -- --ignored
test-coconut-expensive:
cargo test --workspace --features coconut -- --ignored
test-contracts: test-contracts:
cargo test --manifest-path contracts/Cargo.toml --all-features cargo test --manifest-path contracts/Cargo.toml --all-features
@@ -67,24 +68,18 @@ test-wallet:
test-wallet-expensive: test-wallet-expensive:
cargo test --manifest-path nym-wallet/Cargo.toml --all-features -- --ignored cargo test --manifest-path nym-wallet/Cargo.toml --all-features -- --ignored
test-wasm-client:
cargo test --workspace --manifest-path clients/webassembly/Cargo.toml --all-features
test-connect: test-connect:
cargo test --manifest-path nym-connect/desktop/Cargo.toml --all-features cargo test --manifest-path nym-connect/Cargo.toml --all-features
test-connect-expensive: test-connect-expensive:
cargo test --manifest-path nym-connect/desktop/Cargo.toml --all-features -- --ignored cargo test --manifest-path nym-connect/Cargo.toml --all-features -- --ignored
test-connect-mobile:
cargo test --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --all-features
test-connect-mobile-expensive:
cargo test --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --all-features -- --ignored
build-main: build-main:
cargo build --workspace cargo build --workspace
build-main-examples:
cargo build --workspace --examples
build-contracts: build-contracts:
cargo build --manifest-path contracts/Cargo.toml --workspace cargo build --manifest-path contracts/Cargo.toml --workspace
@@ -92,10 +87,7 @@ build-wallet:
cargo build --manifest-path nym-wallet/Cargo.toml --workspace cargo build --manifest-path nym-wallet/Cargo.toml --workspace
build-connect: build-connect:
cargo build --manifest-path nym-connect/desktop/Cargo.toml --workspace cargo build --manifest-path nym-connect/Cargo.toml --workspace
build-connect-mobile:
cargo build --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --workspace
build-explorer-api: build-explorer-api:
cargo build --manifest-path explorer-api/Cargo.toml --workspace cargo build --manifest-path explorer-api/Cargo.toml --workspace
@@ -116,10 +108,7 @@ fmt-wallet:
cargo fmt --manifest-path nym-wallet/Cargo.toml --all cargo fmt --manifest-path nym-wallet/Cargo.toml --all
fmt-connect: fmt-connect:
cargo fmt --manifest-path nym-connect/desktop/Cargo.toml --all cargo fmt --manifest-path nym-connect/Cargo.toml --all
fmt-connect-mobile:
cargo fmt --manifest-path nym-connect/mobile/src-tauri/Cargo.toml --all
fmt-wasm-client: fmt-wasm-client:
cargo fmt --manifest-path clients/webassembly/Cargo.toml --all cargo fmt --manifest-path clients/webassembly/Cargo.toml --all
@@ -133,6 +122,3 @@ mixnet-opt: wasm
generate-typescript: generate-typescript:
cd tools/ts-rs-cli && cargo run && cd ../.. cd tools/ts-rs-cli && cargo run && cd ../..
yarn types:lint:fix yarn types:lint:fix
run-api-tests:
cd nym-api/tests/functional_test && yarn test:qa
+11 -9
View File
@@ -1,6 +1,6 @@
[package] [package]
name = "client-core" name = "client-core"
version = "1.1.10" version = "1.1.5"
authors = ["Dave Hrycyszyn <futurechimp@users.noreply.github.com>"] authors = ["Dave Hrycyszyn <futurechimp@users.noreply.github.com>"]
edition = "2021" edition = "2021"
rust-version = "1.66" rust-version = "1.66"
@@ -13,7 +13,7 @@ dirs = "4.0"
dashmap = "5.4.0" dashmap = "5.4.0"
futures = "0.3" futures = "0.3"
humantime-serde = "1.0" humantime-serde = "1.0"
log = { workspace = true } log = "0.4"
rand = { version = "0.7.3", features = ["wasm-bindgen"] } rand = { version = "0.7.3", features = ["wasm-bindgen"] }
serde = { version = "1.0", features = ["derive"] } serde = { version = "1.0", features = ["derive"] }
serde_json = "1.0.89" serde_json = "1.0.89"
@@ -24,17 +24,18 @@ tokio = { version = "1.24.1", features = ["macros"]}
time = "0.3.17" time = "0.3.17"
# internal # internal
nym-config = { path = "../../common/config" } config = { path = "../../common/config" }
nym-crypto = { path = "../../common/crypto" } client-connections = { path = "../../common/client-connections" }
crypto = { path = "../../common/crypto" }
gateway-client = { path = "../../common/client-libs/gateway-client" } gateway-client = { path = "../../common/client-libs/gateway-client" }
#gateway-client = { path = "../../common/client-libs/gateway-client", default-features = false, features = ["wasm", "coconut"] } #gateway-client = { path = "../../common/client-libs/gateway-client", default-features = false, features = ["wasm", "coconut"] }
gateway-requests = { path = "../../gateway/gateway-requests" } gateway-requests = { path = "../../gateway/gateway-requests" }
nym-nonexhaustive-delayqueue = { path = "../../common/nonexhaustive-delayqueue" } nonexhaustive-delayqueue = { path = "../../common/nonexhaustive-delayqueue" }
nym-sphinx = { path = "../../common/nymsphinx" } nymsphinx = { path = "../../common/nymsphinx" }
nym-pemstore = { path = "../../common/pemstore" } pemstore = { path = "../../common/pemstore" }
nym-topology = { path = "../../common/topology" } topology = { path = "../../common/topology" }
validator-client = { path = "../../common/client-libs/validator-client", default-features = false } validator-client = { path = "../../common/client-libs/validator-client", default-features = false }
nym-task = { path = "../../common/task" } task = { path = "../../common/task" }
[target."cfg(not(target_arch = \"wasm32\"))".dependencies.tokio-stream] [target."cfg(not(target_arch = \"wasm32\"))".dependencies.tokio-stream]
version = "0.1.11" version = "0.1.11"
@@ -81,4 +82,5 @@ sqlx = { version = "0.6.2", features = ["runtime-tokio-rustls", "sqlite", "macro
default = [] default = []
fs-surb-storage = ["sqlx"] fs-surb-storage = ["sqlx"]
wasm = ["gateway-client/wasm"] wasm = ["gateway-client/wasm"]
coconut = ["gateway-client/coconut", "gateway-requests/coconut"]
@@ -1,11 +0,0 @@
// Copyright 2023 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0
//
use crate::{client::replies::reply_storage, config::DebugConfig};
pub fn setup_empty_reply_surb_backend(debug_config: &DebugConfig) -> reply_storage::Empty {
reply_storage::Empty {
min_surb_threshold: debug_config.minimum_reply_surb_storage_threshold,
max_surb_threshold: debug_config.maximum_reply_surb_storage_threshold,
}
}
@@ -21,52 +21,35 @@ use crate::client::topology_control::{
use crate::config::{Config, DebugConfig, GatewayEndpointConfig}; use crate::config::{Config, DebugConfig, GatewayEndpointConfig};
use crate::error::ClientCoreError; use crate::error::ClientCoreError;
use crate::spawn_future; use crate::spawn_future;
use client_connections::{ConnectionCommandReceiver, ConnectionCommandSender, LaneQueueLengths};
use crypto::asymmetric::{encryption, identity};
use futures::channel::mpsc; use futures::channel::mpsc;
use gateway_client::bandwidth::BandwidthController; use gateway_client::bandwidth::BandwidthController;
#[cfg(target_arch = "wasm32")]
use gateway_client::wasm_mockups::CosmWasmClient;
use gateway_client::{ use gateway_client::{
AcknowledgementReceiver, AcknowledgementSender, GatewayClient, MixnetMessageReceiver, AcknowledgementReceiver, AcknowledgementSender, GatewayClient, MixnetMessageReceiver,
MixnetMessageSender, MixnetMessageSender,
}; };
use log::{debug, info}; use log::{debug, info};
use nym_crypto::asymmetric::{encryption, identity}; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::acknowledgements::AckKey; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::nodes::NodeIdentity;
use nym_sphinx::addressing::nodes::NodeIdentity; use nymsphinx::receiver::ReconstructedMessage;
use nym_sphinx::receiver::ReconstructedMessage;
use nym_task::connections::{ConnectionCommandReceiver, ConnectionCommandSender, LaneQueueLengths};
use nym_task::{TaskClient, TaskManager};
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
use tap::TapFallible; use tap::TapFallible;
use task::{TaskClient, TaskManager};
use url::Url; use url::Url;
#[cfg(not(target_arch = "wasm32"))]
use validator_client::nyxd::CosmWasmClient;
use super::received_buffer::ReceivedBufferMessage; use super::received_buffer::ReceivedBufferMessage;
#[cfg(all(not(target_arch = "wasm32"), feature = "fs-surb-storage"))] #[cfg(all(not(target_arch = "wasm32"), feature = "fs-surb-storage"))]
pub mod non_wasm_helpers; pub mod non_wasm_helpers;
pub mod helpers;
#[derive(Clone)]
pub struct ClientInput { pub struct ClientInput {
pub connection_command_sender: ConnectionCommandSender, pub connection_command_sender: ConnectionCommandSender,
pub input_sender: InputMessageSender, pub input_sender: InputMessageSender,
} }
impl ClientInput {
pub async fn send(
&self,
message: InputMessage,
) -> Result<(), tokio::sync::mpsc::error::SendError<InputMessage>> {
self.input_sender.send(message).await
}
}
#[derive(Clone)]
pub struct ClientOutput { pub struct ClientOutput {
pub received_buffer_request_sender: ReceivedBufferRequestSender, pub received_buffer_request_sender: ReceivedBufferRequestSender,
} }
@@ -146,7 +129,7 @@ impl From<bool> for CredentialsToggle {
} }
} }
pub struct BaseClientBuilder<'a, B, C: Clone> { pub struct BaseClientBuilder<'a, B> {
// due to wasm limitations I had to split it like this : ( // due to wasm limitations I had to split it like this : (
gateway_config: &'a GatewayEndpointConfig, gateway_config: &'a GatewayEndpointConfig,
debug_config: &'a DebugConfig, debug_config: &'a DebugConfig,
@@ -154,21 +137,20 @@ pub struct BaseClientBuilder<'a, B, C: Clone> {
nym_api_endpoints: Vec<Url>, nym_api_endpoints: Vec<Url>,
reply_storage_backend: B, reply_storage_backend: B,
bandwidth_controller: Option<BandwidthController<C>>, bandwidth_controller: Option<BandwidthController>,
key_manager: KeyManager, key_manager: KeyManager,
} }
impl<'a, B, C> BaseClientBuilder<'a, B, C> impl<'a, B> BaseClientBuilder<'a, B>
where where
B: ReplyStorageBackend + Send + Sync + 'static, B: ReplyStorageBackend + Send + Sync + 'static,
C: CosmWasmClient + Sync + Send + Clone + 'static,
{ {
pub fn new_from_base_config<T>( pub fn new_from_base_config<T>(
base_config: &'a Config<T>, base_config: &'a Config<T>,
key_manager: KeyManager, key_manager: KeyManager,
bandwidth_controller: Option<BandwidthController<C>>, bandwidth_controller: Option<BandwidthController>,
reply_storage_backend: B, reply_storage_backend: B,
) -> BaseClientBuilder<'a, B, C> { ) -> BaseClientBuilder<'a, B> {
BaseClientBuilder { BaseClientBuilder {
gateway_config: base_config.get_gateway_endpoint_config(), gateway_config: base_config.get_gateway_endpoint_config(),
debug_config: base_config.get_debug_config(), debug_config: base_config.get_debug_config(),
@@ -184,11 +166,11 @@ where
gateway_config: &'a GatewayEndpointConfig, gateway_config: &'a GatewayEndpointConfig,
debug_config: &'a DebugConfig, debug_config: &'a DebugConfig,
key_manager: KeyManager, key_manager: KeyManager,
bandwidth_controller: Option<BandwidthController<C>>, bandwidth_controller: Option<BandwidthController>,
reply_storage_backend: B, reply_storage_backend: B,
credentials_toggle: CredentialsToggle, credentials_toggle: CredentialsToggle,
nym_api_endpoints: Vec<Url>, nym_api_endpoints: Vec<Url>,
) -> BaseClientBuilder<'a, B, C> { ) -> BaseClientBuilder<'a, B> {
BaseClientBuilder { BaseClientBuilder {
gateway_config, gateway_config,
debug_config, debug_config,
@@ -297,11 +279,15 @@ where
mixnet_message_sender: MixnetMessageSender, mixnet_message_sender: MixnetMessageSender,
ack_sender: AcknowledgementSender, ack_sender: AcknowledgementSender,
shutdown: TaskClient, shutdown: TaskClient,
) -> Result<GatewayClient<C>, ClientCoreError> { ) -> Result<GatewayClient, ClientCoreError> {
let gateway_id = self.gateway_config.gateway_id.clone(); let gateway_id = self.gateway_config.gateway_id.clone();
if gateway_id.is_empty() { if gateway_id.is_empty() {
return Err(ClientCoreError::GatewayIdUnknown); return Err(ClientCoreError::GatewayIdUnknown);
} }
let gateway_owner = self.gateway_config.gateway_owner.clone();
if gateway_owner.is_empty() {
return Err(ClientCoreError::GatewayOwnerUnknown);
}
let gateway_address = self.gateway_config.gateway_listener.clone(); let gateway_address = self.gateway_config.gateway_listener.clone();
if gateway_address.is_empty() { if gateway_address.is_empty() {
return Err(ClientCoreError::GatwayAddressUnknown); return Err(ClientCoreError::GatwayAddressUnknown);
@@ -314,7 +300,6 @@ where
let shared_key = if self.key_manager.is_gateway_key_set() { let shared_key = if self.key_manager.is_gateway_key_set() {
Some(self.key_manager.gateway_shared_key()) Some(self.key_manager.gateway_shared_key())
} else { } else {
log::info!("Gateway key not set! Will proceed anyway.");
None None
}; };
@@ -322,6 +307,7 @@ where
gateway_address, gateway_address,
self.key_manager.identity_keypair(), self.key_manager.identity_keypair(),
gateway_identity, gateway_identity,
gateway_owner,
shared_key, shared_key,
mixnet_message_sender, mixnet_message_sender,
ack_sender, ack_sender,
@@ -379,7 +365,7 @@ where
// over it. Perhaps GatewayClient needs to be thread-shareable or have some channel for // over it. Perhaps GatewayClient needs to be thread-shareable or have some channel for
// requests? // requests?
fn start_mix_traffic_controller( fn start_mix_traffic_controller(
gateway_client: GatewayClient<C>, gateway_client: GatewayClient,
shutdown: TaskClient, shutdown: TaskClient,
) -> BatchMixMessageSender { ) -> BatchMixMessageSender {
info!("Starting mix traffic controller..."); info!("Starting mix traffic controller...");
@@ -395,32 +381,22 @@ where
where where
<B as ReplyStorageBackend>::StorageError: Sync + Send, <B as ReplyStorageBackend>::StorageError: Sync + Send,
{ {
if backend.is_active() { let persistent_storage = PersistentReplyStorage::new(backend);
log::trace!("Setup persistent reply storage"); let mem_store = persistent_storage
let persistent_storage = PersistentReplyStorage::new(backend); .load_state_from_backend()
let mem_store = persistent_storage .await
.load_state_from_backend() .map_err(|err| ClientCoreError::SurbStorageError {
source: Box::new(err),
})?;
let store_clone = mem_store.clone();
spawn_future(async move {
persistent_storage
.flush_on_shutdown(store_clone, shutdown)
.await .await
.map_err(|err| ClientCoreError::SurbStorageError { });
source: Box::new(err),
})?;
let store_clone = mem_store.clone(); Ok(mem_store)
spawn_future(async move {
persistent_storage
.flush_on_shutdown(store_clone, shutdown)
.await
});
Ok(mem_store)
} else {
log::trace!("Setup inactive reply storage");
Ok(backend
.get_inactive_storage()
.map_err(|err| ClientCoreError::SurbStorageError {
source: Box::new(err),
})?)
}
} }
pub async fn start_base(mut self) -> Result<BaseClient, ClientCoreError> pub async fn start_base(mut self) -> Result<BaseClient, ClientCoreError>
@@ -2,7 +2,7 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::client::replies::reply_storage::{ use crate::client::replies::reply_storage::{
fs_backend, CombinedReplyStorage, ReplyStorageBackend, self, fs_backend, CombinedReplyStorage, ReplyStorageBackend,
}; };
use crate::config::DebugConfig; use crate::config::DebugConfig;
use crate::error::ClientCoreError; use crate::error::ClientCoreError;
@@ -43,14 +43,6 @@ async fn setup_fresh_backend<P: AsRef<Path>>(
Ok(storage_backend) Ok(storage_backend)
} }
fn setup_inactive_backend(debug_config: &DebugConfig) -> fs_backend::Backend {
info!("creating inactive surb database");
fs_backend::Backend::new_inactive(
debug_config.minimum_reply_surb_storage_threshold,
debug_config.maximum_reply_surb_storage_threshold,
)
}
fn archive_corrupted_database<P: AsRef<Path>>(db_path: P) -> io::Result<()> { fn archive_corrupted_database<P: AsRef<Path>>(db_path: P) -> io::Result<()> {
let db_path = db_path.as_ref(); let db_path = db_path.as_ref();
debug_assert!(db_path.exists()); debug_assert!(db_path.exists());
@@ -73,28 +65,30 @@ fn archive_corrupted_database<P: AsRef<Path>>(db_path: P) -> io::Result<()> {
} }
pub async fn setup_fs_reply_surb_backend<P: AsRef<Path>>( pub async fn setup_fs_reply_surb_backend<P: AsRef<Path>>(
db_path: Option<P>, db_path: P,
debug_config: &DebugConfig, debug_config: &DebugConfig,
) -> Result<fs_backend::Backend, ClientCoreError> { ) -> Result<fs_backend::Backend, ClientCoreError> {
if let Some(db_path) = db_path { // if the database file doesnt exist, initialise fresh storage, otherwise attempt to load the existing one
// if the database file doesnt exist, initialise fresh storage, otherwise attempt to load let db_path = db_path.as_ref();
// the existing one if db_path.exists() {
let db_path = db_path.as_ref(); info!("loading existing surb database");
if db_path.exists() { match fs_backend::Backend::try_load(db_path).await {
info!("loading existing surb database"); Ok(backend) => Ok(backend),
match fs_backend::Backend::try_load(db_path).await { Err(err) => {
Ok(backend) => Ok(backend), error!("failed to setup persistent storage backend for our reply needs: {err}. We're going to create a fresh database instead. This behaviour might change in the future");
Err(err) => {
error!("failed to setup persistent storage backend for our reply needs: {err}. We're going to create a fresh database instead. This behaviour might change in the future");
archive_corrupted_database(db_path)?; archive_corrupted_database(db_path)?;
setup_fresh_backend(db_path, debug_config).await setup_fresh_backend(db_path, debug_config).await
}
} }
} else {
setup_fresh_backend(db_path, debug_config).await
} }
} else { } else {
Ok(setup_inactive_backend(debug_config)) setup_fresh_backend(db_path, debug_config).await
}
}
pub fn setup_empty_reply_surb_backend(debug_config: &DebugConfig) -> reply_storage::Empty {
reply_storage::Empty {
min_surb_threshold: debug_config.minimum_reply_surb_storage_threshold,
max_surb_threshold: debug_config.maximum_reply_surb_storage_threshold,
} }
} }
@@ -7,11 +7,11 @@ use crate::spawn_future;
use futures::task::{Context, Poll}; use futures::task::{Context, Poll};
use futures::{Future, Stream, StreamExt}; use futures::{Future, Stream, StreamExt};
use log::*; use log::*;
use nym_sphinx::acknowledgements::AckKey; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::cover::generate_loop_cover_packet; use nymsphinx::cover::generate_loop_cover_packet;
use nym_sphinx::params::PacketSize; use nymsphinx::params::PacketSize;
use nym_sphinx::utils::sample_poisson_duration; use nymsphinx::utils::sample_poisson_duration;
use rand::{rngs::OsRng, CryptoRng, Rng}; use rand::{rngs::OsRng, CryptoRng, Rng};
use std::pin::Pin; use std::pin::Pin;
use std::sync::Arc; use std::sync::Arc;
@@ -192,7 +192,7 @@ impl LoopCoverTrafficStream<OsRng> {
// However it's still useful to alert the user that the gateway or the link to // However it's still useful to alert the user that the gateway or the link to
// the gateway can't keep up. Either due to insufficient bandwidth on the // the gateway can't keep up. Either due to insufficient bandwidth on the
// client side, or that the gateway is overloaded. // client side, or that the gateway is overloaded.
log::warn!("Failed to send sphinx packet - gateway or connection to gateway can't keep up"); log::warn!("Failed to send sphinx packet - gateway or connection to gatway can't keep up");
} }
TrySendError::Closed(_) => { TrySendError::Closed(_) => {
log::warn!("Failed to send cover message - channel closed"); log::warn!("Failed to send cover message - channel closed");
@@ -213,7 +213,7 @@ impl LoopCoverTrafficStream<OsRng> {
tokio::task::yield_now().await; tokio::task::yield_now().await;
} }
pub fn start_with_shutdown(mut self, mut shutdown: nym_task::TaskClient) { pub fn start_with_shutdown(mut self, mut shutdown: task::TaskClient) {
// we should set initial delay only when we actually start the stream // we should set initial delay only when we actually start the stream
let sampled = let sampled =
sample_poisson_duration(&mut self.rng, self.average_cover_message_sending_delay); sample_poisson_duration(&mut self.rng, self.average_cover_message_sending_delay);
@@ -1,6 +1,6 @@
use nym_sphinx::addressing::clients::Recipient; use client_connections::TransmissionLane;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::addressing::clients::Recipient;
use nym_task::connections::TransmissionLane; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
pub type InputMessageSender = tokio::sync::mpsc::Sender<InputMessage>; pub type InputMessageSender = tokio::sync::mpsc::Sender<InputMessage>;
pub type InputMessageReceiver = tokio::sync::mpsc::Receiver<InputMessage>; pub type InputMessageReceiver = tokio::sync::mpsc::Receiver<InputMessage>;
@@ -77,12 +77,4 @@ impl InputMessage {
lane, lane,
} }
} }
pub fn lane(&self) -> &TransmissionLane {
match self {
InputMessage::Regular { lane, .. }
| InputMessage::Anonymous { lane, .. }
| InputMessage::Reply { lane, .. } => lane,
}
}
} }
+14 -14
View File
@@ -2,10 +2,10 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::config::persistence::key_pathfinder::ClientKeyPathfinder; use crate::config::persistence::key_pathfinder::ClientKeyPathfinder;
use crypto::asymmetric::{encryption, identity};
use gateway_requests::registration::handshake::SharedKeys; use gateway_requests::registration::handshake::SharedKeys;
use log::*; use log::*;
use nym_crypto::asymmetric::{encryption, identity}; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::acknowledgements::AckKey;
use rand::{CryptoRng, RngCore}; use rand::{CryptoRng, RngCore};
use std::io; use std::io;
use std::sync::Arc; use std::sync::Arc;
@@ -72,17 +72,17 @@ impl KeyManager {
/// Loads previously stored client keys from the disk. /// Loads previously stored client keys from the disk.
fn load_client_keys(client_pathfinder: &ClientKeyPathfinder) -> io::Result<Self> { fn load_client_keys(client_pathfinder: &ClientKeyPathfinder) -> io::Result<Self> {
let identity_keypair: identity::KeyPair = let identity_keypair: identity::KeyPair =
nym_pemstore::load_keypair(&nym_pemstore::KeyPairPath::new( pemstore::load_keypair(&pemstore::KeyPairPath::new(
client_pathfinder.private_identity_key().to_owned(), client_pathfinder.private_identity_key().to_owned(),
client_pathfinder.public_identity_key().to_owned(), client_pathfinder.public_identity_key().to_owned(),
))?; ))?;
let encryption_keypair: encryption::KeyPair = let encryption_keypair: encryption::KeyPair =
nym_pemstore::load_keypair(&nym_pemstore::KeyPairPath::new( pemstore::load_keypair(&pemstore::KeyPairPath::new(
client_pathfinder.private_encryption_key().to_owned(), client_pathfinder.private_encryption_key().to_owned(),
client_pathfinder.public_encryption_key().to_owned(), client_pathfinder.public_encryption_key().to_owned(),
))?; ))?;
let ack_key: AckKey = nym_pemstore::load_key(client_pathfinder.ack_key())?; let ack_key: AckKey = pemstore::load_key(client_pathfinder.ack_key())?;
Ok(KeyManager { Ok(KeyManager {
identity_keypair: Arc::new(identity_keypair), identity_keypair: Arc::new(identity_keypair),
@@ -98,7 +98,7 @@ impl KeyManager {
let mut key_manager = Self::load_client_keys(client_pathfinder)?; let mut key_manager = Self::load_client_keys(client_pathfinder)?;
let gateway_shared_key: SharedKeys = let gateway_shared_key: SharedKeys =
nym_pemstore::load_key(client_pathfinder.gateway_shared_key())?; pemstore::load_key(client_pathfinder.gateway_shared_key())?;
key_manager.gateway_shared_key = Some(Arc::new(gateway_shared_key)); key_manager.gateway_shared_key = Some(Arc::new(gateway_shared_key));
@@ -113,7 +113,7 @@ impl KeyManager {
let mut key_manager = Self::load_client_keys(client_pathfinder)?; let mut key_manager = Self::load_client_keys(client_pathfinder)?;
let gateway_shared_key: Result<SharedKeys, io::Error> = let gateway_shared_key: Result<SharedKeys, io::Error> =
nym_pemstore::load_key(client_pathfinder.gateway_shared_key()); pemstore::load_key(client_pathfinder.gateway_shared_key());
// It's ok if the gateway key was not found // It's ok if the gateway key was not found
let gateway_shared_key = match gateway_shared_key { let gateway_shared_key = match gateway_shared_key {
@@ -132,27 +132,27 @@ impl KeyManager {
// it is done so for the consistency sake so that you wouldn't require an rng instance // it is done so for the consistency sake so that you wouldn't require an rng instance
// during `load_keys` to generate the said key. // during `load_keys` to generate the said key.
pub fn store_keys(&self, client_pathfinder: &ClientKeyPathfinder) -> io::Result<()> { pub fn store_keys(&self, client_pathfinder: &ClientKeyPathfinder) -> io::Result<()> {
nym_pemstore::store_keypair( pemstore::store_keypair(
self.identity_keypair.as_ref(), self.identity_keypair.as_ref(),
&nym_pemstore::KeyPairPath::new( &pemstore::KeyPairPath::new(
client_pathfinder.private_identity_key().to_owned(), client_pathfinder.private_identity_key().to_owned(),
client_pathfinder.public_identity_key().to_owned(), client_pathfinder.public_identity_key().to_owned(),
), ),
)?; )?;
nym_pemstore::store_keypair( pemstore::store_keypair(
self.encryption_keypair.as_ref(), self.encryption_keypair.as_ref(),
&nym_pemstore::KeyPairPath::new( &pemstore::KeyPairPath::new(
client_pathfinder.private_encryption_key().to_owned(), client_pathfinder.private_encryption_key().to_owned(),
client_pathfinder.public_encryption_key().to_owned(), client_pathfinder.public_encryption_key().to_owned(),
), ),
)?; )?;
nym_pemstore::store_key(self.ack_key.as_ref(), client_pathfinder.ack_key())?; pemstore::store_key(self.ack_key.as_ref(), client_pathfinder.ack_key())?;
match self.gateway_shared_key.as_ref() { match self.gateway_shared_key.as_ref() {
None => debug!("No gateway shared key available to store!"), None => debug!("No gateway shared key available to store!"),
Some(gate_key) => { Some(gate_key) => {
nym_pemstore::store_key(gate_key.as_ref(), client_pathfinder.gateway_shared_key())? pemstore::store_key(gate_key.as_ref(), client_pathfinder.gateway_shared_key())?
} }
} }
@@ -168,7 +168,7 @@ impl KeyManager {
)) ))
} }
Some(gate_key) => { Some(gate_key) => {
nym_pemstore::store_key(gate_key.as_ref(), client_pathfinder.gateway_shared_key())? pemstore::store_key(gate_key.as_ref(), client_pathfinder.gateway_shared_key())?
} }
} }
+6 -15
View File
@@ -2,13 +2,9 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::spawn_future; use crate::spawn_future;
#[cfg(target_arch = "wasm32")]
use gateway_client::wasm_mockups::CosmWasmClient;
use gateway_client::GatewayClient; use gateway_client::GatewayClient;
use log::*; use log::*;
use nym_sphinx::forwarding::packet::MixPacket; use nymsphinx::forwarding::packet::MixPacket;
#[cfg(not(target_arch = "wasm32"))]
use validator_client::nyxd::CosmWasmClient;
pub type BatchMixMessageSender = tokio::sync::mpsc::Sender<Vec<MixPacket>>; pub type BatchMixMessageSender = tokio::sync::mpsc::Sender<Vec<MixPacket>>;
pub type BatchMixMessageReceiver = tokio::sync::mpsc::Receiver<Vec<MixPacket>>; pub type BatchMixMessageReceiver = tokio::sync::mpsc::Receiver<Vec<MixPacket>>;
@@ -17,10 +13,10 @@ pub type BatchMixMessageReceiver = tokio::sync::mpsc::Receiver<Vec<MixPacket>>;
pub const MIX_MESSAGE_RECEIVER_BUFFER_SIZE: usize = 32; pub const MIX_MESSAGE_RECEIVER_BUFFER_SIZE: usize = 32;
const MAX_FAILURE_COUNT: usize = 100; const MAX_FAILURE_COUNT: usize = 100;
pub struct MixTrafficController<C: Clone> { pub struct MixTrafficController {
// TODO: most likely to be replaced by some higher level construct as // TODO: most likely to be replaced by some higher level construct as
// later on gateway_client will need to be accessible by other entities // later on gateway_client will need to be accessible by other entities
gateway_client: GatewayClient<C>, gateway_client: GatewayClient,
mix_rx: BatchMixMessageReceiver, mix_rx: BatchMixMessageReceiver,
// TODO: this is temporary work-around. // TODO: this is temporary work-around.
@@ -28,13 +24,8 @@ pub struct MixTrafficController<C: Clone> {
consecutive_gateway_failure_count: usize, consecutive_gateway_failure_count: usize,
} }
impl<C> MixTrafficController<C> impl MixTrafficController {
where pub fn new(gateway_client: GatewayClient) -> (MixTrafficController, BatchMixMessageSender) {
C: CosmWasmClient + Sync + Send + Clone + 'static,
{
pub fn new(
gateway_client: GatewayClient<C>,
) -> (MixTrafficController<C>, BatchMixMessageSender) {
let (sphinx_message_sender, sphinx_message_receiver) = let (sphinx_message_sender, sphinx_message_receiver) =
tokio::sync::mpsc::channel(MIX_MESSAGE_RECEIVER_BUFFER_SIZE); tokio::sync::mpsc::channel(MIX_MESSAGE_RECEIVER_BUFFER_SIZE);
( (
@@ -76,7 +67,7 @@ where
} }
} }
pub fn start_with_shutdown(mut self, mut shutdown: nym_task::TaskClient) { pub fn start_with_shutdown(mut self, mut shutdown: task::TaskClient) {
spawn_future(async move { spawn_future(async move {
debug!("Started MixTrafficController with graceful shutdown support"); debug!("Started MixTrafficController with graceful shutdown support");
@@ -5,7 +5,7 @@ use super::action_controller::{AckActionSender, Action};
use futures::StreamExt; use futures::StreamExt;
use gateway_client::AcknowledgementReceiver; use gateway_client::AcknowledgementReceiver;
use log::*; use log::*;
use nym_sphinx::{ use nymsphinx::{
acknowledgements::{identifier::recover_identifier, AckKey}, acknowledgements::{identifier::recover_identifier, AckKey},
chunking::fragment::{FragmentIdentifier, COVER_FRAG_ID}, chunking::fragment::{FragmentIdentifier, COVER_FRAG_ID},
}; };
@@ -65,7 +65,7 @@ impl AcknowledgementListener {
} }
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started AcknowledgementListener with graceful shutdown support"); debug!("Started AcknowledgementListener with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
@@ -6,9 +6,9 @@ use crate::client::real_messages_control::acknowledgement_control::Retransmissio
use futures::channel::mpsc; use futures::channel::mpsc;
use futures::StreamExt; use futures::StreamExt;
use log::*; use log::*;
use nym_nonexhaustive_delayqueue::{Expired, NonExhaustiveDelayQueue, QueueKey}; use nonexhaustive_delayqueue::{Expired, NonExhaustiveDelayQueue, QueueKey};
use nym_sphinx::chunking::fragment::FragmentIdentifier; use nymsphinx::chunking::fragment::FragmentIdentifier;
use nym_sphinx::Delay as SphinxDelay; use nymsphinx::Delay as SphinxDelay;
use std::collections::HashMap; use std::collections::HashMap;
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
@@ -216,7 +216,7 @@ impl ActionController {
fn handle_expired_ack_timer( fn handle_expired_ack_timer(
&mut self, &mut self,
expired_ack: Expired<FragmentIdentifier>, expired_ack: Expired<FragmentIdentifier>,
task_client: &mut nym_task::TaskClient, task_client: &mut task::TaskClient,
) { ) {
// I'm honestly not sure how to handle it, because getting it means other things in our // I'm honestly not sure how to handle it, because getting it means other things in our
// system are already misbehaving. If we ever see this panic, then I guess we should worry // system are already misbehaving. If we ever see this panic, then I guess we should worry
@@ -260,7 +260,7 @@ impl ActionController {
} }
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started ActionController with graceful shutdown support"); debug!("Started ActionController with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
@@ -4,10 +4,10 @@
use crate::client::inbound_messages::{InputMessage, InputMessageReceiver}; use crate::client::inbound_messages::{InputMessage, InputMessageReceiver};
use crate::client::real_messages_control::message_handler::MessageHandler; use crate::client::real_messages_control::message_handler::MessageHandler;
use crate::client::replies::reply_controller::ReplyControllerSender; use crate::client::replies::reply_controller::ReplyControllerSender;
use client_connections::TransmissionLane;
use log::*; use log::*;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use nym_task::connections::TransmissionLane;
use rand::{CryptoRng, Rng}; use rand::{CryptoRng, Rng};
/// Module responsible for dealing with the received messages: splitting them, creating acknowledgements, /// Module responsible for dealing with the received messages: splitting them, creating acknowledgements,
@@ -109,7 +109,7 @@ where
}; };
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started InputMessageListener with graceful shutdown support"); debug!("Started InputMessageListener with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
@@ -15,9 +15,9 @@ use action_controller::AckActionReceiver;
use futures::channel::mpsc; use futures::channel::mpsc;
use gateway_client::AcknowledgementReceiver; use gateway_client::AcknowledgementReceiver;
use log::*; use log::*;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use nym_sphinx::params::PacketSize; use nymsphinx::params::PacketSize;
use nym_sphinx::{ use nymsphinx::{
acknowledgements::AckKey, acknowledgements::AckKey,
addressing::clients::Recipient, addressing::clients::Recipient,
chunking::fragment::{Fragment, FragmentIdentifier}, chunking::fragment::{Fragment, FragmentIdentifier},
@@ -249,7 +249,7 @@ where
} }
} }
pub(super) fn start_with_shutdown(self, shutdown: nym_task::TaskClient) { pub(super) fn start_with_shutdown(self, shutdown: task::TaskClient) {
let mut acknowledgement_listener = self.acknowledgement_listener; let mut acknowledgement_listener = self.acknowledgement_listener;
let mut input_message_listener = self.input_message_listener; let mut input_message_listener = self.input_message_listener;
let mut retransmission_request_listener = self.retransmission_request_listener; let mut retransmission_request_listener = self.retransmission_request_listener;
@@ -9,12 +9,12 @@ use crate::client::real_messages_control::acknowledgement_control::PacketDestina
use crate::client::real_messages_control::message_handler::{MessageHandler, PreparationError}; use crate::client::real_messages_control::message_handler::{MessageHandler, PreparationError};
use crate::client::real_messages_control::real_traffic_stream::RealMessage; use crate::client::real_messages_control::real_traffic_stream::RealMessage;
use crate::client::replies::reply_controller::ReplyControllerSender; use crate::client::replies::reply_controller::ReplyControllerSender;
use client_connections::TransmissionLane;
use futures::StreamExt; use futures::StreamExt;
use log::*; use log::*;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::chunking::fragment::Fragment; use nymsphinx::chunking::fragment::Fragment;
use nym_sphinx::preparer::PreparedFragment; use nymsphinx::preparer::PreparedFragment;
use nym_task::connections::TransmissionLane;
use rand::{CryptoRng, Rng}; use rand::{CryptoRng, Rng};
use std::sync::{Arc, Weak}; use std::sync::{Arc, Weak};
@@ -137,7 +137,7 @@ where
.await .await
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started RetransmissionRequestListener with graceful shutdown support"); debug!("Started RetransmissionRequestListener with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
@@ -5,7 +5,7 @@ use super::action_controller::{AckActionSender, Action};
use super::SentPacketNotificationReceiver; use super::SentPacketNotificationReceiver;
use futures::StreamExt; use futures::StreamExt;
use log::*; use log::*;
use nym_sphinx::chunking::fragment::{FragmentIdentifier, COVER_FRAG_ID}; use nymsphinx::chunking::fragment::{FragmentIdentifier, COVER_FRAG_ID};
/// Module responsible for starting up retransmission timers. /// Module responsible for starting up retransmission timers.
/// It is required because when we send our packet to the `real traffic stream` controlled /// It is required because when we send our packet to the `real traffic stream` controlled
@@ -37,7 +37,7 @@ impl SentNotificationListener {
.unwrap(); .unwrap();
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started SentNotificationListener with graceful shutdown support"); debug!("Started SentNotificationListener with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
@@ -8,23 +8,23 @@ use crate::client::real_messages_control::real_traffic_stream::{
use crate::client::real_messages_control::{AckActionSender, Action}; use crate::client::real_messages_control::{AckActionSender, Action};
use crate::client::replies::reply_storage::{ReceivedReplySurbsMap, SentReplyKeys, UsedSenderTags}; use crate::client::replies::reply_storage::{ReceivedReplySurbsMap, SentReplyKeys, UsedSenderTags};
use crate::client::topology_control::{TopologyAccessor, TopologyReadPermit}; use crate::client::topology_control::{TopologyAccessor, TopologyReadPermit};
use client_connections::TransmissionLane;
use log::{debug, error, info, trace, warn}; use log::{debug, error, info, trace, warn};
use nym_sphinx::acknowledgements::AckKey; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::anonymous_replies::requests::{AnonymousSenderTag, RepliableMessage, ReplyMessage}; use nymsphinx::anonymous_replies::requests::{AnonymousSenderTag, RepliableMessage, ReplyMessage};
use nym_sphinx::anonymous_replies::{ReplySurb, SurbEncryptionKey}; use nymsphinx::anonymous_replies::{ReplySurb, SurbEncryptionKey};
use nym_sphinx::chunking::fragment::{Fragment, FragmentIdentifier}; use nymsphinx::chunking::fragment::{Fragment, FragmentIdentifier};
use nym_sphinx::message::NymMessage; use nymsphinx::message::NymMessage;
use nym_sphinx::params::{PacketSize, DEFAULT_NUM_MIX_HOPS}; use nymsphinx::params::{PacketSize, DEFAULT_NUM_MIX_HOPS};
use nym_sphinx::preparer::{MessagePreparer, PreparedFragment}; use nymsphinx::preparer::{MessagePreparer, PreparedFragment};
use nym_sphinx::Delay; use nymsphinx::Delay;
use nym_task::connections::TransmissionLane;
use nym_topology::{NymTopology, NymTopologyError};
use rand::{CryptoRng, Rng}; use rand::{CryptoRng, Rng};
use std::collections::HashMap; use std::collections::HashMap;
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
use thiserror::Error; use thiserror::Error;
use topology::{NymTopology, NymTopologyError};
// TODO: move that error elsewhere since it seems to be contaminating different files // TODO: move that error elsewhere since it seems to be contaminating different files
#[derive(Debug, Clone, Error)] #[derive(Debug, Clone, Error)]
@@ -21,13 +21,13 @@ use crate::{
}, },
spawn_future, spawn_future,
}; };
use client_connections::{ConnectionCommandReceiver, LaneQueueLengths};
use futures::channel::mpsc; use futures::channel::mpsc;
use gateway_client::AcknowledgementReceiver; use gateway_client::AcknowledgementReceiver;
use log::*; use log::*;
use nym_sphinx::acknowledgements::AckKey; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::params::PacketSize; use nymsphinx::params::PacketSize;
use nym_task::connections::{ConnectionCommandReceiver, LaneQueueLengths};
use rand::{rngs::OsRng, CryptoRng, Rng}; use rand::{rngs::OsRng, CryptoRng, Rng};
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
@@ -81,11 +81,7 @@ pub struct Config {
/// Defines maximum amount of time the client is going to wait for reply surbs before explicitly asking /// Defines maximum amount of time the client is going to wait for reply surbs before explicitly asking
/// for more even though in theory they wouldn't need to. /// for more even though in theory they wouldn't need to.
maximum_reply_surb_rerequest_waiting_period: Duration, maximum_reply_surb_waiting_period: Duration,
/// Defines maximum amount of time the client is going to wait for reply surbs before
/// deciding it's never going to get them and would drop all pending messages
maximum_reply_surb_drop_waiting_period: Duration,
/// Defines maximum amount of time given reply surb is going to be valid for. /// Defines maximum amount of time given reply surb is going to be valid for.
/// This is going to be superseded by key rotation once implemented. /// This is going to be superseded by key rotation once implemented.
@@ -123,8 +119,7 @@ impl<'a> From<&'a Config> for reply_controller::Config {
cfg.minimum_reply_surb_request_size, cfg.minimum_reply_surb_request_size,
cfg.maximum_reply_surb_request_size, cfg.maximum_reply_surb_request_size,
cfg.maximum_allowed_reply_surb_request_size, cfg.maximum_allowed_reply_surb_request_size,
cfg.maximum_reply_surb_rerequest_waiting_period, cfg.maximum_reply_surb_waiting_period,
cfg.maximum_reply_surb_drop_waiting_period,
cfg.maximum_reply_surb_age, cfg.maximum_reply_surb_age,
cfg.maximum_reply_key_age, cfg.maximum_reply_key_age,
) )
@@ -166,10 +161,8 @@ impl Config {
.maximum_reply_surb_request_size, .maximum_reply_surb_request_size,
maximum_allowed_reply_surb_request_size: base_client_debug_config maximum_allowed_reply_surb_request_size: base_client_debug_config
.maximum_allowed_reply_surb_request_size, .maximum_allowed_reply_surb_request_size,
maximum_reply_surb_rerequest_waiting_period: base_client_debug_config maximum_reply_surb_waiting_period: base_client_debug_config
.maximum_reply_surb_rerequest_waiting_period, .maximum_reply_surb_waiting_period,
maximum_reply_surb_drop_waiting_period: base_client_debug_config
.maximum_reply_surb_drop_waiting_period,
maximum_reply_surb_age: base_client_debug_config.maximum_reply_surb_age, maximum_reply_surb_age: base_client_debug_config.maximum_reply_surb_age,
maximum_reply_key_age: base_client_debug_config.maximum_reply_key_age, maximum_reply_key_age: base_client_debug_config.maximum_reply_key_age,
} }
@@ -270,7 +263,7 @@ impl RealMessagesController<OsRng> {
} }
} }
pub fn start_with_shutdown(self, shutdown: nym_task::TaskClient) { pub fn start_with_shutdown(self, shutdown: task::TaskClient) {
let mut out_queue_control = self.out_queue_control; let mut out_queue_control = self.out_queue_control;
let ack_control = self.ack_control; let ack_control = self.ack_control;
let mut reply_control = self.reply_control; let mut reply_control = self.reply_control;
@@ -6,20 +6,20 @@ use crate::client::mix_traffic::BatchMixMessageSender;
use crate::client::real_messages_control::acknowledgement_control::SentPacketNotificationSender; use crate::client::real_messages_control::acknowledgement_control::SentPacketNotificationSender;
use crate::client::topology_control::TopologyAccessor; use crate::client::topology_control::TopologyAccessor;
use crate::client::transmission_buffer::TransmissionBuffer; use crate::client::transmission_buffer::TransmissionBuffer;
use client_connections::{
ConnectionCommand, ConnectionCommandReceiver, ConnectionId, LaneQueueLengths, TransmissionLane,
};
use futures::task::{Context, Poll}; use futures::task::{Context, Poll};
use futures::{Future, Stream, StreamExt}; use futures::{Future, Stream, StreamExt};
use log::*; use log::*;
use nym_sphinx::acknowledgements::AckKey; use nymsphinx::acknowledgements::AckKey;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::chunking::fragment::FragmentIdentifier; use nymsphinx::chunking::fragment::FragmentIdentifier;
use nym_sphinx::cover::generate_loop_cover_packet; use nymsphinx::cover::generate_loop_cover_packet;
use nym_sphinx::forwarding::packet::MixPacket; use nymsphinx::forwarding::packet::MixPacket;
use nym_sphinx::params::PacketSize; use nymsphinx::params::PacketSize;
use nym_sphinx::preparer::PreparedFragment; use nymsphinx::preparer::PreparedFragment;
use nym_sphinx::utils::sample_poisson_duration; use nymsphinx::utils::sample_poisson_duration;
use nym_task::connections::{
ConnectionCommand, ConnectionCommandReceiver, ConnectionId, LaneQueueLengths, TransmissionLane,
};
use rand::{CryptoRng, Rng}; use rand::{CryptoRng, Rng};
use std::pin::Pin; use std::pin::Pin;
use std::sync::Arc; use std::sync::Arc;
@@ -342,6 +342,7 @@ where
if let Poll::Ready(Some(id)) = Pin::new(&mut self.client_connection_rx).poll_next(cx) { if let Poll::Ready(Some(id)) = Pin::new(&mut self.client_connection_rx).poll_next(cx) {
match id { match id {
ConnectionCommand::Close(id) => self.on_close_connection(id), ConnectionCommand::Close(id) => self.on_close_connection(id),
ConnectionCommand::ActiveConnections(_) => panic!(),
} }
} }
@@ -420,6 +421,7 @@ where
if let Poll::Ready(Some(id)) = Pin::new(&mut self.client_connection_rx).poll_next(cx) { if let Poll::Ready(Some(id)) = Pin::new(&mut self.client_connection_rx).poll_next(cx) {
match id { match id {
ConnectionCommand::Close(id) => self.on_close_connection(id), ConnectionCommand::Close(id) => self.on_close_connection(id),
ConnectionCommand::ActiveConnections(_) => panic!(),
} }
} }
@@ -460,7 +462,7 @@ where
} }
#[cfg(not(target_arch = "wasm32"))] #[cfg(not(target_arch = "wasm32"))]
fn log_status(&self, shutdown: &mut nym_task::TaskClient) { fn log_status(&self, shutdown: &mut task::TaskClient) {
use crate::error::ClientCoreStatusMessage; use crate::error::ClientCoreStatusMessage;
let packets = self.transmission_buffer.total_size(); let packets = self.transmission_buffer.total_size();
@@ -501,7 +503,7 @@ where
} }
} }
pub(super) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(super) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started OutQueueControl with graceful shutdown support"); debug!("Started OutQueueControl with graceful shutdown support");
#[cfg(not(target_arch = "wasm32"))] #[cfg(not(target_arch = "wasm32"))]
@@ -4,20 +4,20 @@
use crate::client::replies::reply_controller::ReplyControllerSender; use crate::client::replies::reply_controller::ReplyControllerSender;
use crate::client::replies::reply_storage::SentReplyKeys; use crate::client::replies::reply_storage::SentReplyKeys;
use crate::spawn_future; use crate::spawn_future;
use crypto::asymmetric::encryption;
use crypto::Digest;
use futures::channel::mpsc; use futures::channel::mpsc;
use futures::lock::Mutex; use futures::lock::Mutex;
use futures::StreamExt; use futures::StreamExt;
use gateway_client::MixnetMessageReceiver; use gateway_client::MixnetMessageReceiver;
use log::*; use log::*;
use nym_crypto::asymmetric::encryption; use nymsphinx::anonymous_replies::requests::{
use nym_crypto::Digest;
use nym_sphinx::anonymous_replies::requests::{
RepliableMessage, RepliableMessageContent, ReplyMessage, ReplyMessageContent, RepliableMessage, RepliableMessageContent, ReplyMessage, ReplyMessageContent,
}; };
use nym_sphinx::anonymous_replies::{encryption_key::EncryptionKeyDigest, SurbEncryptionKey}; use nymsphinx::anonymous_replies::{encryption_key::EncryptionKeyDigest, SurbEncryptionKey};
use nym_sphinx::message::{NymMessage, PlainMessage}; use nymsphinx::message::{NymMessage, PlainMessage};
use nym_sphinx::params::ReplySurbKeyDigestAlgorithm; use nymsphinx::params::ReplySurbKeyDigestAlgorithm;
use nym_sphinx::receiver::{MessageReceiver, MessageRecoveryError, ReconstructedMessage}; use nymsphinx::receiver::{MessageReceiver, MessageRecoveryError, ReconstructedMessage};
use std::collections::HashSet; use std::collections::HashSet;
use std::sync::Arc; use std::sync::Arc;
@@ -47,7 +47,7 @@ struct ReceivedMessagesBufferInner {
impl ReceivedMessagesBufferInner { impl ReceivedMessagesBufferInner {
fn recover_from_fragment(&mut self, fragment_data: &[u8]) -> Option<NymMessage> { fn recover_from_fragment(&mut self, fragment_data: &[u8]) -> Option<NymMessage> {
if nym_sphinx::cover::is_cover(fragment_data) { if nymsphinx::cover::is_cover(fragment_data) {
trace!("The message was a loop cover message! Skipping it"); trace!("The message was a loop cover message! Skipping it");
return None; return None;
} }
@@ -399,7 +399,7 @@ impl RequestReceiver {
} }
} }
async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started RequestReceiver with graceful shutdown support"); debug!("Started RequestReceiver with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
tokio::select! { tokio::select! {
@@ -438,7 +438,7 @@ impl FragmentedMessageReceiver {
} }
} }
async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started FragmentedMessageReceiver with graceful shutdown support"); debug!("Started FragmentedMessageReceiver with graceful shutdown support");
while !shutdown.is_shutdown() { while !shutdown.is_shutdown() {
tokio::select! { tokio::select! {
@@ -488,7 +488,7 @@ impl ReceivedMessagesBufferController {
} }
} }
pub fn start_with_shutdown(self, shutdown: nym_task::TaskClient) { pub fn start_with_shutdown(self, shutdown: task::TaskClient) {
let mut fragmented_message_receiver = self.fragmented_message_receiver; let mut fragmented_message_receiver = self.fragmented_message_receiver;
let mut request_receiver = self.request_receiver; let mut request_receiver = self.request_receiver;
@@ -4,14 +4,14 @@
use crate::client::real_messages_control::acknowledgement_control::PendingAcknowledgement; use crate::client::real_messages_control::acknowledgement_control::PendingAcknowledgement;
use crate::client::real_messages_control::message_handler::{MessageHandler, PreparationError}; use crate::client::real_messages_control::message_handler::{MessageHandler, PreparationError};
use crate::client::replies::reply_storage::CombinedReplyStorage; use crate::client::replies::reply_storage::CombinedReplyStorage;
use client_connections::{ConnectionId, TransmissionLane};
use futures::channel::oneshot; use futures::channel::oneshot;
use futures::StreamExt; use futures::StreamExt;
use log::{debug, error, info, trace, warn}; use log::{debug, error, info, trace, warn};
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use nym_sphinx::anonymous_replies::ReplySurb; use nymsphinx::anonymous_replies::ReplySurb;
use nym_sphinx::chunking::fragment::{Fragment, FragmentIdentifier}; use nymsphinx::chunking::fragment::{Fragment, FragmentIdentifier};
use nym_task::connections::{ConnectionId, TransmissionLane};
use rand::{CryptoRng, Rng}; use rand::{CryptoRng, Rng};
use std::cmp::{max, min}; use std::cmp::{max, min};
use std::collections::btree_map::Entry; use std::collections::btree_map::Entry;
@@ -30,8 +30,7 @@ pub struct Config {
min_surb_request_size: u32, min_surb_request_size: u32,
max_surb_request_size: u32, max_surb_request_size: u32,
maximum_allowed_reply_surb_request_size: u32, maximum_allowed_reply_surb_request_size: u32,
max_surb_rerequest_waiting_period: Duration, max_surb_waiting_period: Duration,
max_surb_drop_waiting_period: Duration,
max_reply_surb_age: Duration, max_reply_surb_age: Duration,
max_reply_key_age: Duration, max_reply_key_age: Duration,
} }
@@ -41,8 +40,7 @@ impl Config {
min_surb_request_size: u32, min_surb_request_size: u32,
max_surb_request_size: u32, max_surb_request_size: u32,
maximum_allowed_reply_surb_request_size: u32, maximum_allowed_reply_surb_request_size: u32,
max_surb_rerequest_waiting_period: Duration, max_surb_waiting_period: Duration,
max_surb_drop_waiting_period: Duration,
max_reply_surb_age: Duration, max_reply_surb_age: Duration,
max_reply_key_age: Duration, max_reply_key_age: Duration,
) -> Self { ) -> Self {
@@ -50,8 +48,7 @@ impl Config {
min_surb_request_size, min_surb_request_size,
max_surb_request_size, max_surb_request_size,
maximum_allowed_reply_surb_request_size, maximum_allowed_reply_surb_request_size,
max_surb_rerequest_waiting_period, max_surb_waiting_period,
max_surb_drop_waiting_period,
max_reply_surb_age, max_reply_surb_age,
max_reply_key_age, max_reply_key_age,
} }
@@ -745,13 +742,9 @@ where
let diff = now - last_received_time; let diff = now - last_received_time;
if diff > self.config.max_surb_rerequest_waiting_period { if diff > self.config.max_surb_waiting_period {
if diff > self.config.max_surb_drop_waiting_period { warn!("We haven't received any surbs in {:?} from {pending_reply_target}. Going to explicitly ask for more", diff);
to_remove.push(*pending_reply_target) to_request.push(*pending_reply_target);
} else {
debug!("We haven't received any surbs in {:?} from {pending_reply_target}. Going to explicitly ask for more", diff);
to_request.push(*pending_reply_target);
}
} }
} }
@@ -835,7 +828,7 @@ where
// todo!() // todo!()
// } // }
pub(crate) async fn run_with_shutdown(&mut self, mut shutdown: nym_task::TaskClient) { pub(crate) async fn run_with_shutdown(&mut self, mut shutdown: task::TaskClient) {
debug!("Started ReplyController with graceful shutdown support"); debug!("Started ReplyController with graceful shutdown support");
let polling_rate = Duration::from_secs(5); let polling_rate = Duration::from_secs(5);
@@ -2,12 +2,12 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::client::real_messages_control::acknowledgement_control::PendingAcknowledgement; use crate::client::real_messages_control::acknowledgement_control::PendingAcknowledgement;
use client_connections::{ConnectionId, TransmissionLane};
use futures::channel::{mpsc, oneshot}; use futures::channel::{mpsc, oneshot};
use log::error; use log::error;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use nym_sphinx::anonymous_replies::ReplySurb; use nymsphinx::anonymous_replies::ReplySurb;
use nym_task::connections::{ConnectionId, TransmissionLane};
use std::sync::Weak; use std::sync::Weak;
pub(crate) fn new_control_channels() -> (ReplyControllerSender, ReplyControllerReceiver) { pub(crate) fn new_control_channels() -> (ReplyControllerSender, ReplyControllerReceiver) {
@@ -5,8 +5,6 @@ use crate::client::replies::reply_storage::backend::Empty;
use crate::client::replies::reply_storage::{CombinedReplyStorage, ReplyStorageBackend}; use crate::client::replies::reply_storage::{CombinedReplyStorage, ReplyStorageBackend};
use async_trait::async_trait; use async_trait::async_trait;
use std::path::PathBuf;
// well, right now we don't have the browser storage : ( // well, right now we don't have the browser storage : (
// so we keep everything in memory // so we keep everything in memory
#[derive(Debug)] #[derive(Debug)]
@@ -29,18 +27,6 @@ impl Backend {
impl ReplyStorageBackend for Backend { impl ReplyStorageBackend for Backend {
type StorageError = <Empty as ReplyStorageBackend>::StorageError; type StorageError = <Empty as ReplyStorageBackend>::StorageError;
async fn new(
debug_config: &crate::config::DebugConfig,
_db_path: Option<PathBuf>,
) -> Result<Self, Self::StorageError> {
Ok(Backend {
empty: Empty {
min_surb_threshold: debug_config.minimum_reply_surb_storage_threshold,
max_surb_threshold: debug_config.maximum_reply_surb_storage_threshold,
},
})
}
async fn flush_surb_storage( async fn flush_surb_storage(
&mut self, &mut self,
storage: &CombinedReplyStorage, storage: &CombinedReplyStorage,
@@ -55,8 +41,4 @@ impl ReplyStorageBackend for Backend {
async fn load_surb_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError> { async fn load_surb_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError> {
self.empty.load_surb_storage().await self.empty.load_surb_storage().await
} }
fn get_inactive_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError> {
self.empty.get_inactive_storage()
}
} }
@@ -10,12 +10,6 @@ pub enum StorageError {
#[error("the provided database path doesn't have a filename defined")] #[error("the provided database path doesn't have a filename defined")]
DatabasePathWithoutFilename { provided_path: PathBuf }, DatabasePathWithoutFilename { provided_path: PathBuf },
#[error("unable to create the directory for the database")]
DatabasePathUnableToCreateParentDirectory {
provided_path: PathBuf,
source: io::Error,
},
#[error("failed to rename our databse file - {source}")] #[error("failed to rename our databse file - {source}")]
DatabaseRenameError { DatabaseRenameError {
#[source] #[source]
@@ -56,9 +50,4 @@ pub enum StorageError {
details: String, details: String,
// err: Option<Box<dyn std::error::Error>> // err: Option<Box<dyn std::error::Error>>
}, },
#[error("failed to create storage")]
FailedToCreateStorage {
source: Box<dyn std::error::Error + Send + Sync>,
},
} }
@@ -20,16 +20,6 @@ impl StorageManager {
database_path: P, database_path: P,
fresh: bool, fresh: bool,
) -> Result<Self, StorageError> { ) -> Result<Self, StorageError> {
// ensure the whole directory structure exists
if let Some(parent_dir) = database_path.as_ref().parent() {
std::fs::create_dir_all(parent_dir).map_err(|source| {
StorageError::DatabasePathUnableToCreateParentDirectory {
provided_path: database_path.as_ref().to_path_buf(),
source,
}
})?;
}
let mut opts = sqlx::sqlite::SqliteConnectOptions::new() let mut opts = sqlx::sqlite::SqliteConnectOptions::new()
.filename(database_path) .filename(database_path)
.create_if_missing(fresh); .create_if_missing(fresh);
@@ -1,7 +1,6 @@
// Copyright 2022 - Nym Technologies SA <contact@nymtech.net> // Copyright 2022 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::client::base_client::non_wasm_helpers;
use crate::client::replies::reply_storage::backend::fs_backend::manager::StorageManager; use crate::client::replies::reply_storage::backend::fs_backend::manager::StorageManager;
use crate::client::replies::reply_storage::backend::fs_backend::models::{ use crate::client::replies::reply_storage::backend::fs_backend::models::{
ReplySurbStorageMetadata, StoredReplyKey, StoredReplySurb, StoredSenderTag, StoredSurbSender, ReplySurbStorageMetadata, StoredReplyKey, StoredReplySurb, StoredSenderTag, StoredSurbSender,
@@ -12,7 +11,7 @@ use crate::client::replies::reply_storage::{
}; };
use async_trait::async_trait; use async_trait::async_trait;
use log::{error, info, warn}; use log::{error, info, warn};
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use std::fs; use std::fs;
use std::path::{Path, PathBuf}; use std::path::{Path, PathBuf};
use time::OffsetDateTime; use time::OffsetDateTime;
@@ -23,49 +22,11 @@ mod error;
mod manager; mod manager;
mod models; mod models;
#[derive(Debug)]
enum StorageManagerState {
Storage(StorageManager),
Inactive(InactiveMetadata),
}
// When the storage backaed is initialized as inactive, it will still contain metadata parameters
// that will be needed when the in-mem storage is fetched for use.
#[derive(Debug)]
struct InactiveMetadata {
pub minimum_reply_surb_storage_threshold: usize,
pub maximum_reply_surb_storage_threshold: usize,
}
impl StorageManagerState {
fn get(&self) -> &StorageManager {
match self {
StorageManagerState::Storage(manager) => manager,
StorageManagerState::Inactive(_) => {
panic!("tried to get storage of an inactive backend")
}
}
}
fn get_mut(&mut self) -> &mut StorageManager {
match self {
StorageManagerState::Storage(manager) => manager,
StorageManagerState::Inactive(_) => {
panic!("tried to get storage of an inactive backend")
}
}
}
fn is_active(&self) -> bool {
matches!(self, StorageManagerState::Storage(_))
}
}
#[derive(Debug)] #[derive(Debug)]
pub struct Backend { pub struct Backend {
temporary_old_path: Option<PathBuf>, temporary_old_path: Option<PathBuf>,
database_path: PathBuf, database_path: PathBuf,
manager: StorageManagerState, manager: StorageManager,
} }
impl Backend { impl Backend {
@@ -79,30 +40,15 @@ impl Backend {
}); });
} }
let manager = StorageManager::init(database_path, true).await?;
manager.create_status_table().await?;
let backend = Backend { let backend = Backend {
temporary_old_path: None, temporary_old_path: None,
database_path: owned_path, database_path: owned_path,
manager: StorageManagerState::Storage(manager), manager: StorageManager::init(database_path, true).await?,
}; };
Ok(backend) backend.manager.create_status_table().await?;
}
pub fn new_inactive( Ok(backend)
minimum_reply_surb_storage_threshold: usize,
maximum_reply_surb_storage_threshold: usize,
) -> Self {
Backend {
temporary_old_path: None,
database_path: PathBuf::new(),
manager: StorageManagerState::Inactive(InactiveMetadata {
minimum_reply_surb_storage_threshold,
maximum_reply_surb_storage_threshold,
}),
}
} }
pub async fn try_load<P: AsRef<Path>>(database_path: P) -> Result<Self, StorageError> { pub async fn try_load<P: AsRef<Path>>(database_path: P) -> Result<Self, StorageError> {
@@ -173,12 +119,12 @@ impl Backend {
Ok(Backend { Ok(Backend {
temporary_old_path: None, temporary_old_path: None,
database_path: owned_path, database_path: owned_path,
manager: StorageManagerState::Storage(manager), manager,
}) })
} }
async fn close_pool(&mut self) { async fn close_pool(&mut self) {
self.manager.get_mut().connection_pool.close().await; self.manager.connection_pool.close().await;
} }
async fn rotate(&mut self) -> Result<(), StorageError> { async fn rotate(&mut self) -> Result<(), StorageError> {
@@ -197,9 +143,8 @@ impl Backend {
fs::rename(&self.database_path, &temp_old) fs::rename(&self.database_path, &temp_old)
.map_err(|err| StorageError::DatabaseRenameError { source: err })?; .map_err(|err| StorageError::DatabaseRenameError { source: err })?;
self.manager = self.manager = StorageManager::init(&self.database_path, true).await?;
StorageManagerState::Storage(StorageManager::init(&self.database_path, true).await?); self.manager.create_status_table().await?;
self.manager.get_mut().create_status_table().await?;
self.temporary_old_path = Some(temp_old); self.temporary_old_path = Some(temp_old);
Ok(()) Ok(())
@@ -216,27 +161,26 @@ impl Backend {
} }
async fn start_storage_flush(&self) -> Result<(), StorageError> { async fn start_storage_flush(&self) -> Result<(), StorageError> {
Ok(self.manager.get().set_flush_status(true).await?) Ok(self.manager.set_flush_status(true).await?)
} }
async fn end_storage_flush(&self) -> Result<(), StorageError> { async fn end_storage_flush(&self) -> Result<(), StorageError> {
self.manager self.manager
.get()
.set_previous_flush_timestamp(OffsetDateTime::now_utc().unix_timestamp()) .set_previous_flush_timestamp(OffsetDateTime::now_utc().unix_timestamp())
.await?; .await?;
Ok(self.manager.get().set_flush_status(false).await?) Ok(self.manager.set_flush_status(false).await?)
} }
async fn start_client_use(&self) -> Result<(), StorageError> { async fn start_client_use(&self) -> Result<(), StorageError> {
Ok(self.manager.get().set_client_in_use_status(true).await?) Ok(self.manager.set_client_in_use_status(true).await?)
} }
async fn stop_client_use(&self) -> Result<(), StorageError> { async fn stop_client_use(&self) -> Result<(), StorageError> {
Ok(self.manager.get().set_client_in_use_status(false).await?) Ok(self.manager.set_client_in_use_status(false).await?)
} }
async fn get_stored_tags(&self) -> Result<UsedSenderTags, StorageError> { async fn get_stored_tags(&self) -> Result<UsedSenderTags, StorageError> {
let stored = self.manager.get().get_tags().await?; let stored = self.manager.get_tags().await?;
// stop at the first instance of corruption. if even a single entry is malformed, // stop at the first instance of corruption. if even a single entry is malformed,
// something weird has happened and we can't trust the rest of the data // something weird has happened and we can't trust the rest of the data
@@ -252,7 +196,6 @@ impl Backend {
for map_ref in tags.as_raw_iter() { for map_ref in tags.as_raw_iter() {
let (recipient, tag) = map_ref.pair(); let (recipient, tag) = map_ref.pair();
self.manager self.manager
.get()
.insert_tag(StoredSenderTag::new(*recipient, *tag)) .insert_tag(StoredSenderTag::new(*recipient, *tag))
.await?; .await?;
} }
@@ -260,7 +203,7 @@ impl Backend {
} }
async fn get_stored_reply_keys(&self) -> Result<SentReplyKeys, StorageError> { async fn get_stored_reply_keys(&self) -> Result<SentReplyKeys, StorageError> {
let stored = self.manager.get().get_reply_keys().await?; let stored = self.manager.get_reply_keys().await?;
// stop at the first instance of corruption. if even a single entry is malformed, // stop at the first instance of corruption. if even a single entry is malformed,
// something weird has happened and we can't trust the rest of the data // something weird has happened and we can't trust the rest of the data
@@ -276,7 +219,6 @@ impl Backend {
for map_ref in reply_keys.as_raw_iter() { for map_ref in reply_keys.as_raw_iter() {
let (digest, key) = map_ref.pair(); let (digest, key) = map_ref.pair();
self.manager self.manager
.get()
.insert_reply_key(StoredReplyKey::new(*digest, *key)) .insert_reply_key(StoredReplyKey::new(*digest, *key))
.await?; .await?;
} }
@@ -284,7 +226,7 @@ impl Backend {
} }
async fn get_stored_reply_surbs(&self) -> Result<ReceivedReplySurbsMap, StorageError> { async fn get_stored_reply_surbs(&self) -> Result<ReceivedReplySurbsMap, StorageError> {
let surb_senders = self.manager.get().get_surb_senders().await?; let surb_senders = self.manager.get_surb_senders().await?;
let metadata = self.get_reply_surb_storage_metadata().await?; let metadata = self.get_reply_surb_storage_metadata().await?;
let mut received_surbs = Vec::with_capacity(surb_senders.len()); let mut received_surbs = Vec::with_capacity(surb_senders.len());
@@ -294,7 +236,6 @@ impl Backend {
sender.try_into()?; sender.try_into()?;
let stored_surbs = self let stored_surbs = self
.manager .manager
.get()
.get_reply_surbs(sender_id) .get_reply_surbs(sender_id)
.await? .await?
.into_iter() .into_iter()
@@ -322,7 +263,6 @@ impl Backend {
let (tag, received_surbs) = map_ref.pair(); let (tag, received_surbs) = map_ref.pair();
let sender_id = self let sender_id = self
.manager .manager
.get()
.insert_surb_sender(StoredSurbSender::new( .insert_surb_sender(StoredSurbSender::new(
*tag, *tag,
received_surbs.surbs_last_received_at(), received_surbs.surbs_last_received_at(),
@@ -331,7 +271,6 @@ impl Backend {
for reply_surb in received_surbs.surbs_ref() { for reply_surb in received_surbs.surbs_ref() {
self.manager self.manager
.get()
.insert_reply_surb(StoredReplySurb::new(sender_id, reply_surb)) .insert_reply_surb(StoredReplySurb::new(sender_id, reply_surb))
.await? .await?
} }
@@ -343,7 +282,6 @@ impl Backend {
&self, &self,
) -> Result<ReplySurbStorageMetadata, StorageError> { ) -> Result<ReplySurbStorageMetadata, StorageError> {
self.manager self.manager
.get()
.get_reply_surb_storage_metadata() .get_reply_surb_storage_metadata()
.await .await
.map_err(Into::into) .map_err(Into::into)
@@ -354,7 +292,6 @@ impl Backend {
reply_surbs: &ReceivedReplySurbsMap, reply_surbs: &ReceivedReplySurbsMap,
) -> Result<(), StorageError> { ) -> Result<(), StorageError> {
self.manager self.manager
.get()
.insert_reply_surb_storage_metadata(ReplySurbStorageMetadata::new( .insert_reply_surb_storage_metadata(ReplySurbStorageMetadata::new(
reply_surbs.min_surb_threshold(), reply_surbs.min_surb_threshold(),
reply_surbs.max_surb_threshold(), reply_surbs.max_surb_threshold(),
@@ -368,24 +305,6 @@ impl Backend {
impl ReplyStorageBackend for Backend { impl ReplyStorageBackend for Backend {
type StorageError = error::StorageError; type StorageError = error::StorageError;
async fn new(
debug_config: &crate::config::DebugConfig,
db_path: Option<PathBuf>,
) -> Result<Self, Self::StorageError> {
non_wasm_helpers::setup_fs_reply_surb_backend(db_path, debug_config)
.await
.map_err(|err| {
log::error!("Failed to create storage: {err}");
Self::StorageError::FailedToCreateStorage {
source: Box::new(err),
}
})
}
fn is_active(&self) -> bool {
self.manager.is_active()
}
async fn start_storage_session(&self) -> Result<(), Self::StorageError> { async fn start_storage_session(&self) -> Result<(), Self::StorageError> {
self.start_client_use().await self.start_client_use().await
} }
@@ -423,18 +342,6 @@ impl ReplyStorageBackend for Backend {
Ok(CombinedReplyStorage::load(reply_keys, reply_surbs, tags)) Ok(CombinedReplyStorage::load(reply_keys, reply_surbs, tags))
} }
fn get_inactive_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError> {
match self.manager {
StorageManagerState::Storage(_) => {
panic!("tried to get inactive storage from an active storage backend")
}
StorageManagerState::Inactive(ref state) => Ok(CombinedReplyStorage::new(
state.minimum_reply_surb_storage_threshold,
state.maximum_reply_surb_storage_threshold,
)),
}
}
async fn stop_storage_session(self) -> Result<(), Self::StorageError> { async fn stop_storage_session(self) -> Result<(), Self::StorageError> {
self.stop_client_use().await self.stop_client_use().await
} }
@@ -3,13 +3,13 @@
use crate::client::replies::reply_storage::backend::fs_backend::error::StorageError; use crate::client::replies::reply_storage::backend::fs_backend::error::StorageError;
use crate::client::replies::reply_storage::key_storage::UsedReplyKey; use crate::client::replies::reply_storage::key_storage::UsedReplyKey;
use nym_crypto::generic_array::typenum::Unsigned; use crypto::generic_array::typenum::Unsigned;
use nym_crypto::Digest; use crypto::Digest;
use nym_sphinx::addressing::clients::{Recipient, RecipientBytes}; use nymsphinx::addressing::clients::{Recipient, RecipientBytes};
use nym_sphinx::anonymous_replies::encryption_key::EncryptionKeyDigest; use nymsphinx::anonymous_replies::encryption_key::EncryptionKeyDigest;
use nym_sphinx::anonymous_replies::requests::{AnonymousSenderTag, SENDER_TAG_SIZE}; use nymsphinx::anonymous_replies::requests::{AnonymousSenderTag, SENDER_TAG_SIZE};
use nym_sphinx::anonymous_replies::{ReplySurb, SurbEncryptionKey, SurbEncryptionKeySize}; use nymsphinx::anonymous_replies::{ReplySurb, SurbEncryptionKey, SurbEncryptionKeySize};
use nym_sphinx::params::ReplySurbKeyDigestAlgorithm; use nymsphinx::params::ReplySurbKeyDigestAlgorithm;
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub(crate) struct StoredSenderTag { pub(crate) struct StoredSenderTag {
@@ -3,7 +3,7 @@
use crate::client::replies::reply_storage::CombinedReplyStorage; use crate::client::replies::reply_storage::CombinedReplyStorage;
use async_trait::async_trait; use async_trait::async_trait;
use std::{error::Error, path::PathBuf}; use std::error::Error;
use thiserror::Error; use thiserror::Error;
#[cfg(target_arch = "wasm32")] #[cfg(target_arch = "wasm32")]
@@ -30,16 +30,6 @@ pub struct Empty {
impl ReplyStorageBackend for Empty { impl ReplyStorageBackend for Empty {
type StorageError = UndefinedError; type StorageError = UndefinedError;
async fn new(
debug_config: &crate::config::DebugConfig,
_db_path: Option<PathBuf>,
) -> Result<Self, Self::StorageError> {
Ok(Self {
min_surb_threshold: debug_config.minimum_reply_surb_storage_threshold,
max_surb_threshold: debug_config.maximum_reply_surb_storage_threshold,
})
}
async fn flush_surb_storage( async fn flush_surb_storage(
&mut self, &mut self,
_storage: &CombinedReplyStorage, _storage: &CombinedReplyStorage,
@@ -60,28 +50,12 @@ impl ReplyStorageBackend for Empty {
self.max_surb_threshold, self.max_surb_threshold,
)) ))
} }
fn get_inactive_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError> {
Ok(CombinedReplyStorage::new(
self.min_surb_threshold,
self.max_surb_threshold,
))
}
} }
#[async_trait] #[async_trait]
pub trait ReplyStorageBackend: Sized { pub trait ReplyStorageBackend: Sized {
type StorageError: Error + 'static; type StorageError: Error + 'static;
async fn new(
debug_config: &crate::config::DebugConfig,
db_path: Option<PathBuf>,
) -> Result<Self, Self::StorageError>;
fn is_active(&self) -> bool {
true
}
async fn start_storage_session(&self) -> Result<(), Self::StorageError> { async fn start_storage_session(&self) -> Result<(), Self::StorageError> {
Ok(()) Ok(())
} }
@@ -99,11 +73,6 @@ pub trait ReplyStorageBackend: Sized {
async fn load_surb_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError>; async fn load_surb_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError>;
/// In the case the storage backend is initialized in an inactive state (persisting data is
/// disabled), we might still need to fetch the (in-mem) storage and the parameters it was
/// created with.
fn get_inactive_storage(&self) -> Result<CombinedReplyStorage, Self::StorageError>;
async fn stop_storage_session(self) -> Result<(), Self::StorageError> { async fn stop_storage_session(self) -> Result<(), Self::StorageError> {
Ok(()) Ok(())
} }
@@ -3,8 +3,8 @@
use dashmap::iter::Iter; use dashmap::iter::Iter;
use dashmap::DashMap; use dashmap::DashMap;
use nym_sphinx::anonymous_replies::encryption_key::EncryptionKeyDigest; use nymsphinx::anonymous_replies::encryption_key::EncryptionKeyDigest;
use nym_sphinx::anonymous_replies::SurbEncryptionKey; use nymsphinx::anonymous_replies::SurbEncryptionKey;
use std::ops::Deref; use std::ops::Deref;
use std::sync::Arc; use std::sync::Arc;
use time::OffsetDateTime; use time::OffsetDateTime;
@@ -37,7 +37,7 @@ where
pub async fn flush_on_shutdown( pub async fn flush_on_shutdown(
mut self, mut self,
mem_state: CombinedReplyStorage, mem_state: CombinedReplyStorage,
mut shutdown: nym_task::TaskClient, mut shutdown: task::TaskClient,
) { ) {
use log::{debug, error, info, warn}; use log::{debug, error, info, warn};
@@ -4,8 +4,8 @@
use dashmap::iter::Iter; use dashmap::iter::Iter;
use dashmap::DashMap; use dashmap::DashMap;
use log::trace; use log::trace;
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use nym_sphinx::anonymous_replies::ReplySurb; use nymsphinx::anonymous_replies::ReplySurb;
use std::collections::VecDeque; use std::collections::VecDeque;
use std::sync::atomic::{AtomicUsize, Ordering}; use std::sync::atomic::{AtomicUsize, Ordering};
use std::sync::Arc; use std::sync::Arc;
@@ -2,8 +2,8 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use dashmap::DashMap; use dashmap::DashMap;
use nym_sphinx::addressing::clients::{Recipient, RecipientBytes}; use nymsphinx::addressing::clients::{Recipient, RecipientBytes};
use nym_sphinx::anonymous_replies::requests::AnonymousSenderTag; use nymsphinx::anonymous_replies::requests::AnonymousSenderTag;
use std::sync::Arc; use std::sync::Arc;
#[cfg(all(not(target_arch = "wasm32"), feature = "fs-surb-storage"))] #[cfg(all(not(target_arch = "wasm32"), feature = "fs-surb-storage"))]
@@ -4,15 +4,15 @@
use crate::spawn_future; use crate::spawn_future;
use futures::StreamExt; use futures::StreamExt;
use log::*; use log::*;
use nym_sphinx::addressing::clients::Recipient; use nymsphinx::addressing::clients::Recipient;
use nym_sphinx::params::DEFAULT_NUM_MIX_HOPS; use nymsphinx::params::DEFAULT_NUM_MIX_HOPS;
use nym_topology::{nym_topology_from_detailed, NymTopology, NymTopologyError};
use rand::seq::SliceRandom; use rand::seq::SliceRandom;
use rand::thread_rng; use rand::thread_rng;
use std::ops::Deref; use std::ops::Deref;
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
use tokio::sync::{RwLock, RwLockReadGuard}; use tokio::sync::{RwLock, RwLockReadGuard};
use topology::{nym_topology_from_detailed, NymTopology, NymTopologyError};
use url::Url; use url::Url;
// I'm extremely curious why compiler NEVER complained about lack of Debug here before // I'm extremely curious why compiler NEVER complained about lack of Debug here before
@@ -306,7 +306,7 @@ impl TopologyRefresher {
self.topology_accessor.ensure_is_routable().await self.topology_accessor.ensure_is_routable().await
} }
pub fn start_with_shutdown(mut self, mut shutdown: nym_task::TaskClient) { pub fn start_with_shutdown(mut self, mut shutdown: task::TaskClient) {
spawn_future(async move { spawn_future(async move {
debug!("Started TopologyRefresher with graceful shutdown support"); debug!("Started TopologyRefresher with graceful shutdown support");
@@ -3,8 +3,8 @@
use crate::client::helpers::{get_time_now, Instant}; use crate::client::helpers::{get_time_now, Instant};
use crate::client::real_messages_control::real_traffic_stream::RealMessage; use crate::client::real_messages_control::real_traffic_stream::RealMessage;
use nym_sphinx::chunking::fragment::Fragment; use client_connections::TransmissionLane;
use nym_task::connections::TransmissionLane; use nymsphinx::chunking::fragment::Fragment;
use rand::{seq::SliceRandom, Rng}; use rand::{seq::SliceRandom, Rng};
use std::{ use std::{
collections::{HashMap, HashSet, VecDeque}, collections::{HashMap, HashSet, VecDeque},
+19 -36
View File
@@ -1,9 +1,9 @@
// Copyright 2021 - Nym Technologies SA <contact@nymtech.net> // Copyright 2021 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use nym_config::defaults::NymNetworkDetails; use config::defaults::NymNetworkDetails;
use nym_config::{NymConfig, OptionalSet, DB_FILE_NAME}; use config::{NymConfig, OptionalSet, DB_FILE_NAME};
use nym_sphinx::params::PacketSize; use nymsphinx::params::PacketSize;
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use std::marker::PhantomData; use std::marker::PhantomData;
use std::path::PathBuf; use std::path::PathBuf;
@@ -45,8 +45,7 @@ const DEFAULT_MAXIMUM_REPLY_SURB_REQUEST_SIZE: u32 = 100;
const DEFAULT_MAXIMUM_ALLOWED_SURB_REQUEST_SIZE: u32 = 500; const DEFAULT_MAXIMUM_ALLOWED_SURB_REQUEST_SIZE: u32 = 500;
const DEFAULT_MAXIMUM_REPLY_SURB_REREQUEST_WAITING_PERIOD: Duration = Duration::from_secs(10); const DEFAULT_MAXIMUM_REPLY_SURB_WAITING_PERIOD: Duration = Duration::from_secs(10);
const DEFAULT_MAXIMUM_REPLY_SURB_DROP_WAITING_PERIOD: Duration = Duration::from_secs(5 * 60);
// 12 hours // 12 hours
const DEFAULT_MAXIMUM_REPLY_SURB_AGE: Duration = Duration::from_secs(12 * 60 * 60); const DEFAULT_MAXIMUM_REPLY_SURB_AGE: Duration = Duration::from_secs(12 * 60 * 60);
@@ -171,15 +170,10 @@ impl<T> Config<T> {
self self
} }
pub fn set_gateway_endpoint(&mut self, gateway_endpoint: GatewayEndpointConfig) { pub fn with_gateway_endpoint(&mut self, gateway_endpoint: GatewayEndpointConfig) {
self.client.gateway_endpoint = gateway_endpoint; self.client.gateway_endpoint = gateway_endpoint;
} }
pub fn with_gateway_endpoint(mut self, gateway_endpoint: GatewayEndpointConfig) -> Self {
self.client.gateway_endpoint = gateway_endpoint;
self
}
pub fn with_gateway_id<S: Into<String>>(&mut self, id: S) { pub fn with_gateway_id<S: Into<String>>(&mut self, id: S) {
self.client.gateway_endpoint.gateway_id = id.into(); self.client.gateway_endpoint.gateway_id = id.into();
} }
@@ -378,12 +372,8 @@ impl<T> Config<T> {
self.debug.maximum_allowed_reply_surb_request_size self.debug.maximum_allowed_reply_surb_request_size
} }
pub fn get_maximum_reply_surb_rerequest_waiting_period(&self) -> Duration { pub fn get_maximum_reply_surb_waiting_period(&self) -> Duration {
self.debug.maximum_reply_surb_rerequest_waiting_period self.debug.maximum_reply_surb_waiting_period
}
pub fn get_maximum_reply_surb_drop_waiting_period(&self) -> Duration {
self.debug.maximum_reply_surb_drop_waiting_period
} }
pub fn get_maximum_reply_surb_age(&self) -> Duration { pub fn get_maximum_reply_surb_age(&self) -> Duration {
@@ -435,8 +425,8 @@ impl GatewayEndpointConfig {
} }
} }
impl From<nym_topology::gateway::Node> for GatewayEndpointConfig { impl From<topology::gateway::Node> for GatewayEndpointConfig {
fn from(node: nym_topology::gateway::Node) -> GatewayEndpointConfig { fn from(node: topology::gateway::Node) -> GatewayEndpointConfig {
let gateway_listener = node.clients_address(); let gateway_listener = node.clients_address();
GatewayEndpointConfig { GatewayEndpointConfig {
gateway_id: node.identity_key.to_base58_string(), gateway_id: node.identity_key.to_base58_string(),
@@ -551,35 +541,35 @@ impl<T: NymConfig> Default for Client<T> {
impl<T: NymConfig> Client<T> { impl<T: NymConfig> Client<T> {
fn default_private_identity_key_file(id: &str) -> PathBuf { fn default_private_identity_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("private_identity.pem") T::default_data_directory(Some(id)).join("private_identity.pem")
} }
fn default_public_identity_key_file(id: &str) -> PathBuf { fn default_public_identity_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("public_identity.pem") T::default_data_directory(Some(id)).join("public_identity.pem")
} }
fn default_private_encryption_key_file(id: &str) -> PathBuf { fn default_private_encryption_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("private_encryption.pem") T::default_data_directory(Some(id)).join("private_encryption.pem")
} }
fn default_public_encryption_key_file(id: &str) -> PathBuf { fn default_public_encryption_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("public_encryption.pem") T::default_data_directory(Some(id)).join("public_encryption.pem")
} }
fn default_gateway_shared_key_file(id: &str) -> PathBuf { fn default_gateway_shared_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("gateway_shared.pem") T::default_data_directory(Some(id)).join("gateway_shared.pem")
} }
fn default_ack_key_file(id: &str) -> PathBuf { fn default_ack_key_file(id: &str) -> PathBuf {
T::default_data_directory(id).join("ack_key.pem") T::default_data_directory(Some(id)).join("ack_key.pem")
} }
fn default_reply_surb_database_path(id: &str) -> PathBuf { fn default_reply_surb_database_path(id: &str) -> PathBuf {
T::default_data_directory(id).join("persistent_reply_store.sqlite") T::default_data_directory(Some(id)).join("persistent_reply_store.sqlite")
} }
fn default_database_path(id: &str) -> PathBuf { fn default_database_path(id: &str) -> PathBuf {
T::default_data_directory(id).join(DB_FILE_NAME) T::default_data_directory(Some(id)).join(DB_FILE_NAME)
} }
} }
@@ -673,12 +663,7 @@ pub struct DebugConfig {
/// Defines maximum amount of time the client is going to wait for reply surbs before explicitly asking /// Defines maximum amount of time the client is going to wait for reply surbs before explicitly asking
/// for more even though in theory they wouldn't need to. /// for more even though in theory they wouldn't need to.
#[serde(with = "humantime_serde")] #[serde(with = "humantime_serde")]
pub maximum_reply_surb_rerequest_waiting_period: Duration, pub maximum_reply_surb_waiting_period: Duration,
/// Defines maximum amount of time the client is going to wait for reply surbs before
/// deciding it's never going to get them and would drop all pending messages
#[serde(with = "humantime_serde")]
pub maximum_reply_surb_drop_waiting_period: Duration,
/// Defines maximum amount of time given reply surb is going to be valid for. /// Defines maximum amount of time given reply surb is going to be valid for.
/// This is going to be superseded by key rotation once implemented. /// This is going to be superseded by key rotation once implemented.
@@ -719,9 +704,7 @@ impl Default for DebugConfig {
minimum_reply_surb_request_size: DEFAULT_MINIMUM_REPLY_SURB_REQUEST_SIZE, minimum_reply_surb_request_size: DEFAULT_MINIMUM_REPLY_SURB_REQUEST_SIZE,
maximum_reply_surb_request_size: DEFAULT_MAXIMUM_REPLY_SURB_REQUEST_SIZE, maximum_reply_surb_request_size: DEFAULT_MAXIMUM_REPLY_SURB_REQUEST_SIZE,
maximum_allowed_reply_surb_request_size: DEFAULT_MAXIMUM_ALLOWED_SURB_REQUEST_SIZE, maximum_allowed_reply_surb_request_size: DEFAULT_MAXIMUM_ALLOWED_SURB_REQUEST_SIZE,
maximum_reply_surb_rerequest_waiting_period: maximum_reply_surb_waiting_period: DEFAULT_MAXIMUM_REPLY_SURB_WAITING_PERIOD,
DEFAULT_MAXIMUM_REPLY_SURB_REREQUEST_WAITING_PERIOD,
maximum_reply_surb_drop_waiting_period: DEFAULT_MAXIMUM_REPLY_SURB_DROP_WAITING_PERIOD,
maximum_reply_surb_age: DEFAULT_MAXIMUM_REPLY_SURB_AGE, maximum_reply_surb_age: DEFAULT_MAXIMUM_REPLY_SURB_AGE,
maximum_reply_key_age: DEFAULT_MAXIMUM_REPLY_KEY_AGE, maximum_reply_key_age: DEFAULT_MAXIMUM_REPLY_KEY_AGE,
} }
@@ -2,7 +2,7 @@
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crate::config::Config; use crate::config::Config;
use nym_config::NymConfig; use config::NymConfig;
use std::path::{Path, PathBuf}; use std::path::{Path, PathBuf};
#[derive(Debug)] #[derive(Debug)]
+2 -2
View File
@@ -1,9 +1,9 @@
// Copyright 2022 - Nym Technologies SA <contact@nymtech.net> // Copyright 2022 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use crypto::asymmetric::identity::Ed25519RecoveryError;
use gateway_client::error::GatewayClientError; use gateway_client::error::GatewayClientError;
use nym_crypto::asymmetric::identity::Ed25519RecoveryError; use topology::NymTopologyError;
use nym_topology::NymTopologyError;
use validator_client::ValidatorClientError; use validator_client::ValidatorClientError;
#[derive(thiserror::Error, Debug)] #[derive(thiserror::Error, Debug)]
+5 -8
View File
@@ -6,19 +6,15 @@ use crate::{
config::{persistence::key_pathfinder::ClientKeyPathfinder, Config}, config::{persistence::key_pathfinder::ClientKeyPathfinder, Config},
error::ClientCoreError, error::ClientCoreError,
}; };
#[cfg(target_arch = "wasm32")] use config::NymConfig;
use gateway_client::wasm_mockups::SigningNyxdClient; use crypto::asymmetric::identity;
use gateway_client::GatewayClient; use gateway_client::GatewayClient;
use gateway_requests::registration::handshake::SharedKeys; use gateway_requests::registration::handshake::SharedKeys;
use nym_config::NymConfig;
use nym_crypto::asymmetric::identity;
use nym_topology::{filter::VersionFilterable, gateway};
use rand::{seq::SliceRandom, thread_rng}; use rand::{seq::SliceRandom, thread_rng};
use std::{sync::Arc, time::Duration}; use std::{sync::Arc, time::Duration};
use tap::TapFallible; use tap::TapFallible;
use topology::{filter::VersionFilterable, gateway};
use url::Url; use url::Url;
#[cfg(not(target_arch = "wasm32"))]
use validator_client::nyxd::SigningNyxdClient;
pub(super) async fn query_gateway_details( pub(super) async fn query_gateway_details(
validator_servers: Vec<Url>, validator_servers: Vec<Url>,
@@ -60,9 +56,10 @@ pub(super) async fn register_with_gateway(
our_identity: Arc<identity::KeyPair>, our_identity: Arc<identity::KeyPair>,
) -> Result<Arc<SharedKeys>, ClientCoreError> { ) -> Result<Arc<SharedKeys>, ClientCoreError> {
let timeout = Duration::from_millis(1500); let timeout = Duration::from_millis(1500);
let mut gateway_client: GatewayClient<SigningNyxdClient> = GatewayClient::new_init( let mut gateway_client = GatewayClient::new_init(
gateway.clients_address(), gateway.clients_address(),
gateway.identity_key, gateway.identity_key,
gateway.owner.clone(),
our_identity.clone(), our_identity.clone(),
timeout, timeout,
); );
+7 -7
View File
@@ -5,13 +5,13 @@
use std::fmt::Display; use std::fmt::Display;
use nym_sphinx::addressing::{clients::Recipient, nodes::NodeIdentity}; use nymsphinx::addressing::{clients::Recipient, nodes::NodeIdentity};
use rand::rngs::OsRng; use rand::rngs::OsRng;
use serde::Serialize; use serde::Serialize;
use tap::TapFallible; use tap::TapFallible;
use nym_config::NymConfig; use config::NymConfig;
use nym_crypto::asymmetric::{encryption, identity}; use crypto::asymmetric::{encryption, identity};
use url::Url; use url::Url;
use crate::client::key_manager::KeyManager; use crate::client::key_manager::KeyManager;
@@ -149,7 +149,7 @@ pub fn load_existing_gateway_config<T>(id: &str) -> Result<GatewayEndpointConfig
where where
T: NymConfig + ClientCoreConfigTrait, T: NymConfig + ClientCoreConfigTrait,
{ {
T::load_from_file(id) T::load_from_file(Some(id))
.map(|existing_config| existing_config.get_gateway_endpoint().clone()) .map(|existing_config| existing_config.get_gateway_endpoint().clone())
.map_err(|err| { .map_err(|err| {
log::error!( log::error!(
@@ -182,13 +182,13 @@ pub fn get_client_address_from_stored_keys<T>(
config: &Config<T>, config: &Config<T>,
) -> Result<Recipient, ClientCoreError> ) -> Result<Recipient, ClientCoreError>
where where
T: nym_config::NymConfig, T: config::NymConfig,
{ {
fn load_identity_keys( fn load_identity_keys(
pathfinder: &ClientKeyPathfinder, pathfinder: &ClientKeyPathfinder,
) -> Result<identity::KeyPair, ClientCoreError> { ) -> Result<identity::KeyPair, ClientCoreError> {
let identity_keypair: identity::KeyPair = let identity_keypair: identity::KeyPair =
nym_pemstore::load_keypair(&nym_pemstore::KeyPairPath::new( pemstore::load_keypair(&pemstore::KeyPairPath::new(
pathfinder.private_identity_key().to_owned(), pathfinder.private_identity_key().to_owned(),
pathfinder.public_identity_key().to_owned(), pathfinder.public_identity_key().to_owned(),
)) ))
@@ -200,7 +200,7 @@ where
pathfinder: &ClientKeyPathfinder, pathfinder: &ClientKeyPathfinder,
) -> Result<encryption::KeyPair, ClientCoreError> { ) -> Result<encryption::KeyPair, ClientCoreError> {
let sphinx_keypair: encryption::KeyPair = let sphinx_keypair: encryption::KeyPair =
nym_pemstore::load_keypair(&nym_pemstore::KeyPairPath::new( pemstore::load_keypair(&pemstore::KeyPairPath::new(
pathfinder.private_encryption_key().to_owned(), pathfinder.private_encryption_key().to_owned(),
pathfinder.public_encryption_key().to_owned(), pathfinder.public_encryption_key().to_owned(),
)) ))
+8 -6
View File
@@ -7,8 +7,8 @@ edition = "2021"
[dependencies] [dependencies]
bip39 = "1.0.1" bip39 = "1.0.1"
cfg-if = "0.1"
clap = { version = "4.0", features = ["cargo", "derive"] } clap = { version = "4.0", features = ["cargo", "derive"] }
log = "0.4"
rand = "0.7.3" rand = "0.7.3"
serde = { version = "1.0", features = ["derive"] } serde = { version = "1.0", features = ["derive"] }
thiserror = "1.0" thiserror = "1.0"
@@ -16,12 +16,14 @@ url = "2.2"
tokio = { version = "1.24.1", features = ["rt-multi-thread", "net", "signal", "macros"] } # async runtime tokio = { version = "1.24.1", features = ["rt-multi-thread", "net", "signal", "macros"] } # async runtime
coconut-interface = { path = "../../common/coconut-interface" } coconut-interface = { path = "../../common/coconut-interface" }
nym-config = { path = "../../common/config" } config = { path = "../../common/config" }
completions = { path = "../../common/completions" }
credentials = { path = "../../common/credentials" } credentials = { path = "../../common/credentials" }
credential-storage = { path = "../../common/credential-storage" } credential-storage = { path = "../../common/credential-storage" }
nym-crypto = { path = "../../common/crypto", features = ["rand", "asymmetric", "symmetric", "aes", "hashing"] } crypto = { path = "../../common/crypto", features = ["rand", "asymmetric", "symmetric", "aes", "hashing"] }
nym-bin-common = { path = "../../common/bin-common"} network-defaults = { path = "../../common/network-defaults" }
nym-network-defaults = { path = "../../common/network-defaults" } pemstore = { path = "../../common/pemstore" }
nym-pemstore = { path = "../../common/pemstore" }
validator-client = { path = "../../common/client-libs/validator-client", features = ["nyxd-client"] } validator-client = { path = "../../common/client-libs/validator-client", features = ["nyxd-client"] }
[features]
coconut = ["credentials/coconut"]
+1 -1
View File
@@ -3,7 +3,7 @@
use crate::error::Result; use crate::error::Result;
use bip39::Mnemonic; use bip39::Mnemonic;
use nym_network_defaults::{NymNetworkDetails, VOUCHER_INFO}; use network_defaults::{NymNetworkDetails, VOUCHER_INFO};
use std::str::FromStr; use std::str::FromStr;
use url::Url; use url::Url;
use validator_client::nyxd; use validator_client::nyxd;
+35 -87
View File
@@ -1,9 +1,8 @@
// Copyright 2022 - Nym Technologies SA <contact@nymtech.net> // Copyright 2022 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use clap::{ArgGroup, Args, Subcommand}; use clap::{Args, Subcommand};
use log::*; use completions::ArgShell;
use nym_bin_common::completions::ArgShell;
use rand::rngs::OsRng; use rand::rngs::OsRng;
use std::str::FromStr; use std::str::FromStr;
@@ -12,21 +11,18 @@ use credential_storage::storage::Storage;
use credential_storage::PersistentStorage; use credential_storage::PersistentStorage;
use credentials::coconut::bandwidth::{BandwidthVoucher, TOTAL_ATTRIBUTES}; use credentials::coconut::bandwidth::{BandwidthVoucher, TOTAL_ATTRIBUTES};
use credentials::coconut::utils::obtain_aggregate_signature; use credentials::coconut::utils::obtain_aggregate_signature;
use nym_crypto::asymmetric::{encryption, identity}; use crypto::asymmetric::{encryption, identity};
use nym_network_defaults::VOUCHER_INFO; use network_defaults::{NymNetworkDetails, VOUCHER_INFO};
use validator_client::nyxd::traits::DkgQueryClient;
use validator_client::nyxd::tx::Hash; use validator_client::nyxd::tx::Hash;
use validator_client::nyxd::CosmWasmClient; use validator_client::{CoconutApiClient, Config};
use validator_client::CoconutApiClient;
use crate::client::Client; use crate::client::Client;
use crate::error::{CredentialClientError, Result}; use crate::error::{CredentialClientError, Result};
use crate::recovery_storage::RecoveryStorage;
use crate::state::{KeyPair, State}; use crate::state::{KeyPair, State};
#[derive(Subcommand)] #[derive(Subcommand)]
pub(crate) enum Command { pub(crate) enum Command {
/// Run the binary to obtain a credential /// Run the binary
Run(Run), Run(Run),
/// Generate shell completions /// Generate shell completions
@@ -37,11 +33,6 @@ pub(crate) enum Command {
} }
#[derive(Args)] #[derive(Args)]
#[clap(group(
ArgGroup::new("recov")
.required(true)
.args(&["amount", "recovery_mode"]),
))]
pub(crate) struct Run { pub(crate) struct Run {
/// Home directory of the client that is supposed to use the credential. /// Home directory of the client that is supposed to use the credential.
#[clap(long)] #[clap(long)]
@@ -55,25 +46,15 @@ pub(crate) struct Run {
#[clap(long)] #[clap(long)]
pub(crate) mnemonic: String, pub(crate) mnemonic: String,
/// The amount of utokens the credential will hold. If recovery mode is enabled, this value /// The amount of utokens the credential will hold
/// is not needed #[clap(long)]
#[clap(long, default_value = "0")]
pub(crate) amount: u64, pub(crate) amount: u64,
/// Path to a directory used to store recovery files for unconsumed deposits
#[clap(long)]
pub(crate) recovery_dir: std::path::PathBuf,
/// Recovery mode, when enabled, tries to recover any deposit data dumped in recovery_dir
#[clap(long)]
pub(crate) recovery_mode: bool,
} }
pub(crate) async fn deposit(nyxd_url: &str, mnemonic: &str, amount: u64) -> Result<State> { pub(crate) async fn deposit(nyxd_url: &str, mnemonic: &str, amount: u64) -> Result<State> {
let mut rng = OsRng; let mut rng = OsRng;
let signing_keypair = KeyPair::from(identity::KeyPair::new(&mut rng)); let signing_keypair = KeyPair::from(identity::KeyPair::new(&mut rng));
let encryption_keypair = KeyPair::from(encryption::KeyPair::new(&mut rng)); let encryption_keypair = KeyPair::from(encryption::KeyPair::new(&mut rng));
let params = Parameters::new(TOTAL_ATTRIBUTES).unwrap();
let client = Client::new(nyxd_url, mnemonic); let client = Client::new(nyxd_url, mnemonic);
let tx_hash = client let tx_hash = client
@@ -85,81 +66,48 @@ pub(crate) async fn deposit(nyxd_url: &str, mnemonic: &str, amount: u64) -> Resu
) )
.await?; .await?;
let voucher = BandwidthVoucher::new( let state = State {
&params, amount,
amount.to_string(), tx_hash,
VOUCHER_INFO.to_string(), signing_keypair,
Hash::from_str(&tx_hash).map_err(|_| CredentialClientError::InvalidTxHash)?, encryption_keypair,
identity::PrivateKey::from_base58_string(&signing_keypair.private_key)?, };
encryption::PrivateKey::from_base58_string(&encryption_keypair.private_key)?,
);
let state = State { voucher, params };
Ok(state) Ok(state)
} }
pub(crate) async fn get_credential<C: Clone + CosmWasmClient + Send + Sync>( pub(crate) async fn get_credential(state: &State, shared_storage: PersistentStorage) -> Result<()> {
state: &State, let network_details = NymNetworkDetails::new_from_env();
client: validator_client::Client<C>, let config = Config::try_from_nym_network_details(&network_details)?;
shared_storage: PersistentStorage, let client = validator_client::Client::new_query(config)?;
) -> Result<()> { let coconut_api_clients = CoconutApiClient::all_coconut_api_clients(&client).await?;
let epoch_id = client.nyxd.get_current_epoch().await?.epoch_id;
let threshold = client let params = Parameters::new(TOTAL_ATTRIBUTES).unwrap();
.nyxd let bandwidth_credential_attributes = BandwidthVoucher::new(
.get_current_epoch_threshold() &params,
.await? state.amount.to_string(),
.ok_or(CredentialClientError::NoThreshold)?; VOUCHER_INFO.to_string(),
let coconut_api_clients = CoconutApiClient::all_coconut_api_clients(&client, epoch_id).await?; Hash::from_str(&state.tx_hash).map_err(|_| CredentialClientError::InvalidTxHash)?,
identity::PrivateKey::from_base58_string(&state.signing_keypair.private_key)?,
encryption::PrivateKey::from_base58_string(&state.encryption_keypair.private_key)?,
);
let signature = obtain_aggregate_signature( let signature = obtain_aggregate_signature(
&state.params, &params,
&state.voucher, &bandwidth_credential_attributes,
&coconut_api_clients, &coconut_api_clients,
threshold,
) )
.await?; .await?;
info!("Signature: {:?}", signature.to_bs58()); println!("Signature: {:?}", signature.to_bs58());
shared_storage shared_storage
.insert_coconut_credential( .insert_coconut_credential(
state.voucher.get_voucher_value(), state.amount.to_string(),
VOUCHER_INFO.to_string(), VOUCHER_INFO.to_string(),
state.voucher.get_private_attributes()[0].to_bs58(), bandwidth_credential_attributes.get_private_attributes()[0].to_bs58(),
state.voucher.get_private_attributes()[1].to_bs58(), bandwidth_credential_attributes.get_private_attributes()[1].to_bs58(),
signature.to_bs58(), signature.to_bs58(),
epoch_id.to_string(),
) )
.await?; .await?;
Ok(()) Ok(())
} }
pub(crate) async fn recover_credentials<C: Clone + CosmWasmClient + Send + Sync>(
client: validator_client::Client<C>,
recovery_storage: &RecoveryStorage,
shared_storage: PersistentStorage,
) -> Result<()> {
for voucher in recovery_storage.unconsumed_vouchers()? {
let state = State {
voucher,
params: Parameters::new(TOTAL_ATTRIBUTES).unwrap(),
};
if let Err(e) = get_credential(&state, client.clone(), shared_storage.clone()).await {
error!(
"Could not recover deposit {} due to {:?}, try again later",
state.voucher.tx_hash(),
e
)
} else {
info!(
"Converted deposit {} to a credential, removing recovery data for it",
state.voucher.tx_hash()
);
if let Err(e) = recovery_storage.remove_voucher(state.voucher.tx_hash().to_string()) {
warn!("Could not remove recovery data - {:?}", e);
}
}
}
Ok(())
}
+2 -12
View File
@@ -1,13 +1,12 @@
// Copyright 2022 - Nym Technologies SA <contact@nymtech.net> // Copyright 2022 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
use std::time::SystemTimeError;
use thiserror::Error; use thiserror::Error;
use credential_storage::error::StorageError; use credential_storage::error::StorageError;
use credentials::error::Error as CredentialError; use credentials::error::Error as CredentialError;
use nym_crypto::asymmetric::encryption::KeyRecoveryError; use crypto::asymmetric::encryption::KeyRecoveryError;
use nym_crypto::asymmetric::identity::Ed25519RecoveryError; use crypto::asymmetric::identity::Ed25519RecoveryError;
use validator_client::nyxd::error::NyxdError; use validator_client::nyxd::error::NyxdError;
use validator_client::ValidatorClientError; use validator_client::ValidatorClientError;
@@ -15,9 +14,6 @@ pub type Result<T> = std::result::Result<T, CredentialClientError>;
#[derive(Error, Debug)] #[derive(Error, Debug)]
pub enum CredentialClientError { pub enum CredentialClientError {
#[error("IO error: {0}")]
IOError(#[from] std::io::Error),
#[error("Nyxd error: {0}")] #[error("Nyxd error: {0}")]
Nyxd(#[from] NyxdError), Nyxd(#[from] NyxdError),
@@ -38,10 +34,4 @@ pub enum CredentialClientError {
#[error("Could not use shared storage")] #[error("Could not use shared storage")]
SharedStorageError(#[from] StorageError), SharedStorageError(#[from] StorageError),
#[error("Could not get system time")]
SysTimeError(#[from] SystemTimeError),
#[error("Threshold not set yet")]
NoThreshold,
} }
+40 -93
View File
@@ -1,109 +1,56 @@
// Copyright 2022 - Nym Technologies SA <contact@nymtech.net> // Copyright 2022 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: Apache-2.0
mod client; cfg_if::cfg_if! {
mod commands; if #[cfg(feature = "coconut")] {
mod error;
mod recovery_storage;
mod state;
use commands::*; mod client;
use error::Result; mod commands;
use log::*; mod error;
use nym_bin_common::completions::fig_generate; mod state;
use nym_config::{DATA_DIR, DB_FILE_NAME};
use nym_network_defaults::{setup_env, NymNetworkDetails};
use std::process::exit;
use std::time::{Duration, SystemTime};
use clap::{CommandFactory, Parser}; use error::Result;
use nym_bin_common::logging::setup_logging; use network_defaults::setup_env;
use validator_client::nyxd::traits::DkgQueryClient; use completions::fig_generate;
use validator_client::nyxd::CosmWasmClient; use commands::*;
use validator_client::Config; use config::{DATA_DIR, DB_FILE_NAME};
const SAFETY_BUFFER_SECS: u64 = 60; // 1 minute use clap::{CommandFactory, Parser};
#[derive(Parser)] #[derive(Parser)]
#[clap(author = "Nymtech", version, about)] #[clap(author = "Nymtech", version, about)]
struct Cli { struct Cli {
/// Path pointing to an env file that configures the client. /// Path pointing to an env file that configures the client.
#[clap(short, long)] #[clap(short, long)]
pub(crate) config_env_file: Option<std::path::PathBuf>, pub(crate) config_env_file: Option<std::path::PathBuf>,
#[clap(subcommand)] #[clap(subcommand)]
pub(crate) command: Command, pub(crate) command: Command,
}
async fn block_until_coconut_is_available<C: Clone + CosmWasmClient + Send + Sync>(
client: &validator_client::Client<C>,
) -> Result<()> {
loop {
let epoch = client.nyxd.get_current_epoch().await?;
let current_timestamp_secs = SystemTime::now()
.duration_since(SystemTime::UNIX_EPOCH)?
.as_secs();
if epoch.state.is_final() {
if current_timestamp_secs + SAFETY_BUFFER_SECS >= epoch.finish_timestamp.seconds() {
info!("In the next {} minute(s), a transition will take place in the coconut system. Deposits should be halted in this time for safety reasons.", SAFETY_BUFFER_SECS / 60);
exit(0);
}
break;
} else {
// Use 20 additional seconds to avoid the exact moment of going into the final epoch state
let secs_until_final = epoch.final_timestamp_secs() + 20 - current_timestamp_secs;
info!("Approximately {} seconds until coconut is available. Sleeping until then. You can safely kill the process at any moment.", secs_until_final);
std::thread::sleep(Duration::from_secs(secs_until_final));
} }
}
Ok(()) #[tokio::main]
} async fn main() -> Result<()> {
let args = Cli::parse();
setup_env(args.config_env_file.as_ref());
let bin_name = "nym-credential-client";
#[tokio::main] match args.command {
async fn main() -> Result<()> { Command::Run(r) => {
let args = Cli::parse(); let db_path = r.client_home_directory.join(DATA_DIR).join(DB_FILE_NAME);
setup_logging(); let shared_storage = credential_storage::initialise_storage(db_path).await;
setup_env(args.config_env_file.as_ref());
let bin_name = "nym-credential-client";
match args.command { let state = deposit(&r.nyxd_url, &r.mnemonic, r.amount).await?;
Command::Run(r) => { get_credential(&state, shared_storage).await?;
let db_path = r.client_home_directory.join(DATA_DIR).join(DB_FILE_NAME);
let shared_storage = credential_storage::initialise_storage(db_path).await;
let recovery_storage = recovery_storage::RecoveryStorage::new(r.recovery_dir)?;
let network_details = NymNetworkDetails::new_from_env();
let config = Config::try_from_nym_network_details(&network_details)?;
let client = validator_client::Client::new_query(config)?;
block_until_coconut_is_available(&client).await?;
info!("Starting depositing funds, don't kill the process");
if !r.recovery_mode {
let state = deposit(&r.nyxd_url, &r.mnemonic, r.amount).await?;
if get_credential(&state, client, shared_storage)
.await
.is_err()
{
warn!("Failed to obtain credential. Dumping recovery data.",);
match recovery_storage.insert_voucher(&state.voucher) {
Ok(file_path) => {
warn!("Dumped recovery data to {:?}. Try using recovery mode to convert it to a credential", file_path);
}
Err(e) => {
error!("Could not dump recovery data to file system due to {:?}, the deposit will be lost!", e)
}
}
} }
} else { Command::Completions(c) => c.generate(&mut crate::Cli::command(), bin_name),
recover_credentials(client, &recovery_storage, shared_storage).await?; Command::GenerateFigSpec => fig_generate(&mut crate::Cli::command(), bin_name)
} }
}
Command::Completions(c) => c.generate(&mut crate::Cli::command(), bin_name),
Command::GenerateFigSpec => fig_generate(&mut crate::Cli::command(), bin_name),
}
Ok(()) Ok(())
}
} else {
fn main() {
println!("Crate only designed for coconut feature");
}
}
} }
@@ -1,56 +0,0 @@
// Copyright 2023 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0
use credentials::coconut::bandwidth::BandwidthVoucher;
use std::fs::{create_dir_all, read_dir, File};
use std::io::{Read, Write};
use std::path::PathBuf;
pub struct RecoveryStorage {
recovery_dir: PathBuf,
}
impl RecoveryStorage {
pub fn new(recovery_dir: PathBuf) -> std::io::Result<Self> {
create_dir_all(&recovery_dir)?;
Ok(Self { recovery_dir })
}
pub fn unconsumed_vouchers(&self) -> std::io::Result<impl Iterator<Item = BandwidthVoucher>> {
Ok(read_dir(&self.recovery_dir)?
.filter_map(|entry| entry.ok())
.filter_map(|entry| {
let path = entry.path();
if path.is_file() {
Some(path)
} else {
None
}
})
.filter_map(|path| File::open(path).ok())
.filter_map(|mut f| {
let mut buff = Vec::new();
if f.read_to_end(&mut buff).is_ok() {
Some(buff)
} else {
None
}
})
.filter_map(|buff| BandwidthVoucher::try_from_bytes(&buff).ok()))
}
pub fn insert_voucher(&self, voucher: &BandwidthVoucher) -> std::io::Result<PathBuf> {
let file_name = voucher.tx_hash().to_string();
let file_path = self.recovery_dir.join(file_name);
let mut file = File::create(&file_path)?;
let buff = voucher.to_bytes();
file.write_all(&buff)?;
Ok(file_path)
}
pub fn remove_voucher(&self, file_name: String) -> std::io::Result<()> {
let file_path = self.recovery_dir.join(file_name);
std::fs::remove_file(file_path)
}
}

Some files were not shown because too many files have changed in this diff Show More