Skip to content
Merged
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
5 changes: 5 additions & 0 deletions .changeset/awn-rust-cli.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@resciencelab/agent-world-network": minor
---

Add standalone Rust CLI binary (`awn`) for agent-native AWN interface: Ed25519 crypto (wire-compatible with TS SDK), identity persistence, peer DB with TOFU, IPC daemon with axum, clap CLI with --json dual output, SKILL.md for agent discovery
5 changes: 5 additions & 0 deletions .changeset/beige-nights-jam.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@resciencelab/agent-world-network": minor
---

Rename peer terminology to agent/world across codebase; split world records into dedicated WorldDb and gateway world registry with worldId-as-protocol-identity model and human-readable slug field
169 changes: 169 additions & 0 deletions .github/workflows/release-cli.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,169 @@
name: Release CLI

on:
release:
types: [published]
workflow_dispatch:

permissions:
contents: write

jobs:
build:
name: Build ${{ matrix.target }}
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
include:
- target: x86_64-unknown-linux-gnu
os: ubuntu-latest
archive: tar.gz
- target: x86_64-apple-darwin
os: macos-latest
archive: tar.gz
- target: aarch64-apple-darwin
os: macos-latest
archive: tar.gz

steps:
- uses: actions/checkout@v6

- uses: dtolnay/rust-toolchain@stable
with:
targets: ${{ matrix.target }}

- uses: Swatinem/rust-cache@v2
with:
workspaces: packages/awn-cli

- name: Build
run: cargo build --release --manifest-path packages/awn-cli/Cargo.toml --target ${{ matrix.target }}

