# [ERC7795] dAppsがウォレットにトークン前提条件を指定できるWallet Call Token Capabilitiesの仕組みを理解しよう！

> ERC7795とは、EIP5792のwallet_sendCallsメソッドを拡張し、dAppsがウォレットに対してトークンに関する前提条件を指定できるようにする仕組みのことです。

- URL: https://cardene.dev/articles/09d6129ec75b598cb0c0
- 公開日: 2026-02-01
- 更新日: 2026-02-01
- トピック: Blockchain
- タグ: ethereum, solidity, smartcontract, ブロックチェーン

## はじめに

『DApps開発入門』という本や色々記事を書いているかるでねです。

https://amzn.asia/d/gxvJ0Pw

今回は、EIP-5792の`wallet_sendCalls`を拡張し、dAppsがウォレット呼び出しに必要なトークン残高や承認などの前提条件を指定できるようにする仕組みを提案している**ERC7795**についてまとめていきます！

:::message
以下にまとめられているものを翻訳・要約・補足しながらまとめていきます。
:::

https://eips.ethereum.org/EIPS/eip-7795

他にも様々なEIP・BIP・SLIP・CAIP・ENSIP・RFC・ACPについてまとめています。

https://cardene.notion.site/ERC-EIP-2a03fa3ea33d43baa9ed82288f98d4a9?pvs=4

## 概要

**ERC7795**とは、**EIP5792**の`wallet_sendCalls`メソッドを拡張し、dAppsがウォレットに対してトークンに関する前提条件を指定できるようにする仕組みのことです。

:::message
**EIP5792**は、dAppsがウォレットに対して複数の呼び出しをバッチで送信できるようにする`wallet_sendCalls`メソッドを定義した規格です。
:::

**ERC7795**では、**ERC20**トークンの残高・承認要件を指定できます。

:::message
**ERC20**については以下の記事を参考にしてください。
:::

[\[ERC20\] ERC20を1からわかりやすく解説](/articles/aeefe2d89dd5332c9f43)

また、**ERC721**（NFT）の所有権・承認要件も指定できます。

:::message
**ERC721**については以下の記事を参考にしてください。
:::

[\[ERC721\] ERC721を1からわかりやすく解説](/articles/0570a8d05bc7c9b9593f)

さらに、**ERC1155**トークンの残高・承認要件も指定可能です。

:::message
**ERC1155**については以下の記事を参考にしてください。
:::

https://qiita.com/cardene/items/5c37b0c51e1b9c458c67

これらの機能は`wallet_sendCalls`と`wallet_getCapabilities`RPCメソッドを通じて実装されます。

この規格の特徴は、ウォレットが前提条件を自動的に処理できる点にあります。
dAppsがトークン要件を指定すると、ウォレットはその要件を満たすために必要なトランザクション（承認やスワップなど）を自動的に先頭に追加します。

**ERC7795**では、ERC20の残高・承認、ERC721の所有権・承認、ERC1155の残高・承認に対応する6種類の機能を定義しています。
これらは**EIP5792**の既存の機能発見メカニズム（`wallet_getCapabilities`）を活用するため、ウォレットは対応可能な要件のみを選択的に実装できます。
また、複数の機能を組み合わせて使用することも可能で、将来的に新しい要件タイプを段階的に追加できる拡張性も備えています。

## 動機

この提案が生まれた背景には以下のような課題がありました。

#### トークン承認の複雑さ

現在、dAppsがユーザーのトークンを操作する場合、事前にトークンの承認（approve）を取得する必要があります。
しかし、この承認プロセスはdAppsごとに異なる実装が必要で、ユーザー体験が一貫していませんでした。

#### ウォレット側での最適化が困難

dAppsはトークン操作に必要な前提条件を知っていますが、ウォレットにその情報を伝える標準的な方法がありませんでした。
そのため、ウォレットは最適なトランザクション順序を構築することが困難でした。

#### クロスチェーン操作の課題

ブリッジやスワップなどのクロスチェーン操作では、特定のトークン残高や承認が前提条件となることがあります。
これらの前提条件をウォレットに伝える標準的な方法がないため、ユーザーは手動で複数のトランザクションを実行する必要がありました。

