はじめに
初めまして。
CryptoGamesというブロックチェーンゲーム企業でエンジニアをしている cardene(かるでね) です!
スマートコントラクトを書いたり、フロントエンド・バックエンド・インフラと幅広く触れています。
代表的なゲームはクリプトスペルズというブロックチェーンゲームです。
今回は、ERC20、ERC721、ERC1155トークンに払い戻し機能の追加を提案している規格であるERC5507についてまとめていきます!
以下にまとめられているものを翻訳・要約・補足しながらまとめていきます。
他にも様々なERCについてまとめています。
概要
このERCの提案は、ERC20、ERC721、ERC1155トークンの新規販売において、返金が可能な機能を追加するものです。
ERC20については以下を参考にしてください。
ERC721については以下を参考にしてください。
ERC1155については以下を参考にしてください。
この機能により、ユーザーがトークンを購入したお金は、事前に決定された期間が終了するまで、第三者が管理するエスクロー口座に保管されます。
この期間中であれば、ユーザーは購入したトークンを返して、支払ったお金を戻してもらうことができます。
例えば、もしトークンを買ったけれどもプロジェクトが思ったように進まなかった場合、ユーザーはrefund
関数を通じてトークンを返却し、投資した資金を取り戻すことができます。
動機
NFTとトークンの世界では開発者が資金を持ち逃げする「rugpull」という問題があり、これを防ぐための信頼できる方法が必要です。
購入者への返金機能を導入することで、購入者を保護し、作成者の信頼性も向上します。
このような場合に使う標準化されたインターフェースには、以下のようなメリットがあります。
- EUの「Distance Selling Regulation」に適合しやすくなり、オンラインで購入された商品(例えばトークン)に14日間の返金期間が必要です。
Distance Selling Regulation
主にヨーロッパ連合(EU)において適用される消費者保護の法規則です。
この規則は、消費者が店舗外(オンラインショップ、郵便注文、電話販売など)で商品やサービスを購入する時に適用され、消費者に返品やキャンセルの権利を保証しています。
特に、EUでは「遠隔販売規制」として知られており、オンラインで商品やサービスを購入した消費者には、商品到着後14日以内に無条件でキャンセルする権利が与えられています。
これには、理由を問わずに購入した商品を返送し、全額返金を受けることが含まれます。
この規則の目的は、消費者が実際に商品を見ることなく購入を決定する遠隔販売の特性によるリスクを軽減することにあります。
「Distance Selling Regulatios」は、遠隔販売における透明性を高め、消費者が信頼して取引できるようにするために、販売者が守るべき一連の義務も定めています。
例えば、販売者は商品や契約条件、キャンセルポリシーなどに関する明確な情報を消費者に提供しなければなりません。
- ポートフォリオブラウザーやマーケットプレイスといったNFT関連アプリとの相互運用が可能になります。
- NFTマーケットプレイスは、NFTがまだ返金可能であることを示すバッジを商品に表示したり、マーケットプレイスでのリストよりも返金を提案することができます。
- 分散型取引所は、返金によってより高い収益が見込める場合、トークンの返金を提供できます。
- ウォレットはトークンが返金されるアクションをユーザーにより明確に伝えることができるようになります。
- これは、トークンの転送時に特有のダイアログが表示されるのと似ています。
- DAOは、トークンを返金する機能を含む提案をより明確に表示することができます。
これらの機能は、NFTやトークンの購入者をより守り、市場の信頼性を高めるために大切なステップです。
コントラクトや他のツールがこの新しい標準を採用することで、より安全で信頼性の高い取引環境が作り出されることが期待されます。
仕様
この規格に準拠する実装はERC165も実装する必要があります。
ERC165については以下を参考にしてください。
ERC20 Refund Extension
// SPDX-License-Identifier: CC0-1.0
pragma solidity ^0.8.17;
import "ERC20.sol";
import "ERC165.sol";
/// @notice Refundable ERC-20 tokens
/// @dev The ERC-165 identifier of this interface is `0xf0ca2917`
interface ERC20Refund is ERC20, ERC165 {
/// @notice Emitted when a token is refunded
/// @dev Emitted by `refund`
/// @param _from The account whose assets are refunded
/// @param _amount The amount of token (in terms of the indivisible unit) that was refunded
event Refund(
address indexed _from,
uint256 indexed _amount
);
/// @notice Emitted when a token is refunded
/// @dev Emitted by `refundFrom`
/// @param _sender The account that sent the refund
/// @param _from The account whose assets are refunded
/// @param _amount The amount of token (in terms of the indivisible unit) that was refunded
event RefundFrom(
address indexed _sender,
address indexed _from,
uint256 indexed _amount
);
/// @notice As long as the refund is active, refunds the user
/// @dev Make sure to check that the user has the token, and be aware of potential re-entrancy vectors
/// @param amount The `amount` to refund
function refund(uint256 amount) external;
/// @notice As long as the refund is active and the sender has sufficient approval, refund the tokens and send the ether to the sender
/// @dev Make sure to check that the user has the token, and be aware of potential re-entrancy vectors
/// The ether goes to msg.sender.
/// @param from The user from which to refund the assets
/// @param amount The `amount` to refund
function refundFrom(address from, uint256 amount) external;
/// @notice Gets the refund price
/// @return _wei The amount of ether (in wei) that would be refunded for a single token unit (10**decimals indivisible units)
function refundOf() external view returns (uint256 _wei);
/// @notice Gets the first block for which the refund is not active
/// @return block The first block where the token cannot be refunded
function refundDeadlineOf() external view returns (uint256 block);
}
Refund
event Refund(
address indexed _from,
uint256 indexed _amount
);
概要
トークンが返金された時に発行されるイベント。
詳細
このイベントは、refund
関数によってトリガーされます。
トークンの返金が行われると、このイベントが発行され、返金されたアカウントと金額の情報がブロックチェーンに記録されます。
パラメータ
-
_from
- 資産が返金されたアカウント。
-
_amount
- 返金されたトークンの量(最小分割単位で)。
RefundFrom
event RefundFrom(
address indexed _sender,
address indexed _from,
uint256 indexed _amount
);
概要
他のアカウントに代わってトークンが返金された時に発行されるイベント。
詳細
このイベントは、refundFrom
関数によってトリガーされます。
誰かが他人のアカウントからトークンを返金するときにこのイベントが発行され、実行者、返金されたアカウント、そして返金された金額の情報がブロックチェーンに記録されます。
パラメータ
-
_sender
- 返金を送ったアカウント。
-
_from
- 資産が返金されたアカウント。
-
_amount
- 返金されたトークンの量(最小分割単位で)。
refund
function refund(uint256 amount) external;
概要
返金がアクティブである限り、ユーザーに対して返金を行う関数。
詳細
この関数を実行する前に、ユーザーがトークンを保持していることを確認し、再入可能性に関する問題がないか注意深くチェックする必要があります。
引数
-
amount
- 返金する金額。
refundFrom
function refundFrom(address from, uint256 amount) external;
概要
返金がアクティブであり、送信者に十分な承認がある場合にトークンを返金しETHを送信者に送る関数。
詳細
ユーザーがトークンを保持していることを確認し、再入可能性に関する問題に注意しながらETHをmsg.sender
に送信します。
引数
-
from
- 資産を返金するユーザー。
-
amount
- 返金する金額。
refundOf
function refundOf() external view returns (uint256 _wei);
概要
返金価格を取得する関数。
詳細
一つのトークン単位(10**decimalsで表される分割不可能な単位)に対して返金されるイーサの量(wei
単位)を返します。
戻り値
-
_wei
- 単一のトークン単位に対する返金額(
wei
単位)。
- 単一のトークン単位に対する返金額(
refundDeadlineOf
function refundDeadlineOf() external view returns (uint256 block);
概要
返金がアクティブでない最初のブロックを取得する関数。
詳細
トークンが返金できない最初のブロック番号を返します。
戻り値
-
block
- トークンが返金できない最初のブロック番号。
ERC721 Refund Extension
// SPDX-License-Identifier: CC0-1.0
pragma solidity ^0.8.17;
import "ERC721.sol";
import "ERC165.sol";
/// @notice Refundable ERC-721 tokens
/// @dev The ERC-165 identifier of this interface is `0xe97f3c83`
interface ERC721Refund is ERC721 /* , ERC165 */ {
/// @notice Emitted when a token is refunded
/// @dev Emitted by `refund`
/// @param _from The account whose assets are refunded
/// @param _tokenId The `tokenId` that was refunded
event Refund(
address indexed _from,
uint256 indexed _tokenId
);
/// @notice Emitted when a token is refunded
/// @dev Emitted by `refundFrom`
/// @param _sender The account that sent the refund
/// @param _from The account whose assets are refunded
/// @param _tokenId The `tokenId` that was refunded
event RefundFrom(
address indexed _sender,
address indexed _from,
uint256 indexed _tokenId
);
/// @notice As long as the refund is active for the given `tokenId`, refunds the user
/// @dev Make sure to check that the user has the token, and be aware of potential re-entrancy vectors
/// @param tokenId The `tokenId` to refund
function refund(uint256 tokenId) external;
/// @notice As long as the refund is active and the sender has sufficient approval, refund the token and send the ether to the sender
/// @dev Make sure to check that the user has the token, and be aware of potential re-entrancy vectors
/// The ether goes to msg.sender.
/// @param from The user from which to refund the token
/// @param tokenId The `tokenId` to refund
function refundFrom(address from, uint256 tokenId) external;
/// @notice Gets the refund price of the specific `tokenId`
/// @param tokenId The `tokenId` to query
/// @return _wei The amount of ether (in wei) that would be refunded
function refundOf(uint256 tokenId) external view returns (uint256 _wei);
/// @notice Gets the first block for which the refund is not active for a given `tokenId`
/// @param tokenId The `tokenId` to query
/// @return block The first block where token cannot be refunded
function refundDeadlineOf(uint256 tokenId) external view returns (uint256 block);
}
Refund
event Refund(
address indexed _from,
uint256 indexed _tokenId
);
概要
トークンが返金された時に発行されるイベント。
詳細
このイベントはrefund
関数によって発行され、トークンの返金が行われたときにブロックチェーンに記録されます。
パラメータ
-
_from
- 資産が返金されたアカウント。
-
_tokenId
- 返金されたトークンのID。
RefundFrom
event RefundFrom(
address indexed _sender,
address indexed _from,
uint256 indexed _tokenId
);
概要
代わりにトークンを返金した時に発行されるイベント。
詳細
このイベントはrefundFrom
関数によって発行され、他のアカウントに代わってトークンの返金が行われたときにブロックチェーンに記録されます。
パラメータ
-
_sender
- 返金を行ったアカウント。
-
_from
- 資産が返金されたアカウント。
-
_tokenId
- 返金されたトークンのID。
refund
function refund(uint256 tokenId) external;
概要
指定されたtokenId
について、返金がアクティブである限りユーザーに返金を行う関数。
詳細
この関数を実行する前に、ユーザーがそのトークンを保持していること、そして再入可能性の問題がないかを確認する必要があります。
引数
-
tokenId
- 返金するトークンのID。
refundFrom
function refundFrom(address from, uint256 tokenId) external;
概要
返金がアクティブであり送信者に十分な承認がある場合、トークンを返金しETHを送信者に送る関数。
詳細
ユーザーがトークンを保持していることを確認し、再入可能性の問題に注意しながらETHをmsg.sender
に送る必要があります。
引数
-
from
- トークンを返金するユーザー。
-
tokenId
- 返金するトークンのID。
refundOf
function refundOf(uint256 tokenId) external view returns (uint256 _wei);
概要
特定のtokenId
の返金価格を取得する関数。
詳細
指定されたトークンIDに対して返金されるETHの量をwei
単位で取得します。
引数
-
tokenId
- 問い合わせるトークンのID。
戻り値
-
_wei
- 返金されるイーサの量(
wei
単位)。
- 返金されるイーサの量(
refundDeadlineOf
function refundDeadlineOf(uint256 tokenId) external view returns (uint256 block);
概要
指定されたtokenId
に対して返金がアクティブでない最初のブロックを取得する関数。
詳細
トークンIDに基づいて、返金が可能でなくなる最初のブロック番号を取得します。
引数
-
tokenId
- 問い合わせるトークンのID。
戻り値
-
block
- トークンが返金できなくなる最初のブロック番号。
ERC721 Batch Refund Extension (Option)
// SPDX-License-Identifier: CC0-1.0;
import "ERC721Refund.sol";
/// @notice Batch Refundable ERC-721 tokens
/// @dev The ERC-165 identifier of this interface is ``
contract ERC721BatchRefund is ERC721Refund {
/// @notice Emitted when one or more tokens are batch refunded
/// @dev Emitted by `refundBatch`
/// @param _from The account whose assets are refunded
/// @param _tokenId The `tokenIds` that were refunded
event RefundBatch(
address indexed _from,
uint256[] _tokenIds // This may or may not be indexed
);
/// @notice Emitted when one or more tokens are batch refunded
/// @dev Emitted by `refundFromBatch`
/// @param _sender The account that sent the refund
/// @param _from The account whose assets are refunded
/// @param _tokenId The `tokenId` that was refunded
event RefundFromBatch(
address indexed _sender,
address indexed _from,
uint256 indexed _tokenId
);
/// @notice As long as the refund is active for the given `tokenIds`, refunds the user
/// @dev Make sure to check that the user has the tokens, and be aware of potential re-entrancy vectors
/// These must either succeed or fail together; there are no partial refunds.
/// @param tokenIds The `tokenId`s to refund
function refundBatch(uint256[] tokenIds) external;
/// @notice As long as the refund is active for the given `tokenIds` and the sender has sufficient approval, refund the tokens and send the ether to the sender
/// @dev Make sure to check that the user has the tokens, and be aware of potential re-entrancy vectors
/// The ether goes to msg.sender.
/// These must either succeed or fail together; there are no partial refunds.
/// @param from The user from which to refund the token
/// @param tokenIds The `tokenId`s to refund
function refundFromBatch(address from, uint256[] tokenIds) external;
}
RefundBatch
event RefundBatch(
address indexed _from,
uint256[] _tokenIds
);
概要
一つまたは複数のトークンが一括で返金された時に発行されるイベント。
詳細
このイベントはrefundBatch
関数によって発行され、複数のトークンが一括で返金された際にブロックチェーンに記録されます。
パラメータ
-
_from
- 資産が返金されたアカウント。
-
_tokenIds
- 返金されたトークンIDの配列。
RefundFromBatch
event RefundFromBatch(
address indexed _sender,
address indexed _from,
uint256 indexed _tokenId
);
概要
一つまたは複数のトークンが他のアカウントに代わって一括で返金された時に発行されるイベント。
詳細
このイベントはrefundFromBatch
関数によって発行され、別のアカウントが代表して複数のトークンを一括で返金した際にブロックチェーンに記録されます。
パラメータ
-
_sender
- 返金を送ったアカウント。
-
_from
- 資産が返金されたアカウント。
-
_tokenId
- 返金されたトークンID。
- このパラメータはインデックス付きです。
refundBatch
function refundBatch(uint256[] tokenIds) external;
概要
指定されたtokenIds
について、返金がアクティブである限りユーザーに一括返金を行う関数。
詳細
ユーザーが指定されたトークンを所有しているかを確認し、再入可能性の問題がないかを注意してください。
この操作は、全てのトークンの返金が成功するか、または失敗するかのどちらかであり、部分的な返金はありません。
引数
-
tokenIds
- 返金するトークンIDの配列。
refundFromBatch
function refundFromBatch(address from, uint256[] tokenIds) external;
概要
指定されたtokenIds
について、返金がアクティブであり、かつ送信者に十分な承認がある場合、トークンを一括返金しETHを送信者に送る関数。
詳細
ユーザーが指定されたトークンを所有しているかを確認し、再入可能性の問題がないかを注意してください。
イーサはmsg.sender
に送られます。
この操作は、全てのトークンの返金が成功するか失敗するかのどちらかであり、部分的な返金はありません。
引数
-
from
- トークンを返金するユーザー。
-
tokenIds
- 返金するトークンIDの配列。
ERC1155 Refund Extension
Refund
event Refund(
address indexed _from,
uint256 indexed _tokenId,
uint256 _amount
);
概要
トークンが返金された時に発行されるイベント。
詳細
refund
関数によってこのイベントが発行され、返金をリクエストしたアカウント、返金されたトークンのID、および返金されたトークンの量に関する情報がブロックチェーンに記録されます。
パラメータ
-
_from
- 返金をリクエストしたアカウント。
-
_tokenId
- 返金されたトークンのID。
-
_amount
- 返金されたトークンの量。
RefundFrom
event RefundFrom(
address indexed _sender,
address indexed _from,
uint256 indexed _tokenId
);
概要
他のアカウントに代わってトークンが返金された時に発行されるイベント。
詳細
refundFrom
関数によってこのイベントが発行され、返金を送ったアカウント、資産が返金されたアカウント、返金されたトークンのIDに関する情報がブロックチェーンに記録されます。
ただし、このイベント定義では、返金されたトークンの量(_amount
)が含まれていない点に注意してください。
パラメータ
-
_sender
- 返金を送ったアカウント。
-
_from
- 資産が返金されたアカウント。
-
_tokenId
- 返金されたトークンのID。
refund
function refund(uint256 tokenId, uint256 amount) external;
概要
指定されたtokenId
に対して返金がアクティブである限り、ユーザーに返金を行う関数。
詳細
ユーザーが十分なトークンを持っていること、および再入可能性の問題がないことを確認してください。
返金処理は、指定されたトークンIDと返金する量に基づいて行われます。
引数
-
tokenId
- 返金するトークンのID。
-
amount
- 返金するトークンの量。
refundFrom
function refundFrom(address from, uint256 tokenId, uint256 amount) external;
概要
返金がアクティブであり、送信者に十分な承認がある限りトークンを返金しETHを送信者に送る関数。
詳細
ユーザーが十分なトークンを持っていることを確認し、再入可能性の問題に注意してください。
ETHはmsg.sender
に送られます。
返金処理は、トークンを返金するユーザー、指定されたトークンID、返金する量に基づいて行われます。
引数
-
from
- トークンを返金するユーザー。
-
tokenId
- 返金するトークンのID。
-
amount
- 返金するトークンの量。
refundOf
function refundOf(uint256 tokenId) external view returns (uint256 _wei);
概要
特定のtokenId
の返金価格を取得する関数。
詳細
指定されたトークンIDの一つあたりの返金されるETHの量(wei
単位)を返します。
引数
-
tokenId
- 問い合わせるトークンのID。
戻り値
-
_wei
- 単一のトークンに対する返金額(
wei
単位)。
- 単一のトークンに対する返金額(
refundDeadlineOf
function refundDeadlineOf(uint256 tokenId) external view returns (uint256 block);
概要
指定されたtokenId
に対して返金がアクティブでない最初のブロックを取得する関数。
詳細
トークンIDに基づいて、返金が可能でなくなる最初のブロック番号を取得します。
引数
-
tokenId
- 問い合わせるトークンのID。
戻り値
-
block
- トークンが返金できなくなる最初のブロック番号。
ERC1155 Batch Refund Extension (Option)
// SPDX-License-Identifier: CC0-1.0;
import "ERC1155Refund.sol";
/// @notice Batch Refundable ERC-1155 tokens
/// @dev The ERC-165 identifier of this interface is ``
contract ERC1155BatchRefund is ERC1155Refund {
/// @notice Emitted when one or more tokens are batch refunded
/// @dev Emitted by `refundBatch`
/// @param _from The account that requested a refund
/// @param _tokenIds The `tokenIds` that were refunded
/// @param _amounts The amount of each `tokenId` that was refunded
event RefundBatch(
address indexed _from,
uint256[] _tokenIds, // This may or may not be indexed
uint256[] _amounts
);
/// @notice Emitted when one or more tokens are batch refunded
/// @dev Emitted by `refundFromBatch`
/// @param _sender The account that sent the refund
/// @param _from The account whose assets are refunded
/// @param _tokenIds The `tokenIds` that was refunded
/// @param _amounts The amount of each `tokenId` that was refunded
event RefundFromBatch(
address indexed _sender,
address indexed _from,
uint256[] _tokenId, // This may or may not be indexed
uint256[] _amounts
);
/// @notice As long as the refund is active for the given `tokenIds`, refunds the user
/// @dev Make sure to check that the user has enough tokens, and be aware of potential re-entrancy vectors
/// These must either succeed or fail together; there are no partial refunds.
/// @param tokenIds The `tokenId`s to refund
/// @param amounts The amount of each `tokenId` to refund
function refundBatch(uint256[] tokenIds, uint256[] amounts) external;
/// @notice As long as the refund is active for the given `tokenIds` and the sender has sufficient approval, refund the tokens and send the ether to the sender
/// @dev Make sure to check that the user has the tokens, and be aware of potential re-entrancy vectors
/// The ether goes to msg.sender.
/// These must either succeed or fail together; there are no partial refunds.
/// @param from The user from which to refund the token
/// @param tokenIds The `tokenId`s to refund
/// @param amounts The amount of each `tokenId` to refund
function refundFromBatch(address from, uint256[] tokenIds, uint256[] amounts external;
}
RefundBatch
event RefundBatch(
address indexed _from,
uint256[] _tokenIds,
uint256[] _amounts
);
概要
複数のトークンが一括で返金された時に発行されるイベント。
詳細
このイベントはrefundBatch
関数によって発行され、返金を要求したアカウントと返金された各トークンIDとその量に関する情報がブロックチェーンに記録されます。
パラメータ
-
_from
- 返金を要求したアカウント。
-
_tokenIds
- 返金されたトークンIDの配列。
-
_amounts
- 各
tokenId
に返金された量の配列。
- 各
RefundFromBatch
event RefundFromBatch(
address indexed _sender,
address indexed _from,
uint256[] _tokenIds,
uint256[] _amounts
);
概要
他のアカウントに代わって複数のトークンが一括で返金された時に発行されるイベント。
詳細
このイベントはrefundFromBatch
関数によって発行され、返金を送ったアカウントと資産が返金されたアカウント、返金されたトークンIDとその量に関する情報がブロックチェーンに記録されます。
パラメータ
-
_sender
- 返金を送ったアカウント。
-
_from
- 資産が返金されたアカウント。
-
_tokenIds
- 返金されたトークンIDの配列。
- この配列はインデックス付けされているかもしれません。
-
_amounts
- 各
tokenId
に返金された量の配列。
- 各
refundBatch
function refundBatch(uint256[] tokenIds, uint256[] amounts) external;
概要
指定されたtokenIds
について返金がアクティブである限り、ユーザーにそれぞれのtokenId
の指定された量を一括返金する関数。
詳細
ユーザーが十分な量のトークンを持っているかを確認し、再入可能性のリスクに注意する必要があります。
全ての返金処理は同時に成功するか、失敗するかのどちらかであり、部分的な返金は行われません。
引数
-
tokenIds
- 返金するトークンのIDの配列。
-
amounts
- 各
tokenId
に返金する量の配列。
- 各
refundFromBatch
function refundFromBatch(address from, uint256[] tokenIds, uint256[] amounts) external;
概要
指定されたtokenIds
について返金がアクティブであり、送信者に十分な承認がある場合トークンを一括返金しETHを送信者に送る関数。
詳細
ユーザーが十分な量のトークンを持っているかを確認し、再入可能性のリスクに注意する必要があります。
ETHはmsg.sender
に送られます。
全ての返金処理は同時に成功するか、失敗するかのどちらかであり、部分的な返金は行われません。
引数
-
from
- トークンを返金するユーザー。
-
tokenIds
- 返金するトークンのIDの配列。
-
amounts
- 各
tokenId
に返金する量の配列。
- 各
補足
refundDeadlineOf
関数は、返金可能な期限をブロック番号で設定しています。
これは、タイムスタンプよりもブロック番号の方が信頼性が高いためです。
refund
、refundOf
、refundDeadlineOf
という関数名は、ERC20、ERC721、ERC1155といった既存のコントラクト規格に合わせて名付けられています。
ERC165は、DAppsがコントラクトとやり取りする際の内省を容易にするために必要です。
これがないと、DAppsはコントラクトが特定のインターフェースをサポートしているかどうかを効率的に確認できません。
カスタムERC20トークンはサポートされていません。
これは、システムの複雑性を不必要に高めるからです。
ただし、refundFrom
関数をDEXと組み合わせることで、カスタムトークンに対する返金機能を提供できます。
カスタムERC20トークンがサポートされない理由は、システムの複雑性を増加させるためです。
具体的には、カスタムERC20トークンは標準的なERC20インターフェースに加えて独自の機能や挙動を持つことが多く、それらをサポートするためには追加のコードを書く必要があります。
例えば、独自の手数料モデルを持つトークンや、特定の条件下でのみトランザクションを許可するトークンなどです。
これらの特殊な挙動を処理するためには、コントラクトに多くの例外処理や追加のセキュリティチェックを実装する必要があり、それが全体としてのシステムの複雑性を高めることになります。
一方で、refundFrom
関数を分散型取引所(DEX)と組み合わせることで、カスタムトークンに対する返金機能を実現できることがあります。
DEXは多種多様なトークンを扱うため、それらのトークンに特化した処理を行うことができます。
ユーザーがDEXを通じてカスタムトークンを交換する場合、DEXはそのトークンの特殊なルールを処理し、返金処理を実行することができるわけです。
この方法により、返金機能を持つコントラクト自体はシンプルに保ちつつ、カスタムトークンに対応する柔軟性をDEXが提供する形になります。
一括返金機能はオプションです。
将来的にアカウント抽象化が導入されると、こうした一括処理はさらに簡単になるでしょう。
しかし、現時点でも一括返金はガスコストを節約するために適切に実装されるべきです。
後方互換性
後方互換性の問題はありません。
セキュリティ考慮事項
refund
関数には、プログラムが予期せぬ方法で複数回呼び出されることによるセキュリティリスクが存在します。
このリスクを防ぐためには、ETHを送る操作を行う前にトークンが正しく破棄されているかを確認する必要があります。
これは「チェック、効果、やり取り(checks, effects, interactions)」の順番で処理を行うべきです。
まず最初に、セキュリティチェックを行い、次にトークンの破棄のような内部状態を変更する処理を実行し、最後にETHの送金のような外部コントラクトとのやり取りを行います。
この手順に従うことで、再入可能性によるリスクを軽減できます。
引用
elie222 (@elie222), Gavin John (@Pandapip1), "ERC-5507: Refundable Tokens," Ethereum Improvement Proposals, no. 5507, August 2022. [Online serial]. Available: https://eips.ethereum.org/EIPS/eip-5507.
最後に
今回は「ERC20、ERC721、ERC1155トークンに払い戻し機能の追加を提案している規格であるERC5507」についてまとめてきました!
いかがだったでしょうか?
質問などがある方は以下のTwitterのDMなどからお気軽に質問してください!
他の媒体でも情報発信しているのでぜひ他も見ていってください!