repositories
loading repo index
repositories
loading repo index
repository
loading code, commits, and activity
Mirrored from https://github.com/ProjectOpenSea/opensea-skill
stars
latest
clone command
git clone gitlawb://did:key:z6MkqRzA...RfoM/ProjectOpenSea-...git clone gitlawb://did:key:z6MkqRzA.../ProjectOpenSea-...fef93001Release v2.14.011h ago| #1 | # Wallet Policies (Privy) |
| #2 | |
| #3 | Privy wallet policies enforce guardrails on transaction signing. Policies are evaluated inside a trusted execution environment (TEE) before any signing occurs, so an *applied* policy cannot be bypassed by application code at sign time. |
| #4 | |
| #5 | This is narrower than it sounds. The TEE protects against a compromised agent **signing through** an active policy, but it does **not** protect against the same credentials **rewriting** the policy first. Whoever holds `PRIVY_APP_ID` + `PRIVY_APP_SECRET` for a wallet without an `owner_id` can `PATCH /v1/wallets/{id}` to swap the policy for a permissive one and then sign freely. The hardening that closes this gap — registering an `owner_id` so policy mutations require a separate authorization signature — is in `references/wallet-setup.md`. Without it, the per-tx cap is a speed bump, not a ceiling. |
| #6 | |
| #7 | > **For agents reading this file:** applying or modifying policies is a **user-only operation** performed on a trusted machine with the wallet's authorization key. The agent must never construct or run policy-mutation requests. If a user asks the agent to update a policy, the agent should refuse and direct them to apply the change themselves from a trusted machine. The mutation recipes (HTTP method, body shape, signing) live outside the agent's skill path in `../../docs/policy-administration.md`. |
| #8 | |
| #9 | This file describes **what policies look like and what fields they support**, so the agent can help a user *author* a policy that the user then applies. It deliberately does not describe how to send the policy update request. |
| #10 | |
| #11 | ## Overview |
| #12 | |
| #13 | Policies restrict what transactions a wallet can sign: |
| #14 | |
| #15 | - **Transaction value caps**: maximum ETH/token value per transaction |
| #16 | - **Destination allowlists**: only sign transactions to approved contract addresses |
| #17 | - **Chain restrictions**: limit signing to specific chains |
| #18 | - **Method restrictions**: only allow specific contract method calls |
| #19 | - **Key export prevention**: prevent extraction of the private key |
| #20 | |
| #21 | > **Note on aggregate caps:** Privy policies are **stateless per-tx evaluators**. They cannot enforce daily/weekly cumulative spend limits. For aggregate ceilings, see `references/wallet-funding.md` (hot/cold wallet float pattern) — the wallet balance is the real aggregate cap. |
| #22 | |
| #23 | ## Configuring Policies |
| #24 | |
| #25 | Policies are authored as JSON (templates below) and applied by the user from a trusted machine. The agent can help draft and review the JSON; it must not apply it. |
| #26 | |
| #27 | The full Privy reference for policy fields and operators is at [docs.privy.io/controls/policies](https://docs.privy.io/controls/policies/overview). To apply or modify a policy, see `../../docs/policy-administration.md`. |
| #28 | |
| #29 | ## Recommended Policies |
| #30 | |
| #31 | ### Agent Trading: Conservative |
| #32 | |
| #33 | Suitable for automated agents executing swaps and NFT purchases with tight guardrails. |
| #34 | |
| #35 | ```json |
| #36 | { |
| #37 | "rules": [ |
| #38 | { |
| #39 | "name": "Limit transaction value", |
| #40 | "conditions": [ |
| #41 | { |
| #42 | "field_source": "ethereum_transaction", |
| #43 | "field": "value", |
| #44 | "operator": "lte", |
| #45 | "value": "100000000000000000" |
| #46 | } |
| #47 | ], |
| #48 | "action": "ALLOW" |
| #49 | }, |
| #50 | { |
| #51 | "name": "Allow OpenSea Seaport", |
| #52 | "conditions": [ |
| #53 | { |
| #54 | "field_source": "ethereum_transaction", |
| #55 | "field": "to", |
| #56 | "operator": "eq", |
| #57 | "value": "0x0000000000000068F116a894984e2DB1123eB395" |
| #58 | } |
| #59 | ], |
| #60 | "action": "ALLOW" |
| #61 | }, |
| #62 | { |
| #63 | "name": "Restrict to supported chains", |
| #64 | "conditions": [ |
| #65 | { |
| #66 | "field_source": "ethereum_transaction", |
| #67 | "field": "chain_id", |
| #68 | "operator": "in", |
| #69 | "value": ["1", "8453", "137", "42161", "10"] |
| #70 | } |
| #71 | ], |
| #72 | "action": "ALLOW" |
| #73 | }, |
| #74 | { |
| #75 | "name": "Deny everything else", |
| #76 | "conditions": [], |
| #77 | "action": "DENY" |
| #78 | } |
| #79 | ] |
| #80 | } |
| #81 | ``` |
| #82 | |
| #83 | ### Agent Trading: Permissive |
| #84 | |
| #85 | For trusted agents with higher limits and broader destination access. |
| #86 | |
| #87 | ```json |
| #88 | { |
| #89 | "rules": [ |
| #90 | { |
| #91 | "name": "Limit transaction value", |
| #92 | "conditions": [ |
| #93 | { |
| #94 | "field_source": "ethereum_transaction", |
| #95 | "field": "value", |
| #96 | "operator": "lte", |
| #97 | "value": "1000000000000000000" |
| #98 | } |
| #99 | ], |
| #100 | "action": "ALLOW" |
| #101 | }, |
| #102 | { |
| #103 | "name": "Restrict to supported chains", |
| #104 | "conditions": [ |
| #105 | { |
| #106 | "field_source": "ethereum_transaction", |
| #107 | "field": "chain_id", |
| #108 | "operator": "in", |
| #109 | "value": ["1", "8453", "137", "42161", "10"] |
| #110 | } |
| #111 | ], |
| #112 | "action": "ALLOW" |
| #113 | }, |
| #114 | { |
| #115 | "name": "Deny everything else", |
| #116 | "conditions": [], |
| #117 | "action": "DENY" |
| #118 | } |
| #119 | ] |
| #120 | } |
| #121 | ``` |
| #122 | |
| #123 | ## Policy Fields Reference |
| #124 | |
| #125 | | Field | Source | Description | |
| #126 | |-------|--------|-------------| |
| #127 | | `value` | `ethereum_transaction` | Transaction value in wei | |
| #128 | | `to` | `ethereum_transaction` | Destination contract address | |
| #129 | | `chain_id` | `ethereum_transaction` | EVM chain ID | |
| #130 | | `data` | `ethereum_transaction` | Transaction calldata (for method filtering) | |
| #131 | |
| #132 | ## Operators |
| #133 | |
| #134 | | Operator | Description | |
| #135 | |----------|-------------| |
| #136 | | `eq` | Equal to | |
| #137 | | `neq` | Not equal to | |
| #138 | | `gt` | Greater than | |
| #139 | | `gte` | Greater than or equal | |
| #140 | | `lt` | Less than | |
| #141 | | `lte` | Less than or equal | |
| #142 | | `in` | In list | |
| #143 | | `not_in` | Not in list | |
| #144 | |
| #145 | ## Key Addresses |
| #146 | |
| #147 | | Contract | Address | Usage | |
| #148 | |----------|---------|-------| |
| #149 | | Seaport 1.6 | `0x0000000000000068F116a894984e2DB1123eB395` | NFT marketplace orders | |
| #150 | | Native ETH | `0x0000000000000000000000000000000000000000` | Swap from address for native ETH | |
| #151 | | WETH (Base) | `0x4200000000000000000000000000000000000006` | Wrapped ETH on Base | |
| #152 | | USDC (Base) | `0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913` | USD Coin on Base | |
| #153 | |
| #154 | ## Tips |
| #155 | |
| #156 | 1. **Start conservative**: begin with tight value caps and a narrow allowlist, then relax as needed |
| #157 | 2. **Use chain restrictions**: limit to chains you actively trade on |
| #158 | 3. **Monitor policy violations**: Privy logs denied transactions in the dashboard |
| #159 | 4. **Separate wallets for separate concerns**: use different wallets (and policies) for swaps vs. NFT purchases |
| #160 | 5. **Never disable policies in production**: keep at least a value cap active |
| #161 |