**この提案による解決策**

**ERC7795**は、dAppsが`wallet_sendCalls`の機能としてトークン前提条件を指定できるようにします。
ウォレットはこれらの前提条件を解釈し、必要に応じてトランザクションを自動的に先頭に追加することで、シームレスなユーザー体験を提供できます。

## 仕様

### 機能一覧

**ERC7795**では、以下の6つの機能を定義しています。

| 機能 | 対象トークン | 説明 |
|--------------|------------|------|
| `erc20MinBalance` | ERC20 | 最小残高要件 |
| `erc20MinAllowance` | ERC20 | 最小承認額要件 |
| `erc721Ownership` | ERC721 | NFT所有権要件 |
| `erc721Approval` | ERC721 | NFT承認要件 |
| `erc1155MinBalance` | ERC1155 | 最小残高要件 |
| `erc1155MinAllowance` | ERC1155 | 最小承認要件 |

### ERC20

ERC20トークンに関する機能として、最小残高要件と最小承認額要件の2つが定義されています。

#### erc20MinBalance

ERC20トークンの最小残高要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前にアカウントが特定のERC20トークンの最小残高を持っている必要があることをウォレットに通知します。
ウォレットはこの要件を満たすために、ブリッジやスワップなどのトランザクションを先頭に追加する場合があります。

##### パラメータ

```javascript
{
  "erc20MinBalance": {
    "0xTokenAddress": "0xMinimumBalanceInHex"
  }
}
```

- `0xTokenAddress`
    - ERC20トークンのコントラクトアドレス。
- `0xMinimumBalanceInHex`
    - 必要な最小残高（16進数形式）。

##### 使用例

```javascript
{
  "capabilities": {
    "erc20MinBalance": {
      "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48": "0x5F5E100" // 100 USDC (6 decimals)
    }
  }
}
```

#### erc20MinAllowance

ERC20トークンの最小承認額要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前に特定のアドレスに対するERC20トークンの最小承認額が必要であることをウォレットに通知します。
ウォレットはこの要件を満たすために、`approve`トランザクションを先頭に追加する場合があります。

##### パラメータ

```javascript
{
  "erc20MinAllowance": {
    "0xTokenAddress": {
      "0xSpenderAddress": "0xMinimumAllowanceInHex"
    }
  }
}
```

- `0xTokenAddress`
    - ERC20トークンのコントラクトアドレス。
- `0xSpenderAddress`
    - 承認を受けるアドレス（スペンダー）。
- `0xMinimumAllowanceInHex`
    - 必要な最小承認額（16進数形式）。

##### 使用例

```javascript
{
  "capabilities": {
    "erc20MinAllowance": {
      "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48": {
        "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D": "0x5F5E100" // Uniswap Router に 100 USDC を承認
      }
    }
  }
}
```

### ERC721

ERC721トークン（NFT）に関する機能として、所有権要件と承認要件の2つが定義されています。

#### erc721Ownership

ERC721トークン（NFT）の所有権要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前にアカウントが特定のNFTを所有している必要があることをウォレットに通知します。
ウォレットはこの要件を満たすために、NFTの購入などのトランザクションを先頭に追加する場合があります。

##### パラメータ

```javascript
{
  "erc721Ownership": {
    "0xTokenAddress": ["0xTokenId1", "0xTokenId2"]
  }
}
```

- `0xTokenAddress`
    - ERC721トークンのコントラクトアドレス。
- `0xTokenId`
    - 必要なトークンID（16進数形式）の配列。

##### 使用例

```javascript
{
  "capabilities": {
    "erc721Ownership": {
      "0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D": ["0x1", "0x2"] // BAYC #1 と #2 の所有権が必要
    }
  }
}
```

#### erc721Approval

ERC721トークン（NFT）の承認要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前に特定のアドレスに対するNFTの承認が必要であることをウォレットに通知します。
`setApprovalForAll`による全体承認、または特定トークンIDへの個別承認のいずれかで要件を満たすことができます。

##### パラメータ

