Skip to content

feat: add Claimable Balance support across lib, AgentClient, and Lang…#76

Open
nishant-uxs wants to merge 2 commits into
Stellar-Tools:mainfrom
nishant-uxs:feat/claimable-balances-v2
Open

feat: add Claimable Balance support across lib, AgentClient, and Lang…#76
nishant-uxs wants to merge 2 commits into
Stellar-Tools:mainfrom
nishant-uxs:feat/claimable-balances-v2

Conversation

@nishant-uxs

Copy link
Copy Markdown

feat: add Claimable Balance support across lib, AgentClient, and LangChain tool

What

First-class support for Stellar Claimable Balances — a unique Stellar
primitive for conditional / time-locked payments (escrow, vesting,
scheduled payouts). Previously absent from the kit. Particularly valuable
for AI-agent workflows that release funds only when a predicate is
satisfied.

Why

Every existing kit feature (bridge, swap, stake, payment, balance) ships a
LangChain DynamicStructuredTool and is bundled into stellarTools.
Claimable balances unlock new agentic use-cases (escrow, vesting, retry
deadlines) that none of the existing tools cover.

Surfaces

  1. Programmaticagent.claimable.{create,claim,list} on AgentClient
  2. LangChain ToolStellarClaimableBalanceTool, auto-included in stellarTools
  3. Lower-levellib/claimableBalance (functions + buildPredicate + constants)

Highlights

  • Friendly tagged-union ClaimPredicate (unconditional / beforeRelativeTime
    / beforeAbsoluteTime / not / and / or) with input validation, depth guard,
    and amount/issuer checks
  • 1:1 claimant-to-operation mapping for deterministic balance-id extraction
  • All Stellar protocol limits exposed as named exports + overridable via
    per-call options (no magic numbers)
  • Tool always returns JSON ({ ok, ... }) for deterministic agent parsing
  • Recursive zod schema so agents can pass nested compound predicates

Tests

  • tests/unit/lib/claimableBalance.test.ts (21 tests)
  • tests/unit/tools/claimableBalance.test.ts (7 tests)
  • All 87 tests pass; tsc --noEmit clean

Files

  • lib/claimableBalance.ts (new)
  • tools/claimableBalance.ts (new)
  • examples/claimable-balance-example.ts (new)
  • tests/unit/lib/claimableBalance.test.ts (new)
  • tests/unit/tools/claimableBalance.test.ts (new)
  • agent.ts (added claimable namespace + type re-exports)
  • index.ts (export tool, types, constants; add to stellarTools)
  • README.md (new "Claimable Balances" section)

…Chain tool

Introduces first-class Stellar Claimable Balance support — a unique Stellar
primitive for conditional / time-locked payments (escrow, vesting, scheduled
payouts) that was previously absent from the kit. Particularly valuable for
AI-agent workflows that need to release funds only when a predicate is
satisfied.

What's new
----------
* lib/claimableBalance.ts
  - createClaimableBalance, claimClaimableBalance, listClaimableBalances
  - buildPredicate helper for the friendly tagged-union ClaimPredicate
    (unconditional / beforeRelativeTime / beforeAbsoluteTime / not / and / or)
  - extractBalanceIdsFromTransactionResult for deterministic balance-id parsing
  - All Stellar protocol limits exported as named constants:
      MAX_CLAIMANTS_PER_BALANCE = 10
      MAX_OPERATIONS_PER_TRANSACTION = 100
      MAX_PREDICATE_DEPTH = 5
      DEFAULT_TRANSACTION_TIMEOUT_SECONDS = 180
  - Per-call options to override caps (maxOperationsPerTransaction,
    maxPredicateDepth, transactionTimeoutSeconds, baseFee) — no magic numbers
    locked into user code

* tools/claimableBalance.ts
  - StellarClaimableBalanceTool — LangChain DynamicStructuredTool exposing
    create / claim / list to AI agents
  - Recursive zod schema for nested compound predicates
  - Always returns JSON ({ ok, ... }) for deterministic agent parsing
  - Auto-included in the exported stellarTools array

* agent.ts
  - agent.claimable.{create,claim,list} on AgentClient
  - Public types re-exported from agent.ts and index.ts

* examples/claimable-balance-example.ts
  - Runnable end-to-end testnet example demonstrating composite predicate
    (and + not + beforeRelativeTime + beforeAbsoluteTime), list, and claim

* tests
  - tests/unit/lib/claimableBalance.test.ts (21 tests):
    constants, predicate validation/depth/overrides, XDR robustness,
    create flow (input validation, op-shape, signing, large batches,
    custom caps, Horizon failure propagation), claim flow, list flow
  - tests/unit/tools/claimableBalance.test.ts (7 tests):
    LangChain tool surface, JSON contract for create/claim/list,
    missing-secret handling

* README
  - New 'Claimable Balances' section with API, predicate table, defaults &
    overrides, and LangChain-tool documentation

Verification
------------
* 87/87 tests pass (28 new + 59 existing)
* tsc --noEmit clean

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1 issue found across 8 files

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="examples/claimable-balance-example.ts">

<violation number="1" location="examples/claimable-balance-example.ts:29">
P2: Example is not runnable as written because it generates new unfunded accounts each run and immediately uses them for create/claim without any funding or reuse mechanism.</violation>
</file>

Reply with feedback, questions, or to request a fix. Tag @cubic-dev-ai to re-run a review.

Comment thread examples/claimable-balance-example.ts
Address Cubic AI review (PR Stellar-Tools#76): the example previously generated fresh
random keypairs each run and immediately invoked create/claim against
unfunded testnet accounts, so it would always fail with account-not-found.

Changes
-------
* resolveAccount() helper:
  - Reads EXAMPLE_SOURCE_SECRET / EXAMPLE_RECIPIENT_SECRET when set
    (preferred for repeated runs)
  - Otherwise generates a fresh keypair and auto-funds it via the
    Friendbot faucet (https://friendbot.stellar.org), then verifies the
    account exists on-chain before returning
  - Prints the freshly-funded secrets so the user can re-export them
    for subsequent runs (avoids hammering Friendbot)
* Wait for the predicate window to open before claiming, so the claim
  step now succeeds end-to-end on a clean run
* Updated header docs to describe both modes (env-var reuse vs Friendbot)

Verification
------------
* tsc --noEmit clean
* 87/87 tests pass
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant