Skip to main content
Everything on this page is defined once, in the shared manowar crate, and used identically by all four programs. Read this before the per-program pages, or jump here whenever they reference it.

Account serialization

Every state account is a 4-byte little-endian length header followed by a borsh payload:
The programs allocate rent-exempt space once at creation (sized to the content), verify the account owner is the expected program before reading, and treat a zero header as “not initialized”. Accounts are never closed — rent stays locked. Borsh field encoding, if you ever read bytes by hand: You don’t need to do this manually. The SDK has a typed decoder per account:

PDA conventions

All PDAs derive with the standard findProgramAddress under the owning program. Two conventions cover the whole suite:
  • Seed constants are short ASCII strings (b"agent", b"workflow", b"rfa"…).
  • Integer ids become 8-byte little-endian seeds (agent_id = 422a 00 00 00 00 00 00 00).
Each program page lists its accounts with their seeds — identity here, market here. The SDK mirrors every seed in ManowarSeeds and exposes ready-made finders:
Cross-program reads follow one rule: an Agent PDA is always derived under the identity program, no matter which program is reading it, and the reader verifies the account’s owner on-chain. Pass the canonical identity program ID from Deployed Contracts.

The Agent struct

One struct, defined in the shared crate, stored by identity, read by everyone:

Indexes

Lookup lists share two structs — U64Index { version, page, total, values: Vec<u64> } and PubkeyIndex (same shape, Vec<Pubkey>) — both capped at 64 entries. page is reserved for future paging; today there is exactly one page, and a full index fails writes with AccountTooSmall. The market program keeps its discovery lists (complete workflows, open RFAs, per-creator, per-leaser…) in these; reputation uses them for client lists; validation for per-agent requests.

Errors

All four programs return one shared error enum as ProgramError::Custom(n). When a transaction fails with Custom(17), that’s AlreadyLicensed.

Limits

Fixed constants — no on-chain config changes them: