SymbioticISM.t.sol
Обзор
Файл SymbioticISM.t.sol содержит набор тестов для смарт-контракта SymbioticISM, реализующего механизм межцепочечной верификации сообщений в экосистеме блокчейнов. Этот тестовый контракт обеспечивает проверку ключевой логики контракта SymbioticISM, включая добавление валидаторов, запросы верификации сообщений, подтверждение сообщений валидаторами, достижение кворума, а также механизмы обработки ошибок и экстренного подтверждения сообщений.
Данные тесты написаны с использованием фреймворка Forge и библиотеки forge-std/Test.sol, что позволяет имитировать различные сценарии и взаимодействия с контрактом SymbioticISM. Основная цель — гарантировать корректность и надежность механизма верификации сообщений, который используется для обеспечения безопасности и достоверности межцепочечных коммуникаций.
Подробное описание класса и методов
Контракт SymbioticISMTest
Это тестовый контракт, наследующийся от Test (часть Forge), который содержит набор методов для тестирования функционала SymbioticISM.
Поля
SymbioticISM public ism — экземпляр тестируемого контракта.
address public admin— адрес администратора контракта.address public validator1,validator2,validator3— адреса валидаторов.address public user— адрес пользователя для тестирования.uint256 public validator1Key,validator2Key,validator3Key— приватные ключи валидаторов (используются для генерации подписей).
События
MessageVerificationRequested— эмитируется при запросе верификации сообщения.ValidatorVerified— эмитируется при подтверждении сообщения отдельным валидатором.MessageVerified— эмитируется при достижении кворума и окончательном подтверждении сообщения.
Методы
function setUp() public
Инициализация тестовой среды:
Генерирует адреса валидаторов на основе приватных ключей.
Создаёт экземпляр
SymbioticISMс администратором.Добавляет валидаторов в контракт.
Добавляет поддерживаемые домены (Ethereum, Polygon, Arbitrum).
Использование:
Автоматически вызывается перед каждым тестом для подготовки состояния.
function testRequestVerification() public
Тестирует процесс запроса верификации сообщения:
Создаёт тестовое сообщение
HyperlaneMessage.Вызывает функцию
requestVerificationконтрактаSymbioticISM.Проверяет, что событие
MessageVerificationRequestedэмитировано корректно.Проверяет статус верификации сообщения (ожидается
PENDING).Проверяет, что количество валидаторов равно нулю, а требуемый кворум — 2 (67% от 3).
function testVerifyMessage() public
Тестирует подтверждение сообщения одним валидатором:
Запрашивает верификацию сообщения.
Формирует подпись валидатора.
Вызывает
verifyMessageс подписью.Проверяет эмиссию события
ValidatorVerified.Проверяет, что статус остаётся
PENDING, количество валидаторов увеличилось до 1.
function testQuorumReached() public
Тестирует сценарий достижения кворума валидаторов:
Запрашивает верификацию сообщения.
Получает подписи двух валидаторов.
Поочерёдно вызывает
verifyMessageдвумя валидаторами.Проверяет эмиссию события
MessageVerifiedпри достижении кворума.Проверяет, что статус меняется на
VERIFIED.Проверяет, что функция
isMessageVerifiedвозвращаетtrue.
function testISMVerifyInterface() public
Проверяет соответствие интерфейсу ISM:
Вызывает
verifyс закодированным сообщением до и после верификации.До верификации ожидает
false.После подтверждения от двух валидаторов —
true.
function testInvalidSignature() public
Проверяет обработку некорректных подписей:
Создаёт неправильную подпись (для другого сообщения).
Ожидает вызов revert с ошибкой
InvalidSignatureпри попытке верификации.
function testUnsupportedDomain() public
Проверяет обработку сообщений из неподдерживаемых доменов:
Создаёт сообщение с неподдерживаемым доменом.
Ожидает revert с ошибкой InvalidDomain при запросе верификации.
function testExpiredVerification() public
Проверяет поведение при истечении таймаута верификации:
Запрашивает верификацию сообщения.
Продвигает время на величину таймаута + 1.
Пытается подтвердить сообщение — ожидает revert
VerificationExpired.Проверяет, что статус сообщения изменён на
EXPIRED.
function testAddRemoveValidator() public
Проверяет функции добавления и удаления валидаторов:
Администратор добавляет нового валидатора — проверяется состояние.
Затем удаляет того же валидатора — проверяется состояние.
function testUpdateQuorumThreshold() public
Проверяет обновление порога кворума:
Администратор обновляет порог кворума.
Проверяет успешное обновление.
Проверяет, что некорректные значения (0 или >10000) приводят к revert с
InvalidQuorum.
function testEmergencyVerifyMessage() public
Проверяет экстренное подтверждение сообщения администратором:
Администратор вызывает
emergencyVerifyMessage.Проверяет эмиссию события
MessageVerifiedс 0 валидаторов.Проверяет, что сообщение помечено как подтверждённое.
function testPauseUnpause() public
Проверяет работу механизма паузы:
Администратор ставит контракт на паузу.
Проверяет, что в паузе нельзя запросить верификацию.
Снимает паузу, проверяет восстановление функционала.
function testFuzzVerification(bytes32 messageId, uint32 origin, uint32 destination) public
Фаззинг-тестирование запроса верификации:
Генерирует случайные, но валидные параметры.
Добавляет домены, если они ещё не поддерживаются.
Запрашивает верификацию.
Проверяет корректность статуса и кворума.
Важные детали реализации и алгоритмы
Кворум валидаторов: Порог подтверждения сообщения устанавливается в 67% от общего числа активных валидаторов. Для 3 валидаторов кворум равен 2.
Подписи: Для подтверждения сообщения валидаторы должны подписывать хэш сообщения в формате Ethereum Signed Message, что обеспечивает совместимость с подписными стандартами Ethereum.
Таймаут верификации: Есть ограничение по времени на подтверждение сообщения. Если оно превышено, сообщения считаются просроченными.
Административные функции: Администратор может добавлять/удалять валидаторов, менять порог кворума, ставить контракт на паузу и экстренно подтверждать сообщения.
Поддержка доменов: Верификация возможна только для сообщений из поддерживаемых доменов (chain IDs), таких как Ethereum (1), Polygon (137), Arbitrum (42161).
Ошибки и revert: В контракте используются специфичные ошибки Solidity (
InvalidSignature, InvalidDomain,VerificationExpired,InvalidQuorum), которые позволяют точечно ловить исключения.
Взаимодействия с другими частями системы
Импортируется и тестируется контракт
SymbioticISMиз../../src/crosschain/SymbioticISM.sol.Используется библиотека
forge-std/Test.solдля создания тестов и управления тестовым окружением (например,vmдля управления вызовами, подписанием сообщений, временем).Тесты моделируют поведение валидаторов, администраторов и пользователей, взаимодействующих с
SymbioticISM.В рамках системы
SymbioticISMслужит для обеспечения безопасности сообщений между разными блокчейнами (cross-chain communication), где верификация сообщений критична для предотвращения атак и мошенничества.
Диаграмма структуры класса
classDiagram
class SymbioticISMTest {
+SymbioticISM ism
+address admin
+address validator1
+address validator2
+address validator3
+address user
+uint256 validator1Key
+uint256 validator2Key
+uint256 validator3Key
+setUp()
+testRequestVerification()
+testVerifyMessage()
+testQuorumReached()
+testISMVerifyInterface()
+testInvalidSignature()
+testUnsupportedDomain()
+testExpiredVerification()
+testAddRemoveValidator()
+testUpdateQuorumThreshold()
+testEmergencyVerifyMessage()
+testPauseUnpause()
+testFuzzVerification(bytes32,uint32,uint32)
}
Пример использования (из тестов)
function exampleRequestAndVerify() public {
SymbioticISM.HyperlaneMessage memory message = SymbioticISM.HyperlaneMessage({
messageId: keccak256("example message"),
origin: 1,
destination: 137,
sender: bytes32(uint256(uint160(address(this)))),
recipient: bytes32(uint256(uint160(user))),
body: "example body",
metadata: "example metadata"
});
// Запрос верификации
bytes32 msgId = ism.requestVerification(message);
// Валидатор подписывает сообщение
bytes32 ethSignedHash = keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", msgId));
(uint8 v, bytes32 r, bytes32 s) = vm.sign(validator1Key, ethSignedHash);
bytes memory signature = abi.encodePacked(r, s, v);
// Валидатор подтверждает сообщение
vm.prank(validator1);
ism.verifyMessage(msgId, signature);
}
Заключение
SymbioticISM.t.sol — это тщательно проработанный набор unit-тестов, обеспечивающих качество и безопасность реализации контракта SymbioticISM. Тесты охватывают ключевые сценарии, включая нормальные случаи, ошибки и экстренные ситуации, что критично для кросс-чейн системы с высокой степенью доверия и безопасности.