Передача сообщений (запись)
Metalayer позволяет разработчикам отправлять произвольные сообщения между сетями. Это полезно для урегулирования намерений, выполнения управления и приложений с мульти-чейн приложениями.
Описание
Metalayer позволяет разработчикам отправлять произвольные сообщения между сетями. Передача сообщений Metalayer реализована как расширение протокола передачи сообщений Hyperlane.
Как работают сообщения в Metalayer
Контракт в сети-источнике вызывает
dispatch
, который отправляет полезную нагрузку контракту в сети назначения.Ретрансляторы Hyperlane безопасно передают сообщение.
Контракт-получатель обрабатывает сообщение, декодируя его.
Пример передачи сообщений
Полную документацию для разработчиков смотрите в разделе Кросс-чейн dApps.
Этот пример демонстрирует простую кросс-чейн систему передачи сообщений с использованием Metalayer. Мы создадим два контракта:
контракт отправителя, который отправляет сообщения
контракт получателя, который подсчитывает и хранит полученные сообщения
Hello World отправитель
Контракт отправителя должен:
Хранить адрес маршрутизатора и информацию о месте назначения
Рассчитывать стоимость газа для доставки сообщений
Форматировать и отправлять сообщения
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;
contract HelloSender {
// The MetalayerRouter on the local chain
IMetalayerRouter public immutable router;
// The domain (chain ID) where messages will be sent
uint32 public immutable destinationDomain;
// Estimated gas needed for message processing
uint256 private constant ESTIMATED_GAS_LIMIT = 100000;
constructor(
address _metalayerRouter,
uint32 _destinationDomain
) {
router = IMetalayerRouter(_metalayerRouter);
destinationDomain = _destinationDomain;
}
function sayHello(address recipient, string calldata message) external payable {
// Calculate required gas payment
uint256 gasPayment = router.quoteGasPayment(
destinationDomain,
ESTIMATED_GAS_LIMIT
);
require(msg.value >= gasPayment, "Insufficient gas payment");
// Format the message data
bytes memory callData = abi.encode(message);
// Create empty reads array since we're not querying data
ReadOperation[] memory reads = new ReadOperation[](0);
// Send the cross-chain message
router.dispatch{value: gasPayment}(
destinationDomain,
recipient,
reads,
callData,
true // Wait for finality
);
}
}
Hello World получатель
Контракт получателя должен:
Реализовать интерфейс IMetalayerRecipient
Хранить адрес маршрутизатора и проверять источники сообщений
Отслеживать полученные сообщения
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;
contract HelloReceiver is IMetalayerRecipient {
// The MetalayerRouter on this chain
IMetalayerRouter public immutable router;
// The domain (chain ID) where messages come from
uint32 public immutable sourceDomain;
// Message tracking
uint256 public messageCount;
mapping(uint256 => string) public messages;
mapping(uint256 => address) public senders;
constructor(
address _metalayerRouter,
uint32 _sourceDomain
) {
router = IMetalayerRouter(_metalayerRouter);
sourceDomain = _sourceDomain;
}
function handle(
uint32 _originDomain,
address _sender,
bytes calldata _message,
ReadOperation[] calldata _reads,
bytes[] calldata _readResults
) external payable {
// Verify message comes from our router
require(msg.sender == address(router), "Unauthorized router");
// Verify message comes from expected chain
require(_originDomain == sourceDomain, "Wrong source domain");
// Decode and store the message
string memory helloMessage = abi.decode(_message, (string));
messages[messageCount] = helloMessage;
senders[messageCount] = _sender;
messageCount++;
}
// View functions to read message history
function getMessageDetails(uint256 index) external view returns (
string memory message,
address sender
) {
require(index < messageCount, "Message index out of bounds");
return (messages[index], senders[index]);
}
}
Last updated