Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 41 additions & 0 deletions .github/workflows/link-check.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
name: Link check

on:
pull_request:

# No write permissions needed — read-only check.
permissions:
contents: read

jobs:
check-links:
name: Check internal & external links
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Setup pnpm
uses: pnpm/action-setup@v4
with:
version: 10

- name: Setup Node
uses: actions/setup-node@v4
with:
node-version: 22
cache: pnpm

- name: Install dependencies
run: pnpm install --frozen-lockfile

- name: Run link checker
run: node scripts/check-links.mjs --report link-check-report.json

- name: Upload failure report
if: failure()
uses: actions/upload-artifact@v4
with:
name: link-check-report
path: link-check-report.json
retention-days: 14
28 changes: 28 additions & 0 deletions .github/workflows/snippets.yml
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,34 @@ jobs:
- name: Check extended snippets (Rust / Python / shell / JSON / TOML / YAML)
run: pnpm run check:snippets-extended

# ── Export path verification ────────────────────────────────────────────────
# Enumerates every import path and named symbol documented in the MDX files,
# then confirms each one exists in @wraith-protocol/sdk for both ESM and CJS.
# Fails the PR if docs and package exports diverge.
check-exports:
name: Verify documented SDK export paths (ESM + CJS)
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Setup pnpm
uses: pnpm/action-setup@v4
with:
version: 10

- name: Setup Node
uses: actions/setup-node@v4
with:
node-version: 22
cache: pnpm

- name: Install dependencies
run: pnpm install --frozen-lockfile

- name: Check documented export paths
run: pnpm run check:exports

stellar-testnet-snippets:
name: Stellar snippet testnet validation
runs-on: ubuntu-latest
Expand Down
31 changes: 31 additions & 0 deletions guides/quickstarts/python.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -636,6 +636,29 @@ announcer contract.
```python no-check
from wraith_crypto import decode_meta_address, generate_stealth_address

# ── Test fixture ────────────────────────────────────────────────────────────────
# This meta-address is deterministically derived from:
# spendingPubKey = ed25519 pubkey of SHA-256("wraith:spending:demo")
# viewingPubKey = ed25519 pubkey of SHA-256("wraith:viewing:demo")
#
# It matches the fixtures in scripts/playground/scanner.js and
# scripts/playground/generate-fixtures.mjs — you can verify those values
# independently by running: node scripts/playground/generate-fixtures.mjs
#
# ── Production ──────────────────────────────────────────────────────────────────
# Replace RECIPIENT_META_ADDRESS with the real recipient's meta-address.
# Sources in increasing order of convenience:
# 1. Wraith Names contract: GET /agent/info/{name}.wraith → metaAddress
# 2. Passed out-of-band (QR code, URL param, user input)
# 3. Your own agent's metaAddresses[Chain.Stellar] after createAgent()
# Never hardcode a production meta-address in source control.
# ───────────────────────────────────────────────────────────────────────────────

RECIPIENT_META_ADDRESS = (
"st:xlm:"
"45e84a059a47ee5d6fb721dcdbb31cecd928161e24b1e789e85d1e0510c99e86" # spendingPubKey
"d25639f6da0834e32d912626fd59d01e79a126ff10a59d034d2e46124e1ca791" # viewingPubKey
)
# The recipient shares their meta-address — either directly or via a .wraith name.
# For this quickstart we use a literal; in production resolve it from the names contract.
RECIPIENT_META_ADDRESS = "st:xlm:<spending_hex><viewing_hex>"
Expand All @@ -648,6 +671,14 @@ print("Ephemeral pub key: ", stealth.ephemeral_pub_key.hex())
print("View tag: ", stealth.view_tag)
```

<Info>
The meta-address above is a **test fixture** derived from well-known demo seeds.
Any `generate_stealth_address` call against it produces a valid, scannable
stealth address — but these keys are public, so never send real funds to them.
Swap in a real meta-address (from the Wraith Names contract or shared
out-of-band) before going to production.
</Info>

### 6b — Fund the stealth address and call the announcer

New Stellar accounts must be activated with `createAccount`. After activation, call
Expand Down
3 changes: 2 additions & 1 deletion guides/stellar-troubleshooting.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,7 @@ const tx = new StellarSdk.TransactionBuilder(account, { fee: "100" })

## Soroban Contract Errors

