Skip to content
Open
9 changes: 5 additions & 4 deletions .github/workflows/backend-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,14 +11,14 @@ jobs:

strategy:
matrix:
node-version: [20]
node-version: [22]

steps:
- name: Checkout repository
uses: actions/checkout@v4
uses: actions/checkout@v5

- name: Setup Node.js
uses: actions/setup-node@v4
uses: actions/setup-node@v5
with:
node-version: ${{ matrix.node-version }}

Expand All @@ -27,7 +27,8 @@ jobs:
run: npm install --legacy-peer-deps

- name: Run backend unit tests
run: npm test --prefix stellar-payment-platform
working-directory: stellar-payment-platform
run: npm test

- name: Run memory leak detection tests (#511)
working-directory: stellar-payment-platform
Expand Down
9 changes: 4 additions & 5 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
name: Production Safety Checks

on:
push:
branches: [ "main" ]
Expand Down Expand Up @@ -46,16 +45,16 @@ jobs:
steps:
- name: Checkout Code
uses: actions/checkout@v4

- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: '22'
cache: 'npm'
cache-dependency-path: ./payment-dashboard/package-lock.json

- name: Install Frontend Dependencies
run: npm install --legacy-peer-deps

- name: Verify Vite Build (Catches Vercel Crashes)
run: npm run build
run: npm run build
14 changes: 3 additions & 11 deletions .github/workflows/rust-security.yml
Original file line number Diff line number Diff line change
@@ -1,47 +1,39 @@
name: Rust Security Checks

on:
push:
branches: [ main ]
pull_request:
branches: [ main ]

jobs:
security:
name: Static security analysis
runs-on: ubuntu-latest
defaults:
run:
working-directory: ./payment_router
env:
RUSTFLAGS: "-D warnings"
steps:
- name: Checkout
uses: actions/checkout@v4

uses: actions/checkout@v5
- name: Set up Rust toolchain
uses: dtolnay/rust-toolchain@stable
with:
components: clippy, rustfmt

- name: Verify formatting
run: |
cargo fmt --all -- --check

- name: Run clippy (deny warnings)
run: |
cargo clippy --all-targets --all-features -- -D warnings

- name: Install and run cargo-dylint
run: |
cargo install cargo-dylint --force || true
cargo dylint --all -- -D warnings
cargo dylint --all --all-targets --all-features -- -D warnings

- name: Install and run cargo-audit
run: |
cargo install cargo-audit --force || true
cargo audit --ignore RUSTSEC-2024-0344 --ignore RUSTSEC-2026-0009 --ignore RUSTSEC-2025-0056 --ignore RUSTSEC-2024-0436 --ignore RUSTSEC-2026-0097

- name: Run tests
- name: Run tests (release)
run: |
cargo test --all
19 changes: 7 additions & 12 deletions .github/workflows/soroban.yml
Original file line number Diff line number Diff line change
@@ -1,11 +1,8 @@
name: Soroban Contract CI

on:
name: Soroban Contract CI on:
push:
branches: [main]
pull_request:
branches: [main]

jobs:
contract-checks:
name: Contract Build & Test
Expand All @@ -15,23 +12,21 @@ jobs:
working-directory: ./payment_router
steps:
- name: Checkout Code
uses: actions/checkout@v4

uses: actions/checkout@v5
- name: Setup Rust toolchain
uses: dtolnay/rust-toolchain@stable
with:
targets: wasm32-unknown-unknown

- name: Cache cargo registry and build artifacts
uses: Swatinem/rust-cache@v2
with:
workspaces: ./payment_router

- name: Run contract tests
run: cargo test --verbose

run: cargo test --all-features --verbose
- name: Anomaly Detection
run: cargo test --all-features -- --ignored
- name: Build contract to WASM
run: cargo build --target wasm32-unknown-unknown --release
run: cargo build --all-features --target wasm32-unknown-unknown --release

coverage:
name: Coverage Report (cargo tarpaulin)
Expand Down Expand Up @@ -67,4 +62,4 @@ jobs:
uses: actions/upload-artifact@v4
with:
name: tarpaulin-coverage-report
path: payment_router/coverage/
path: payment_router/coverage/
15 changes: 15 additions & 0 deletions stellar-payment-platform/.env.example
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,21 @@ ADMIN_API_KEY="your-secure-admin-api-key-here"
# CORS_ALLOWED_ORIGINS="https://example.com,https://staging.example.com"
# VITE_API_BASE="https://api.yourdomain.com"

# --- Anomaly Monitor ----------------------------------------------------------
# Cron expression controlling how often the anomaly detection sweep runs.
# Defaults to every 15 minutes.
# ANOMALY_CRON="*/15 * * * *"

# Slack webhook URL to receive anomaly alerts. Left unset, no Slack alert is sent.
# ANOMALY_SLACK_WEBHOOK_URL="https://hooks.slack.com/services/..."

# Email webhook URL to receive anomaly alerts. Left unset, no email alert is sent.
# ANOMALY_EMAIL_WEBHOOK_URL="https://example.com/email-webhook"

# When "true", accounts flagged by the anomaly monitor are automatically
# soft-blocked (flaggedAt set). Defaults to disabled.
# ANOMALY_AUTO_PAUSE="false"

# --- JWT (RS256) --------------------------------------------------------------
# RSA key pair for signing and verifying JWTs.
# Generate with:
Expand Down
2 changes: 2 additions & 0 deletions stellar-payment-platform/server.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ const { prisma, isPrismaConnectionError } = require('./prismaClient');
const { scheduleCleanupJob } = require('./src/cleanup-cron');
const { scheduleSoftDeletePurgeJob } = require('./src/soft-delete-purge-cron');
const { schedulePoolMonitoring } = require('./src/db-pool-monitor');
const { scheduleAnomalyMonitor } = require('./src/scripts/anomalyMonitor');
const { correlationId } = require('./middleware/correlation');
const { idempotencyMiddleware } = require('./middleware/idempotency');
const Filter = require('bad-words');
Expand Down Expand Up @@ -266,6 +267,7 @@ app.use(compression({ threshold: 1024 }));
scheduleCleanupJob(prisma);
scheduleSoftDeletePurgeJob(prisma);
const poolMonitor = schedulePoolMonitoring(prisma);
scheduleAnomalyMonitor(prisma);

const RESERVED_USERNAMES = [
'admin',
Expand Down
Loading
Loading