skills-templates/data-services/weavedb/SKILL.md
Decentralized database protocol with zero-knowledge proofs and permanent storage on Arweave
npx skillsauth add enuno/claude-command-and-control weavedbInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Comprehensive assistance with WeaveDB - a decentralized database protocol built on Arweave with zero-knowledge proofs, permanent storage, and configuration-driven design.
This skill should be triggered when:
npx wdb-cli create mydb && cd mydb
import { DB } from "wdb-sdk"
import { mem } from "wdb-core"
const { q } = mem()
const db = new DB({ jwk: acc[0].jwk, hb: null, mem: q })
// Initialize database
const id = await db.init({ id: "mydb" })
// Create collection with schema
await db.mkdir({
name: "users",
schema: { type: "object", required: ["name", "age"] },
auth: [["set:user,del:user", [["allow()"]]]],
})
// Create
await db.set("set:user", { name: "Bob", age: 20 }, "users", "Bob")
// Read (single document)
const user = await db.get("users", "Bob")
// Read (all documents, sorted)
const users = await db.get("users", ["age", "desc"])
// Read (with limit)
const topUsers = await db.get("users", ["age", "asc"], 2)
// Read (with query)
const thirtyYearOlds = await db.get("users", ["age", "==", 30])
// Delete
await db.set("del:user", "users", "Bob")
# Clone HyperBEAM
git clone -b weavedb https://github.com/weavedb/HyperBEAM.git
cd HyperBEAM
# Start node
yarn start
# Deploy database (in separate terminal)
cd mydb
yarn deploy --wallet .wallet.json
Example 1 - In-Memory Testing (javascript):
import assert from "assert"
import { describe, it } from "node:test"
import { acc } from "wao/test"
import { DB } from "wdb-sdk"
import { mem } from "wdb-core"
describe("Basic API", () => {
it("should query DB", async () => {
const { q } = mem()
const db = new DB({ jwk: acc[0].jwk, hb: null, mem: q })
const id = await db.init({ id: "mydb" })
await db.mkdir({
name: "users",
schema: { type: "object", required: ["name", "age"] },
auth: [["set:user,del:user", [["allow()"]]]],
})
await db.set("set:user", { name: "Bob", age: 20 }, "users", "Bob")
const user = await db.get("users", "Bob")
assert.deepEqual(user, { name: "Bob", age: 20 })
})
})
Example 2 - Schema Definition (javascript):
// /db/schema.js
export default {
notes: {
type: "object",
required: ["id", "actor", "content", "published", "likes"],
properties: {
id: { type: "string" },
actor: { type: "string", pattern: "^[a-zA-Z0-9_-]{43}$" },
content: { type: "string", minLength: 1, maxLength: 140 },
published: { type: "integer" },
likes: { type: "integer" },
},
additionalProperties: false,
},
}
Example 3 - Authentication Rules (javascript):
// /db/auth.js
export default {
notes: [
[
"add:note",
[
["fields()", ["*content"]],
["mod()", { id: "$doc", actor: "$signer", published: "$ts", likes: 0 }],
["allow()"],
],
],
],
}
Example 4 - Database Triggers (javascript):
// /db/triggers.js
export default {
likes: [
{
key: "inc_likes",
on: "create",
fn: [
["update()", [{ likes: { _$: ["inc"] } }, "notes", "$after.object"]],
],
},
],
}
Example 5 - Frontend Integration (Next.js) (javascript):
import { useRef, useEffect, useState } from "react"
import { DB } from "wdb-sdk"
export default function Home() {
const [notes, setNotes] = useState([])
const db = useRef()
const getNotes = async () => {
const _notes = await db.current.cget("notes", ["published", "desc"], 10)
setNotes(_notes)
}
const handlePost = async (content) => {
if (window.arweaveWallet) {
await window.arweaveWallet.connect(["ACCESS_ADDRESS", "SIGN_TRANSACTION"])
}
const res = await db.current.set("add:note", { content }, "notes")
if (res.success) {
await getNotes()
}
}
useEffect(() => {
void (async () => {
db.current = new DB({
id: process.env.NEXT_PUBLIC_DB_ID,
url: process.env.NEXT_PUBLIC_RU_URL,
})
await getNotes()
})()
}, [])
return (
// UI components...
)
}
Example 6 - Package Installation (bash):
# For Node.js projects
yarn add wdb-sdk
# Or with npm
npm install wdb-sdk
# For testing utilities
yarn add arjson wao
This skill includes comprehensive documentation in references/:
Use view to read specific reference files when detailed information is needed.
Create a new project:
npx wdb-cli create mydb && cd mydb
Run tests to verify setup:
yarn test-all
Deploy locally:
yarn start
yarn deploy --wallet .wallet.json
Access explorer:
cd ../weavedb/scan && yarn && yarn dev --port 4000
Follow the complete social dapp tutorial in the quick-start guide:
yarn deploy with walletThe quick reference section above contains practical patterns extracted from the official quick-start guide, including:
Organized documentation extracted from official sources. These files contain:
Add helper scripts here for common automation tasks like:
Add templates, boilerplate, or example projects here:
WeaveDB leverages several powerful patterns:
add:note, del:user for fine-grained access controlRun the complete test suite:
yarn test-all
Write tests using Node.js test framework:
import { describe, it } from "node:test"
import assert from "assert"
import { DB } from "wdb-sdk"
import { mem } from "wdb-core"
describe("My Feature", () => {
it("should work correctly", async () => {
const { q } = mem()
const db = new DB({ jwk: acc[0].jwk, hb: null, mem: q })
// Your test logic...
})
})
WeaveDB integrates with WAO (Weave Arweave Oasis) - a testing framework providing 1000x faster in-memory emulation for Arweave and AO development.
import { DB } from "wdb-sdk"
import { mem } from "wdb-core" // ArMem-based in-memory emulator
// Initialize ArMem-backed database (1000x faster than mainnet)
const { q } = mem() // q is the ArMem query interface
const db = new DB({
jwk: testAccount.jwk,
hb: null, // No HyperBEAM node required
mem: q // Use in-memory emulation
})
// Run tests at full speed
await db.init({ id: "test-db" })
await db.mkdir({ name: "users", schema: userSchema })
await db.add({ name: "Alice", age: 30 }, "users")
// No network latency, instant results
const users = await db.get("users")
assert.equal(users.length, 1)
import { HyperBEAM } from "wao-js-sdk"
// Start local HyperBEAM node for production-like testing
const hb = new HyperBEAM({
port: 3000,
as: ["genesis_wasm"], // Enable WASM runtime
autostart: true
})
await hb.start()
// Connect WeaveDB to HyperBEAM
const db = new DB({
jwk: testAccount.jwk,
hb: hb.getClient(),
mem: null // Use HyperBEAM instead of mem
})
// Test with realistic node environment
await db.init({ id: "production-test-db" })
// Cleanup
await hb.stop()
| Test Environment | Speed | Use Case | |------------------|-------|----------| | ArMem (mem()) | 1000x faster | Unit tests, rapid iteration | | HyperBEAM Local | 100x faster | Integration tests, production-like | | arlocal | 10x faster | Legacy compatibility | | Mainnet | 1x (baseline) | Final validation |
import { describe, it } from "node:test"
import { DB } from "wdb-sdk"
import { mem } from "wdb-core"
describe("WeaveDB Snapshot Tests", () => {
let db, q
beforeEach(async () => {
// Fresh ArMem instance per test
({ q } = mem())
db = new DB({ jwk: acc[0].jwk, hb: null, mem: q })
await db.init({ id: "snapshot-test" })
})
it("should match data snapshot", async () => {
await db.mkdir({ name: "posts", schema: postSchema })
await db.add({ title: "Post 1", content: "..." }, "posts")
const snapshot = await q.getSnapshot() // ArMem snapshot
assert.deepEqual(snapshot.collections.posts.length, 1)
})
it("should restore from snapshot", async () => {
const savedSnapshot = { /* previous state */ }
await q.loadSnapshot(savedSnapshot) // Restore state
const posts = await db.get("posts")
assert.equal(posts.length, 0) // Fresh state
})
})
// Test authorization without network delays
it("should enforce auth rules", async () => {
const { q } = mem()
const ownerDb = new DB({ jwk: owner.jwk, hb: null, mem: q })
const attackerDb = new DB({ jwk: attacker.jwk, hb: null, mem: q })
await ownerDb.init({ id: "auth-test" })
await ownerDb.mkdir({
name: "private_docs",
auth: [["set:doc", [
["equals()", "$signer", owner.address], // Only owner can write
["allow()"]
]]]
})
// Owner can write (instant test)
const { err: err1 } = await ownerDb.add({ secret: "data" }, "private_docs")
assert.equal(err1, null)
// Attacker cannot write (instant test)
const { err: err2 } = await attackerDb.add({ hack: "attempt" }, "private_docs")
assert.notEqual(err2, null)
assert.match(err2.message, /permission denied/i)
})
// Run 100 tests in parallel with independent ArMem instances
const testPromises = Array.from({ length: 100 }, async (_, i) => {
const { q } = mem() // Each test gets isolated memory
const db = new DB({ jwk: acc[i % 5].jwk, hb: null, mem: q })
await db.init({ id: `test-${i}` })
await db.mkdir({ name: "items", schema: itemSchema })
await db.add({ id: i, value: Math.random() }, "items")
const items = await db.get("items")
assert.equal(items.length, 1)
})
// All tests complete in < 1 second (vs minutes on mainnet)
await Promise.all(testPromises)
# Start WAO Hub for visual debugging
npx wao-hub
# Open http://localhost:8080
# - View ArMem state in real-time
# - Inspect message history
# - Monitor query performance
# - Debug auth rule failures
// ❌ Avoid: Allowing unrestricted access
auth: [["set:user", [["allow()"]]]]
// ✅ Better: Require wallet authentication
auth: [["set:user", [
["equals()", "$signer", "$doc.owner"],
["allow()"]
]]]
// ✅ Best: Multi-layered validation
auth: [["set:user", [
["equals()", "$signer", "$doc.owner"],
["gte()", "$now", "$doc.createdAt"],
["fields()", ["*password", "*privateKey"]], // Exclude sensitive fields
["allow()"]
]]]
// Use strict JSON Schema validation
const userSchema = {
type: "object",
required: ["id", "address", "username"],
properties: {
id: { type: "string", pattern: "^[a-zA-Z0-9]{20}$" },
address: { type: "string", pattern: "^[a-zA-Z0-9_-]{43}$" }, // Arweave address
username: { type: "string", minLength: 3, maxLength: 30, pattern: "^[a-zA-Z0-9_]+$" },
email: { type: "string", format: "email" },
age: { type: "integer", minimum: 13, maximum: 120 }
},
additionalProperties: false // Prevent injection
}
// ❌ Avoid: Exposing all user data
const users = await db.get("users")
// ✅ Better: Limit fields and results
const users = await db.get("users", ["createdAt", "desc"], 10, {
fields: ["username", "avatar"] // Only public fields
})
// ✅ Best: User-specific queries with validation
const validateUserId = (id) => /^[a-zA-Z0-9]{20}$/.test(id)
if (!validateUserId(userId)) throw new Error("Invalid user ID")
const user = await db.get("users", userId)
// Implement custom rate limiting with triggers
const rateLimitConfig = {
actions: [{
key: "rate_limit_posts",
on: "create",
fn: [
// Check last post time
["get()", ["posts", ["actor", "==", "$signer"], ["createdAt", "desc"], 1]],
["when()",
["gte()", "$ts", ["+", "$data[0].createdAt", 60000]], // 1 minute cooldown
["error()", "Please wait before posting again"]
],
["allow()"]
]
}]
}
// Define indexes for common queries
export default {
notes: {
index: [
["actor"], // Single-field index
["published"], // For sorting
["actor", "published"], // Composite index for user timeline
["hashtags[n]"] // Array index for tags
]
}
}
// ❌ Slow: Fetching all documents then filtering
const allNotes = await db.get("notes")
const userNotes = allNotes.filter(n => n.actor === userAddress)
// ✅ Fast: Use indexed queries
const userNotes = await db.get("notes", ["actor", "==", userAddress], ["published", "desc"])
// ✅ Faster: Use composite indexes for complex queries
const recentUserNotes = await db.get(
"notes",
["actor", "==", userAddress],
["published", "desc"],
10 // Limit results
)
import { useRef, useEffect, useState } from "react"
import { DB } from "wdb-sdk"
export function useWeaveDB() {
const [cache, setCache] = useState({})
const db = useRef()
const getCached = async (collection, query, ttl = 60000) => {
const cacheKey = JSON.stringify({ collection, query })
const cached = cache[cacheKey]
if (cached && Date.now() - cached.timestamp < ttl) {
return cached.data
}
const data = await db.current.get(collection, query)
setCache(prev => ({
...prev,
[cacheKey]: { data, timestamp: Date.now() }
}))
return data
}
return { db, getCached }
}
// ❌ Slow: Multiple individual writes
for (const user of users) {
await db.set("add:user", user, "users")
}
// ✅ Fast: Batch write (if supported by version)
await db.batch([
["set", "add:user", user1, "users"],
["set", "add:user", user2, "users"],
["set", "add:user", user3, "users"]
])
async function getPaginatedNotes(cursor = null, limit = 10) {
const query = cursor
? ["published", "<", cursor]
: []
const notes = await db.get(
"notes",
...query,
["published", "desc"],
limit + 1 // Fetch one extra to check if there's more
)
const hasMore = notes.length > limit
const results = hasMore ? notes.slice(0, -1) : notes
const nextCursor = hasMore ? results[results.length - 1].published : null
return { notes: results, nextCursor, hasMore }
}
// Use triggers to create searchable indices
export default {
notes: [{
key: "searchable_index",
on: "create",
fn: [
["mod()", {
searchTerms: ["$", ["split()", ["$", ["toLowerCase()", "$data.content"]], " "]]
}],
["allow()"]
]
}]
}
// Query with array contains
const searchResults = await db.get(
"notes",
["searchTerms", "array-contains", searchTerm.toLowerCase()]
)
// Schema with deletedAt field
const schema = {
type: "object",
required: ["id", "content", "active"],
properties: {
id: { type: "string" },
content: { type: "string" },
active: { type: "boolean" },
deletedAt: { type: ["integer", "null"] }
}
}
// Soft delete implementation
auth: [
["del:note", [
["equals()", "$signer", "$doc.actor"],
["mod()", { active: false, deletedAt: "$ts" }],
["allow()"]
]]
]
// Query only active records
const activeNotes = await db.get("notes", ["active", "==", true])
// Create history collection for audit trail
await db.mkdir({
name: "notes_history",
schema: {
type: "object",
required: ["noteId", "version", "content", "modifiedBy", "modifiedAt"],
properties: {
noteId: { type: "string" },
version: { type: "integer" },
content: { type: "string" },
modifiedBy: { type: "string" },
modifiedAt: { type: "integer" }
}
}
})
// Trigger to save history on update
triggers: {
notes: [{
key: "save_history",
on: "update",
fn: [
["set", "add:history", {
noteId: "$before.id",
version: ["$", ["+", ["$", ["get()", "notes_history", ["noteId", "==", "$before.id"], ["version", "desc"], 1]], 1]],
content: "$before.content",
modifiedBy: "$signer",
modifiedAt: "$ts"
}, "notes_history"],
["allow()"]
]
}]
}
Database not initializing:
wdb-sdk is installedSchema validation failing:
/db/schema.jsAuthentication errors:
/db/auth.jsQuery not returning expected results:
To refresh this skill with updated documentation:
/create-skill --config configs/weavedb.json/skill-enhancer weavedb https://docs.weavedb.dev/build/quick-start1.3.0 (2026-01-02): WAO Testing Framework Integration
1.2.0 (2026-01-02): AI-enhanced with production patterns
1.1.0 (2026-01-02): Added comprehensive quick-start guide
1.0.0 (2026-01-02): Initial skill creation
tools
MemPalace local-first AI memory system. Use when setting up persistent memory for Claude Code sessions, mining project files or conversation transcripts, querying past context, configuring MCP tools, managing the knowledge graph, or troubleshooting palace operations.
tools
LangSmith Python SDK — trace, evaluate, and monitor LLM applications. Covers @traceable decorator, trace context manager, Client API, evaluate() / aevaluate(), comparative evaluation, custom evaluators, dataset management, prompt caching, ASGI middleware, and pytest plugin.
development
LangGraph (Python) — build stateful, controllable agent graphs with checkpointing, streaming, persistence, interrupts, fault tolerance, and durable execution. Covers both Graph API (StateGraph) and Functional API (@entrypoint/@task).
development
LangGraph Graph API (Python) — build explicit DAG agent workflows with StateGraph, typed state, nodes, edges, Command routing, Send fan-out, checkpointers, interrupts, and streaming. Use when you need explicit control flow and graph topology.