```javascript
{
  "erc721Approval": {
    "0xTokenAddress": {
      "0xOperatorAddress": ["0xTokenId1", "0xTokenId2"]
    }
  }
}
```

- `0xTokenAddress`
    - ERC721トークンのコントラクトアドレス。
- `0xOperatorAddress`
    - 承認を受けるオペレーターアドレス。
- `0xTokenId`
    - 承認が必要なトークンIDの配列（16進数形式）。

##### 使用例

```javascript
{
  "capabilities": {
    "erc721Approval": {
      "0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D": {
        "0x00000000006c3852cbEf3e08E8dF289169EdE581": ["0x1"] // OpenSea Seaport に BAYC #1 を承認
      }
    }
  }
}
```

### ERC1155

ERC1155トークンに関する機能として、最小残高要件と最小承認要件の2つが定義されています。

#### erc1155MinBalance

ERC1155トークンの最小残高要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前にアカウントが特定のERC1155トークンの最小残高を持っている必要があることをウォレットに通知します。

##### パラメータ

```javascript
{
  "erc1155MinBalance": {
    "0xTokenAddress": {
      "0xTokenId": "0xMinimumBalanceInHex"
    }
  }
}
```

- `0xTokenAddress`
    - ERC1155トークンのコントラクトアドレス。
- `0xTokenId`
    - トークンID（16進数形式）。
- `0xMinimumBalanceInHex`
    - 必要な最小残高（16進数形式）。

##### 使用例

```javascript
{
  "capabilities": {
    "erc1155MinBalance": {
      "0x76BE3b62873462d2142405439777e971754E8E77": {
        "0x1": "0xA" // Token ID 1 の残高が 10 以上必要
      }
    }
  }
}
```

#### erc1155MinAllowance

ERC1155トークンの最小承認要件を指定する機能です。
dAppsはこの機能を使用して、呼び出しを実行する前に特定のアドレスに対するERC1155トークンの承認が必要であることをウォレットに通知します。
ERC1155は`setApprovalForAll`のみをサポートしているため、この機能は全体承認を要求します。

##### パラメータ

```javascript
{
  "erc1155MinAllowance": {
    "0xTokenAddress": ["0xOperatorAddress1", "0xOperatorAddress2"]
  }
}
```

- `0xTokenAddress`
    - ERC1155トークンのコントラクトアドレス。
- `0xOperatorAddress`
    - 承認を受けるオペレーターアドレスの配列。

##### 使用例

```javascript
{
  "capabilities": {
    "erc1155MinAllowance": {
      "0x76BE3b62873462d2142405439777e971754E8E77": [
        "0x00000000006c3852cbEf3e08E8dF289169EdE581" // OpenSea Seaport に承認
      ]
    }
  }
}
```

## 補足

#### 完全な使用例

以下は、複数の機能を組み合わせた`wallet_sendCalls`の完全な使用例です。

```javascript
{
  "method": "wallet_sendCalls",
  "params": [{
    "version": "1.0",
    "chainId": "0x1",
    "from": "0xUserAddress",
    "calls": [
      {
        "to": "0xDeFiProtocol",
        "data": "0x...",
        "value": "0x0"
      }
    ],
    "capabilities": {
      "erc20MinBalance": {
        "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48": "0x5F5E100"
      },
      "erc20MinAllowance": {
        "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48": {
          "0xDeFiProtocol": "0x5F5E100"
        }
      }
    }
  }]
}
```

この例では、以下の前提条件を指定しています。

1. USDCの残高が100以上であること
2. DeFiプロトコルに対してUSDCの承認が100以上であること

#### ウォレットの動作

ウォレットは指定された機能に基づいて、以下のように動作します。

```mermaid
sequenceDiagram
    participant dApp
    participant Wallet
    participant Blockchain

    dApp->>Wallet: wallet_sendCalls (with capabilities)
    Wallet->>Wallet: 前提条件を確認
    alt 前提条件が満たされていない場合
        Wallet->>Wallet: 必要なトランザクションを生成
        Wallet->>Blockchain: 前提条件を満たすTx
    end
    Wallet->>Blockchain: 元のcallsを実行
    Blockchain-->>Wallet: 結果
    Wallet-->>dApp: レスポンス
```

