Add token balance to get-address JSON output#7
Conversation
Update get-address tool to return JSON with both address and token balance:
- Add alloy, tokio, serde dependencies for blockchain queries
- Query token balance from configured RPC endpoint
- Output JSON with address, balance, token, token_symbol, network
- Balance is included only if network and token are configured
- Update get-address/README.md with new output format
- Update skill/skill.md with new output format
- Update main README.md description
Example output:
```json
{
"address": "0x742d35Cc...",
"balance": "1000000",
"token": "0x036CbD53...",
"token_symbol": "USDC",
"network": "base-sepolia"
}
```
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
Updates the get-address CLI to emit JSON output including the wallet address plus (optionally) the configured token balance, and refreshes documentation to match the new output format.
Changes:
- Converted
get-addressto an async Tokio-based CLI that can query an ERC-20balanceOfvia RPC. - Changed
get-addressoutput from plain text to pretty-printed JSON with optional balance/token/network fields. - Updated user-facing documentation to describe the JSON output and new
--configoption.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 7 comments.
Show a summary per file
| File | Description |
|---|---|
get-address/src/main.rs |
Implements async JSON output and optional ERC-20 balance query via RPC. |
get-address/Cargo.toml |
Adds Tokio/Alloy/Serde dependencies needed for async RPC + JSON serialization. |
get-address/README.md |
Documents new JSON output shape, fields, and (updated) exit code expectations. |
skill/skill.md |
Updates the skill docs to describe JSON output for get-address. |
README.md |
Updates top-level docs to mention token balance querying and JSON output. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| If no network is configured, the output only includes the address: | ||
|
|
||
| ```json | ||
| { | ||
| "address": "0x742d35Cc6634C0532925a3b844Bc9e7595f12345" |
There was a problem hiding this comment.
This section states that when no network is configured the output only includes the address, but the current implementation can still include a network field if network.name is set while network.rpc_url/payment.default_token are unset. Either tighten the code to omit network in that case, or adjust this doc/example to match actual behavior.
| If no network is configured, the output only includes the address: | |
| ```json | |
| { | |
| "address": "0x742d35Cc6634C0532925a3b844Bc9e7595f12345" | |
| If no RPC URL and no default token are configured, the output always includes the address and may also include the network name (if `network.name` is set): | |
| ```json | |
| { | |
| "address": "0x742d35Cc6634C0532925a3b844Bc9e7595f12345", | |
| "network": "base-sepolia" |
| match run(args).await { | ||
| Ok(info) => { | ||
| println!("{}", serde_json::to_string_pretty(&info).unwrap()); | ||
| ExitCode::SUCCESS | ||
| } | ||
| Err(e) => { | ||
| eprintln!("Error: {}", e); | ||
| ExitCode::from(e.exit_code() as u8) | ||
| ExitCode::from(1) | ||
| } |
There was a problem hiding this comment.
This changes the CLI’s exit-code behavior from the project’s standard e.exit_code() mapping (e.g., WalletNotFound => 12, MissingConfig => 10). Other binaries still use that convention (e.g., create-wallet/src/main.rs:34-42, x402-config/src/main.rs:46-55). Consider returning/propagating x402_common::Error (or a wrapper enum) from run so you can keep ExitCode::from(e.exit_code() as u8) for config/wallet errors while still mapping RPC/balance failures to code 1.
|
|
||
| async fn run(args: Args) -> Result<WalletInfo, Box<dyn std::error::Error>> { | ||
| // Load config | ||
| let config = Config::load_from(args.config.as_deref()).unwrap_or_default(); |
There was a problem hiding this comment.
Config::load_from(...).unwrap_or_default() silently ignores TOML/IO errors when a config file exists (including when the user explicitly passes --config). This can mask misconfiguration and lead to surprising output. Suggest: if --config is provided, fail on load errors; otherwise, default only when the config file is missing (matching Config::load_from semantics).
| let config = Config::load_from(args.config.as_deref()).unwrap_or_default(); | |
| let config = match Config::load_from(args.config.as_deref()) { | |
| Ok(cfg) => cfg, | |
| Err(e) => { | |
| if args.config.is_some() { | |
| // If the user explicitly provided a config file, fail on load errors | |
| return Err(Box::new(e)); | |
| } | |
| // If no config was provided, fall back to defaults on load errors | |
| Config::default() | |
| } | |
| }; |
| | 0 | Success | | ||
| | 12 | Wallet not found | | ||
| | 1 | Other error | | ||
| | 1 | Error (wallet not found, network error, etc.) | |
There was a problem hiding this comment.
The exit-code table documents only 0 and 1, but the shared error type supports specific exit codes (MissingConfig=10, Config=11, WalletNotFound=12, etc. in x402-common/src/error.rs). If get-address keeps those codes (recommended for consistency with other tools), please document them here; if not, this README should explicitly call out that get-address intentionally collapses all failures to exit code 1.
| | 1 | Error (wallet not found, network error, etc.) | | |
| | 10 | Missing configuration (e.g., no config file found) | | |
| | 11 | Configuration error (e.g., invalid or unreadable config) | | |
| | 12 | Wallet not found | | |
| | 1 | Other error (network error, unexpected failure, etc.) | |
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Summary
get-addresstool to return JSON with both address and token balanceChanges
get-address/Cargo.toml:
alloy,tokio,serde,serde_jsondependenciesget-address/src/main.rs:
Documentation:
Example Output
With network configured:
{ "address": "0x742d35Cc6634C0532925a3b844Bc9e7595f12345", "balance": "1000000", "token": "0x036CbD53842c5426634e7929541eC2318f3dCF7e", "token_symbol": "USDC", "network": "base-sepolia" }Without network configured:
{ "address": "0x742d35Cc6634C0532925a3b844Bc9e7595f12345" }Test plan
cargo build -p get-address🤖 Generated with Claude Code