Skip to content

Commit

Permalink
feat: add TOML cheatcode support (#518)
Browse files Browse the repository at this point in the history
* add StdToml, pending upstream TOML cheatcode support

* fix name

* pull in TOML cheatcode update

* update interface id

* add basic JSON and TOML test, update examples

* chore: struct names

* chore: fix function visibility warnings

---------

Co-authored-by: Matt Solomon <[email protected]>
  • Loading branch information
zerosnacks and mds1 committed Mar 11, 2024
1 parent 1432518 commit b6a506d
Show file tree
Hide file tree
Showing 10 changed files with 377 additions and 13 deletions.
18 changes: 7 additions & 11 deletions src/StdJson.sol
Original file line number Diff line number Diff line change
Expand Up @@ -9,21 +9,17 @@ import {VmSafe} from "./Vm.sol";
// To parse:
// ```
// using stdJson for string;
// string memory json = vm.readFile("some_path");
// json.parseUint("<json_path>");
// string memory json = vm.readFile("<some_path>");
// json.readUint("<json_path>");
// ```
// To write:
// ```
// using stdJson for string;
// string memory json = "deploymentArtifact";
// Contract contract = new Contract();
// json.serialize("contractAddress", address(contract));
// json = json.serialize("deploymentTimes", uint(1));
// // store the stringified JSON to the 'json' variable we have been using as a key
// // as we won't need it any longer
// string memory json2 = "finalArtifact";
// string memory final = json2.serialize("depArtifact", json);
// final.write("<some_path>");
// string memory json = "json";
// json.serialize("a", uint256(123));
// string memory semiFinal = json.serialize("b", string("test"));
// string memory finalJson = json.serialize("c", semiFinal);
// finalJson.write("<some_path>");
// ```

library stdJson {
Expand Down
179 changes: 179 additions & 0 deletions src/StdToml.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.6.0 <0.9.0;

pragma experimental ABIEncoderV2;

import {VmSafe} from "./Vm.sol";

// Helpers for parsing and writing TOML files
// To parse:
// ```
// using stdToml for string;
// string memory toml = vm.readFile("<some_path>");
// toml.readUint("<json_path>");
// ```
// To write:
// ```
// using stdToml for string;
// string memory json = "json";
// json.serialize("a", uint256(123));
// string memory semiFinal = json.serialize("b", string("test"));
// string memory finalJson = json.serialize("c", semiFinal);
// finalJson.write("<some_path>");
// ```

library stdToml {
VmSafe private constant vm = VmSafe(address(uint160(uint256(keccak256("hevm cheat code")))));

function parseRaw(string memory toml, string memory key) internal pure returns (bytes memory) {
return vm.parseToml(toml, key);
}

function readUint(string memory toml, string memory key) internal pure returns (uint256) {
return vm.parseTomlUint(toml, key);
}

function readUintArray(string memory toml, string memory key) internal pure returns (uint256[] memory) {
return vm.parseTomlUintArray(toml, key);
}

function readInt(string memory toml, string memory key) internal pure returns (int256) {
return vm.parseTomlInt(toml, key);
}

function readIntArray(string memory toml, string memory key) internal pure returns (int256[] memory) {
return vm.parseTomlIntArray(toml, key);
}

function readBytes32(string memory toml, string memory key) internal pure returns (bytes32) {
return vm.parseTomlBytes32(toml, key);
}

function readBytes32Array(string memory toml, string memory key) internal pure returns (bytes32[] memory) {
return vm.parseTomlBytes32Array(toml, key);
}

function readString(string memory toml, string memory key) internal pure returns (string memory) {
return vm.parseTomlString(toml, key);
}

function readStringArray(string memory toml, string memory key) internal pure returns (string[] memory) {
return vm.parseTomlStringArray(toml, key);
}

function readAddress(string memory toml, string memory key) internal pure returns (address) {
return vm.parseTomlAddress(toml, key);
}

function readAddressArray(string memory toml, string memory key) internal pure returns (address[] memory) {
return vm.parseTomlAddressArray(toml, key);
}

function readBool(string memory toml, string memory key) internal pure returns (bool) {
return vm.parseTomlBool(toml, key);
}

function readBoolArray(string memory toml, string memory key) internal pure returns (bool[] memory) {
return vm.parseTomlBoolArray(toml, key);
}

function readBytes(string memory toml, string memory key) internal pure returns (bytes memory) {
return vm.parseTomlBytes(toml, key);
}

function readBytesArray(string memory toml, string memory key) internal pure returns (bytes[] memory) {
return vm.parseTomlBytesArray(toml, key);
}

function serialize(string memory jsonKey, string memory rootObject) internal returns (string memory) {
return vm.serializeJson(jsonKey, rootObject);
}

function serialize(string memory jsonKey, string memory key, bool value) internal returns (string memory) {
return vm.serializeBool(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, bool[] memory value)
internal
returns (string memory)
{
return vm.serializeBool(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, uint256 value) internal returns (string memory) {
return vm.serializeUint(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, uint256[] memory value)
internal
returns (string memory)
{
return vm.serializeUint(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, int256 value) internal returns (string memory) {
return vm.serializeInt(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, int256[] memory value)
internal
returns (string memory)
{
return vm.serializeInt(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, address value) internal returns (string memory) {
return vm.serializeAddress(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, address[] memory value)
internal
returns (string memory)
{
return vm.serializeAddress(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, bytes32 value) internal returns (string memory) {
return vm.serializeBytes32(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, bytes32[] memory value)
internal
returns (string memory)
{
return vm.serializeBytes32(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, bytes memory value) internal returns (string memory) {
return vm.serializeBytes(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, bytes[] memory value)
internal
returns (string memory)
{
return vm.serializeBytes(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, string memory value)
internal
returns (string memory)
{
return vm.serializeString(jsonKey, key, value);
}

function serialize(string memory jsonKey, string memory key, string[] memory value)
internal
returns (string memory)
{
return vm.serializeString(jsonKey, key, value);
}

function write(string memory jsonKey, string memory path) internal {
vm.writeToml(jsonKey, path);
}

function write(string memory jsonKey, string memory path, string memory valueKey) internal {
vm.writeToml(jsonKey, path, valueKey);
}
}
1 change: 1 addition & 0 deletions src/Test.sol
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import {stdJson} from "./StdJson.sol";
import {stdMath} from "./StdMath.sol";
import {StdStorage, stdStorage} from "./StdStorage.sol";
import {StdStyle} from "./StdStyle.sol";
import {stdToml} from "./StdToml.sol";
import {StdUtils} from "./StdUtils.sol";
import {Vm} from "./Vm.sol";

Expand Down
77 changes: 76 additions & 1 deletion src/Vm.sol

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions test/StdCheats.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ pragma solidity >=0.7.0 <0.9.0;
import "../src/StdCheats.sol";
import "../src/Test.sol";
import "../src/StdJson.sol";
import "../src/StdToml.sol";
import "../src/interfaces/IERC20.sol";

contract StdCheatsTest is Test {
Expand Down
49 changes: 49 additions & 0 deletions test/StdJson.t.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.7.0 <0.9.0;

import "../src/Test.sol";

contract StdJsonTest is Test {
using stdJson for string;

string root;
string path;

function setUp() public {
root = vm.projectRoot();
path = string.concat(root, "/test/fixtures/test.json");
}

struct SimpleJson {
uint256 a;
string b;
}

struct NestedJson {
uint256 a;
string b;
SimpleJson c;
}

function test_readJson() public view {
string memory json = vm.readFile(path);
assertEq(json.readUint(".a"), 123);
}

function test_writeJson() public {
string memory json = "json";
json.serialize("a", uint256(123));
string memory semiFinal = json.serialize("b", string("test"));
string memory finalJson = json.serialize("c", semiFinal);
finalJson.write(path);

string memory json_ = vm.readFile(path);
bytes memory data = json_.parseRaw("$");
NestedJson memory decodedData = abi.decode(data, (NestedJson));

assertEq(decodedData.a, 123);
assertEq(decodedData.b, "test");
assertEq(decodedData.c.a, 123);
assertEq(decodedData.c.b, "test");
}
}
Loading

0 comments on commit b6a506d

Please sign in to comment.