- name: Build .deb package (Linux only)
if: matrix.target == 'x86_64-unknown-linux-gnu'
run: |
cargo install cargo-deb
cargo deb --manifest-path packages/awn-cli/Cargo.toml --target ${{ matrix.target }} --no-build
cp packages/awn-cli/target/${{ matrix.target }}/debian/*.deb dist/ 2>/dev/null || true

- name: Package
shell: bash
run: |
VERSION=$(grep '^version' packages/awn-cli/Cargo.toml | head -1 | sed 's/.*"\(.*\)"/\1/')
ARCHIVE_NAME="awn-v${VERSION}-${{ matrix.target }}"
mkdir -p "dist/${ARCHIVE_NAME}"
cp "packages/awn-cli/target/${{ matrix.target }}/release/awn" "dist/${ARCHIVE_NAME}/"
cp packages/awn-cli/skills/SKILL.md "dist/${ARCHIVE_NAME}/"
cd dist
tar czf "${ARCHIVE_NAME}.tar.gz" "${ARCHIVE_NAME}"
echo "ARCHIVE=${ARCHIVE_NAME}.tar.gz" >> "$GITHUB_ENV"

- name: Upload artifact
uses: actions/upload-artifact@v4
with:
name: awn-${{ matrix.target }}
path: |
dist/${{ env.ARCHIVE }}
dist/*.deb

upload:
name: Upload to Release
needs: build
runs-on: ubuntu-latest
if: github.event_name == 'release'
steps:
- uses: actions/download-artifact@v4
with:
path: artifacts
merge-multiple: true

- name: Upload release assets
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
for f in artifacts/*.tar.gz artifacts/*.deb; do
[ -f "$f" ] || continue
echo "Uploading $f"
gh release upload "${{ github.event.release.tag_name }}" "$f" \
--repo "${{ github.repository }}" \
--clobber
done

homebrew:
name: Update Homebrew formula
needs: upload
runs-on: ubuntu-latest
if: github.event_name == 'release'
steps:
- uses: actions/checkout@v6

- name: Generate Homebrew formula
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
TAG="${{ github.event.release.tag_name }}"
VERSION="${TAG#v}"
REPO="${{ github.repository }}"
BASE_URL="https://github.com/${REPO}/releases/download/${TAG}"

URL_DARWIN_ARM64="${BASE_URL}/awn-v${VERSION}-aarch64-apple-darwin.tar.gz"
URL_DARWIN_X64="${BASE_URL}/awn-v${VERSION}-x86_64-apple-darwin.tar.gz"
URL_LINUX_X64="${BASE_URL}/awn-v${VERSION}-x86_64-unknown-linux-gnu.tar.gz"

# Download archives and compute SHA256
for target in aarch64-apple-darwin x86_64-apple-darwin x86_64-unknown-linux-gnu; do
url="${BASE_URL}/awn-v${VERSION}-${target}.tar.gz"
curl -sL "$url" -o "/tmp/awn-${target}.tar.gz"
done

SHA_DARWIN_ARM64=$(sha256sum /tmp/awn-aarch64-apple-darwin.tar.gz | cut -d' ' -f1)
SHA_DARWIN_X64=$(sha256sum /tmp/awn-x86_64-apple-darwin.tar.gz | cut -d' ' -f1)
SHA_LINUX_X64=$(sha256sum /tmp/awn-x86_64-unknown-linux-gnu.tar.gz | cut -d' ' -f1)

mkdir -p Formula
cat > Formula/awn.rb <<FORMULA
class Awn < Formula
desc "Agent World Network CLI — world-scoped P2P messaging for AI agents"
homepage "https://github.com/${REPO}"
version "${VERSION}"
license "MIT"

on_macos do
if Hardware::CPU.arm?
url "${URL_DARWIN_ARM64}"
sha256 "${SHA_DARWIN_ARM64}"
else
url "${URL_DARWIN_X64}"
sha256 "${SHA_DARWIN_X64}"
end
end

on_linux do
url "${URL_LINUX_X64}"
sha256 "${SHA_LINUX_X64}"
end

def install
bin.install "awn"
end

test do
assert_match "awn", shell_output("#{bin}/awn --version")
end
end
FORMULA
# Remove leading whitespace from heredoc
sed -i 's/^ //' Formula/awn.rb

- name: Commit formula
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
git checkout main
git add Formula/awn.rb
git diff --cached --quiet && echo "No formula changes" && exit 0
git commit -m "chore(brew): update Homebrew formula to ${{ github.event.release.tag_name }}"
git push origin main
12 changes: 12 additions & 0 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -33,3 +33,15 @@ jobs:
run: npm --prefix packages/agent-world-sdk run build
- if: "!startsWith(github.head_ref, 'changeset-release/')"
run: node --test test/*.test.mjs

test-rust:
name: test (awn-cli)
runs-on: ubuntu-latest
if: "!startsWith(github.head_ref, 'changeset-release/')"
steps:
- uses: actions/checkout@v6
- uses: dtolnay/rust-toolchain@stable
- uses: Swatinem/rust-cache@v2
with:
workspaces: packages/awn-cli
- run: cargo test --manifest-path packages/awn-cli/Cargo.toml
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -31,3 +31,4 @@ animation/out/
.hal/*
!.hal/standards/
!.hal/commands/
packages/awn-cli/target/
5 changes: 4 additions & 1 deletion AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -192,8 +192,9 @@ No manual version bumping, no release scripts, no backmerge.
| Workflow | Trigger | What it does |
|---|---|---|
| `release.yml` | Push to `main`, `workflow_dispatch` | Changesets: create Version PR or publish npm + GH Release + ClawHub |
| `release-cli.yml` | GH Release published, `workflow_dispatch` | Cross-compile Rust `awn` binary (linux-x64, darwin-x64, darwin-arm64), attach to release |
| `publish.yml` | `workflow_dispatch` only | Emergency manual npm publish |
| `test.yml` | Push/PR to `main`, `workflow_dispatch` | Build + test (Node 20+22) |
| `test.yml` | Push/PR to `main`, `workflow_dispatch` | Build + test (Node 20+22) + Rust cargo test |
| `changeset-check.yml` | PR to `main` | Ensure changeset present + validate packages |
| `auto-close-issues.yml` | PR merged | Close linked issues |

Expand Down Expand Up @@ -235,6 +236,7 @@ No `develop` branch. No backmerge.
| `package-lock.json` | `"version"` (auto-updated) |
| `openclaw.plugin.json` | `"version"` |
| `skills/awn/SKILL.md` | `version:` in YAML frontmatter |
| `packages/awn-cli/Cargo.toml` | `version` (also derives `PROTOCOL_VERSION` at compile time) |

### Versioning

Expand Down Expand Up @@ -276,6 +278,7 @@ These files must always have matching versions (synced automatically by `scripts
| `package-lock.json` | `"version"` (auto-updated by `npm version`) |
| `openclaw.plugin.json` | `"version"` |
| `skills/awn/SKILL.md` | `version:` in YAML frontmatter |
| `packages/awn-cli/Cargo.toml` | `version` (also derives `PROTOCOL_VERSION` at compile time) |

### Versioning

Expand Down
17 changes: 8 additions & 9 deletions gateway/schemas.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,8 @@ export const EndpointSchema = {
},
}

export const PeerRecordSchema = {
$id: "PeerRecord",
export const AgentRecordSchema = {
$id: "AgentRecord",
type: "object",
required: ["agentId", "publicKey", "alias", "endpoints", "capabilities", "lastSeen"],
properties: {
Expand All @@ -40,11 +40,10 @@ export const PeerRecordSchema = {
export const WorldSummarySchema = {
$id: "WorldSummary",
type: "object",
required: ["worldId", "agentId", "name", "endpoints", "reachable", "lastSeen"],
required: ["worldId", "endpoints", "reachable", "lastSeen"],
properties: {
worldId: { type: "string" },
agentId: { type: "string" },
name: { type: "string" },
slug: { type: "string" },
endpoints: { type: "array", items: { $ref: "Endpoint#" } },
reachable: { type: "boolean" },
lastSeen: { type: "integer" },
Expand All @@ -54,12 +53,11 @@ export const WorldSummarySchema = {
export const WorldDetailSchema = {
$id: "WorldDetail",
type: "object",
required: ["worldId", "agentId", "publicKey", "name", "endpoints", "reachable", "subscribers", "lastSeen"],
required: ["worldId", "publicKey", "endpoints", "reachable", "subscribers", "lastSeen"],
properties: {
worldId: { type: "string" },
agentId: { type: "string" },
slug: { type: "string" },
publicKey: { type: "string" },
name: { type: "string" },
endpoints: { type: "array", items: { $ref: "Endpoint#" } },
reachable: { type: "boolean" },
subscribers: { type: "integer", description: "Number of active WebSocket subscribers" },
Expand All @@ -75,6 +73,7 @@ export const AnnounceRequestSchema = {
from: { type: "string", description: "aw:sha256:{hex} agent identifier" },
publicKey: { type: "string", description: "Base64-encoded Ed25519 public key" },
alias: { type: "string" },
slug: { type: "string", description: "Optional human-friendly world label for world servers" },
version: { type: "string", default: "1.0.0" },
endpoints: { type: "array", items: { $ref: "Endpoint#" } },
capabilities: { type: "array", items: { type: "string" } },
Expand Down Expand Up @@ -110,7 +109,7 @@ export const SignedMessageSchema = {
export const allSchemas = [
ErrorSchema,
EndpointSchema,
PeerRecordSchema,
AgentRecordSchema,
WorldSummarySchema,
WorldDetailSchema,
AnnounceRequestSchema,
Expand Down
Loading