### 17. `HostError: Error(Contract, #)` / Contract Trapped {#17-hostError-contract-trapped}
### 17. `HostError: Error(Contract, #)` / Contract Trapped {#17-hosterror-errorcontract-n-contract-trapped}
**Meaning**: The smart contract executed a `panic!` or returned a specific error code.
**Cause**: A contract assertion failed (e.g., unauthorized caller, arithmetic overflow).
Expand All @@ -269,7 +270,7 @@ pub enum Error {
// If you see Error(Contract, 2), it's InsufficientBalance.
```

### 18. `op_no_trust` / Missing Trustline
### 18. `op_no_trust` / Missing Trustline {#18-op_no_trust--missing-trustline}
**Meaning**: The Soroban contract attempted to send a Classic asset (like USDC) to an account that doesn't trust it.
**Cause**: The recipient has not established a trustline for the asset being sent by the contract.
**Fix**: Have the recipient submit a `ChangeTrust` operation for the asset before invoking the contract.
Expand Down
2 changes: 1 addition & 1 deletion guides/stellar/stellar-liquidity-pool-swap.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@ const swapTx = new TransactionBuilder(senderAccount, {
.build();
```

> **Important:** Classic path payment operations do not call the `stealth-sender` contract. No announcement event is emitted. You need a separate announcement transaction for the recipient to detect the payment. See [Swap + Announce](#swap--announce) below.
> **Important:** Classic path payment operations do not call the `stealth-sender` contract. No announcement event is emitted. You need a separate announcement transaction for the recipient to detect the payment. See [Swap + Announce](#swap-announce) below.

### Forcing a Pool Route

Expand Down
4 changes: 2 additions & 2 deletions guides/stellar/stellar-quickstart.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -285,7 +285,7 @@ console.log(res.response);

---

## 7. Send a Stealth Payment
## 7. Send a Stealth Payment {#send-a-stealth-payment}

Send USDC to any `.wraith` name. The agent resolves the name to a stealth meta-address, generates a fresh one-time stealth address, and broadcasts the announcement on-chain — all in a single Soroban transaction.

Expand Down Expand Up @@ -391,7 +391,7 @@ You don't need to call these functions directly — the managed agent does it fo

---

## 9. Withdraw to Your Wallet
## 9. Withdraw to Your Wallet {#withdraw-to-your-wallet}

Move funds from stealth addresses to your regular Stellar wallet. The agent warns about privacy tradeoffs before executing:

Expand Down
135 changes: 135 additions & 0 deletions link-exceptions.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
# link-exceptions.yaml
#
# External URLs and known-missing internal paths that the link checker should skip.
#
# Add an entry here when:
# - An external URL is valid but returns 4xx/5xx in CI because the host
# rate-limits crawlers, requires auth, or is behind bot-protection.
# - An internal page is intentionally not yet written (stub / future doc).
# - A URL is a placeholder or example value in prose (not a real link).
#
# Each entry MUST include:
# url – exact URL or URL prefix to skip (string)
# reason – why this exception exists
# owner – GitHub handle of the person who added it
# added – ISO date the exception was added
#
# Review and prune stale entries every quarter.

exceptions:
# ── Social / bot-blocked hosts ─────────────────────────────────────────────

- url: https://twitter.com
reason: Twitter/X returns 403 to all non-browser user-agents.
owner: "@maintainer"
added: "2026-09-25"

- url: https://x.com
reason: Same as twitter.com — bot-protection returns 403.
owner: "@maintainer"
added: "2026-09-25"

- url: https://www.linkedin.com
reason: LinkedIn blocks all crawler user-agents.
owner: "@maintainer"
added: "2026-09-25"

# ── Placeholder / example URLs in prose ───────────────────────────────────

- url: https://pay.wraith.dev
reason: >
Placeholder domain used as an illustrative example in prose.
Not a real endpoint; will be replaced or removed when the feature ships.
owner: "@maintainer"
added: "2026-09-25"

- url: https://usewraith.xyz/pricing
reason: Page not yet published; planned for mainnet launch.
owner: "@maintainer"
added: "2026-09-25"

- url: https://usewraith.xyz/.well-known/security.txt
reason: >
security.txt not yet deployed to production host.
Will be removed once the file is live.
owner: "@maintainer"
added: "2026-09-25"

- url: https://docs.usewraith.xyz/reference/auditor-guide
reason: >
Docs site not yet deployed; link in SECURITY.md points to the future
production URL. Remove exception once the site is live.
owner: "@maintainer"
added: "2026-09-25"

# ── External sites that block CI crawlers ──────────────────────────────────

- url: https://stellarbeat.io
reason: Returns connection errors / blocks non-browser agents in CI.
owner: "@maintainer"
added: "2026-09-25"

- url: https://phoenix-hub.org
reason: Site returns network errors in CI; confirmed reachable in browser.
owner: "@maintainer"
added: "2026-09-25"

- url: https://github.com/stellar/go/tree/master/services/federation
reason: >
GitHub tree-view URLs return 404 to HEAD requests from CI.
The repository and path are valid; this is a GitHub crawler quirk.
owner: "@maintainer"
added: "2026-09-25"

- url: https://developers.stellar.org
reason: >
Stellar developer docs return 404 on some deep paths via HEAD from CI.
URLs are valid in a browser; crawler-blocking behaviour.
owner: "@maintainer"
added: "2026-09-25"

# ── Known stub / not-yet-written internal pages ────────────────────────────
# These are internal links that reference pages planned but not yet created.
# Prefix with "internal:" to distinguish from HTTP exceptions.

- url: internal:/reference/stellar-event-schemas
reason: >
Page planned but not yet written. Referenced by multiple guides.
Remove this exception when the page is created.
owner: "@maintainer"
added: "2026-09-25"

- url: internal:/sdk/stellar-react-hooks
reason: React hooks SDK page not yet authored. Tracked as a docs gap.
owner: "@maintainer"
added: "2026-09-25"

- url: internal:/reference/error-codes
reason: >
Error codes reference page exists on the target branch but not in this
branch. All links to it (including anchors) are suppressed until the
page is merged here.
owner: "@maintainer"
added: "2026-09-25"

- url: internal:/guides/ops/monitoring-and-on-call
reason: >
monitoring-and-on-call.mdx is not yet authored in this branch.
Referenced by guides that will link to it once the page exists.
owner: "@maintainer"
added: "2026-09-25"

- url: internal:/guides/integrations/phoenix
reason: >
phoenix.mdx not yet present in this branch. Contains links to anchors
in sdk/chains/stellar and reference/auditor-guide that are valid once
the page is merged.
owner: "@maintainer"
added: "2026-09-25"

- url: internal:/guides/my-guide
reason: >
Placeholder link used in docs/i18n.md as an illustrative example.
Not a real page; intentional.
owner: "@maintainer"
added: "2026-09-25"
3 changes: 3 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
"check:snippets": "tsx scripts/check-snippets.ts",
"check:snippets-extended": "tsx scripts/check-snippets-extended.ts",
"check:nav-coverage": "node scripts/check-nav-coverage.mjs",
"check:exports": "tsx scripts/check-exports.ts",
"check:contract-registry": "node scripts/check-contract-registry.mjs",
"check:compatibility-matrix": "node scripts/check-compatibility-matrix.mjs",
"check:redirects-and-anchors": "node scripts/check-redirects-and-anchors.mjs",
Expand All @@ -20,6 +21,8 @@
"test:playground": "playwright test --config scripts/playground/tests/playwright.config.ts",
"mint:validate": "mint validate",
"mint:broken-links": "mint broken-links",
"check:links": "node scripts/check-links.mjs",
"test": "npm run check:snippets && npm run check:nav-coverage && npm run check:exports"
"test": "npm run check:snippets && npm run check:nav-coverage && npm run check:contract-registry && npm run check:compatibility-matrix && npm run test:redirects-and-anchors"
},
"dependencies": {
Expand Down
4 changes: 2 additions & 2 deletions reference/auditor-guide.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ description: "Start here to file a security finding against Wraith Protocol —

This is the on-ramp for security researchers who want to actually file a finding against Wraith Protocol. It assumes you can read TypeScript and are comfortable with smart-contract or TEE threat modeling, but it does **not** assume you have read everything else first.

If you just want to report a bug, jump to [Submitting a Report](#submitting-a-report). If you want to reproduce something first, start with the [PoC Template](#poc-repository-template).
If you just want to report a bug, jump to [Submitting a Report](#7-submitting-a-report). If you want to reproduce something first, start with the [PoC Template](#5-poc-repository-template).

<Note>
This guide is the companion to the [Security Disclosure Policy](/reference/security-disclosure) and the [Threat Model](/reference/threat-model). Read those two before submitting a formal report — they define scope, safe harbor, and the full STRIDE analysis that your finding should map onto.
Expand Down Expand Up @@ -137,7 +137,7 @@ Include:
- The affected component(s) and version or commit hash.
- The threat-model ID(s) your finding relates to (e.g. `E-15`, `R-01`).
- Steps to reproduce, as minimal as possible.
- Your proof of concept (link the repo from [Section 5](#poc-repository-template)).
- Your proof of concept (link the repo from [Section 5](#5-poc-repository-template)).
- Your severity assessment and why.
- Suggested fix or mitigation, if you have one.
- Whether you want public credit, and what name to use.
Expand Down
Loading
Loading