fix: harden V1 deployment manifests

This commit is contained in:
golem
2026-08-21 02:36:17 -06:00
parent 52935acf5e
commit be8f01ea4e
8 changed files with 252 additions and 50 deletions
+75 -1
View File
@@ -14,7 +14,7 @@ contract ScriptPreflightHarness is DemoScript {
_requireSupportedChain(chainId);
}
function deriveLocalActor(uint256 chainId, uint32 index) external returns (address actor) {
function deriveLocalActor(uint256 chainId, uint32 index) external pure returns (address actor) {
(, actor) = _deriveLocalActor(chainId, index);
}
@@ -29,6 +29,10 @@ contract ScriptPreflightHarness is DemoScript {
function serializeManifest(Manifest calldata manifest) external returns (string memory) {
return _serializeManifest(manifest);
}
function educationalWarning() external pure returns (string memory) {
return _educationalWarning();
}
}
contract ScriptPreflightTest is Test {
@@ -121,6 +125,50 @@ contract ScriptPreflightTest is Test {
harness.readManifest(path, true);
}
function testManifestRejectsNonParallelActorArrays() public {
string memory path = _writeManifest(31337, 1, TOKEN, PROXY, IMPLEMENTATION);
_etchManifestContracts();
vm.writeJson('["owner","Alice"]', path, ".actorLabels");
vm.expectRevert(DemoScript.InvalidActorConfiguration.selector);
harness.readManifest(path, true);
}
function testAnvilManifestRejectsUnexpectedActorLabels() public {
string memory path = _writeManifest(31337, 1, TOKEN, PROXY, IMPLEMENTATION);
_etchManifestContracts();
vm.writeJson('["owner","Mallory","Bob"]', path, ".actorLabels");
vm.expectRevert(DemoScript.InvalidActorConfiguration.selector);
harness.readManifest(path, true);
}
function testAnvilManifestRequiresOwnerAtActorZero() public {
string memory path = _writeManifest(31337, 1, TOKEN, PROXY, IMPLEMENTATION);
_etchManifestContracts();
vm.writeJson(
string.concat(
'["', vm.toString(ALICE), '","', vm.toString(OWNER), '","0x3C44CdDdB6a900fa2b585dd299e03d12FA4293BC"]'
),
path,
".actors"
);
vm.expectRevert(DemoScript.InvalidActorConfiguration.selector);
harness.readManifest(path, true);
}
function testBaseManifestRequiresOnlyOwnerActor() public {
string memory path = _writeBaseManifest();
vm.chainId(84532);
_etchManifestContracts();
vm.writeJson('["owner","Alice"]', path, ".actorLabels");
vm.writeJson(string.concat('["', vm.toString(OWNER), '","', vm.toString(ALICE), '"]'), path, ".actors");
vm.expectRevert(DemoScript.InvalidActorConfiguration.selector);
harness.readManifest(path, true);
}
function testEducationalWarningIsExact() public view {
assertEq(harness.educationalWarning(), unicode"Educational demo — mock token — never use real funds.");
}
function testSerializedManifestContainsPublicAddressesAndNoSecrets() public {
DemoScript.Manifest memory manifest = DemoScript.Manifest({
schemaVersion: 1,
@@ -245,6 +293,32 @@ contract ScriptPreflightTest is Test {
manifest = harness.readManifest(path, true);
}
function _writeBaseManifest() internal returns (string memory path) {
path = string.concat(fixtureDir, "/base-manifest.json");
vm.writeFile(
path,
string.concat(
'{"schemaVersion":1,"network":"base-sepolia","chainId":84532,"deploymentBlock":1,"rpcUrl":"https://sepolia.base.org","explorerUrl":"https://sepolia.basescan.org","token":"',
vm.toString(TOKEN),
'","proxy":"',
vm.toString(PROXY),
'","implementation":"',
vm.toString(IMPLEMENTATION),
'","owner":"',
vm.toString(OWNER),
'","actorLabels":["owner"],"actors":["',
vm.toString(OWNER),
'"]}'
)
);
}
function _etchManifestContracts() internal {
vm.etch(TOKEN, hex"00");
vm.etch(PROXY, hex"00");
vm.etch(IMPLEMENTATION, hex"00");
}
function _labels() internal pure returns (string[] memory labels) {
labels = new string[](3);
labels[0] = "owner";