この図は、dAppsが`wallet_sendCalls`で機能を指定した場合のウォレットの処理フローを示しています。

1. dAppsが機能付きの`wallet_sendCalls`をウォレットに送信します。
2. ウォレットは指定された前提条件（残高要件、承認要件など）を確認します。
3. 前提条件が満たされていない場合、ウォレットは必要なトランザクション（スワップ、ブリッジ、approve呼び出しなど）を自動的に生成します。
4. 前提条件を満たすトランザクションを先に実行し、その後に元のcallsを実行します。
5. すべてのトランザクションが完了したら、結果をdAppsに返します。

この仕組みにより、dAppsは複雑なトランザクション順序を自分で管理する必要がなくなり、ウォレットが最適な方法で前提条件を処理できます。

#### 機能のサポート確認

ウォレットがこれらの機能をサポートしているかどうかは、`wallet_getCapabilities`メソッドで確認できます。

```javascript
{
  "method": "wallet_getCapabilities",
  "params": ["0xUserAddress"]
}
```

レスポンス例を以下に示します。

```javascript
{
  "0x1": {
    "erc20MinBalance": { "supported": true },
    "erc20MinAllowance": { "supported": true },
    "erc721Ownership": { "supported": true },
    "erc721Approval": { "supported": true },
    "erc1155MinBalance": { "supported": true },
    "erc1155MinAllowance": { "supported": true }
  }
}
```

## 互換性

#### EIP5792との関係

**ERC7795**は以下の規格と関係があります。

| 規格 | 関係性 | 備考 |
|------|--------|------|
| **EIP5792** | 拡張 | `wallet_sendCalls`の機能として実装 |
| **ERC20** | 対象 | 残高・承認要件を指定可能 |
| **ERC721** | 対象 | 所有権・承認要件を指定可能 |
| **ERC1155** | 対象 | 残高・承認要件を指定可能 |

## 後方互換性

**ERC7795**は**EIP5792**の機能システムを使用しているため、この機能をサポートしていないウォレットでも、単純に機能を無視して通常の`wallet_sendCalls`として処理することができます。

## セキュリティ

:::message alert
セキュリティに関する考慮事項として、以下の点に注意が必要です。
:::

#### 過度な承認

dAppsが必要以上の承認額を要求する可能性があります。

ウォレットは要求された承認額をユーザーに明示し、必要に応じて調整できるようにすべきです。
また、無制限承認（`type(uint256).max`）の要求には特に注意が必要です。

#### 悪意のあるdApps

悪意のあるdAppsがユーザーの資産を狙った前提条件を設定する可能性があります。

ウォレットは前提条件を満たすために実行するトランザクションの詳細をユーザーに表示し、明示的な承認を得るべきです。

#### トランザクション順序の操作

前提条件を満たすトランザクションと元のcallsの間でフロントランニング攻撃が発生する可能性があります。

ウォレットは可能な限りアトミックな実行（バッチトランザクション）を使用すべきです。

ウォレット開発者は、前提条件を満たすために自動的に実行するトランザクションについて、ユーザーに明確な同意を求める必要があります。

## 引用

https://eips.ethereum.org/EIPS/eip-7795

https://eips.ethereum.org/EIPS/eip-5792

https://eips.ethereum.org/EIPS/eip-20

https://eips.ethereum.org/EIPS/eip-721

https://eips.ethereum.org/EIPS/eip-1155

## 最後に

今回は「**ERC7795**によるdAppsがウォレットにトークン前提条件を指定できる仕組み」についてまとめてきました！
いかがだったでしょうか？

質問などがある方は以下のTwitterのDMなどからお気軽に質問してください！

[Twitter @cardene777](https://twitter.com/cardene777)

他の媒体でも情報発信しているのでぜひ他も見ていってください！

https://zenn.dev/heku

https://cardene.substack.com/

https://mirror.xyz/0xcE77b9fCd390847627c84359fC1Bc02fC78f0e58

https://cardene.notion.site/ERC-EIP-2a03fa3ea33d43baa9ed82288f98d4a9?pvs=4
