Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add Factories plugin #749

Closed
wants to merge 27 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
b1604b3
feat: add factories
yonadaa May 7, 2023
154cc78
feat: add script to create instances
yonadaa May 8, 2023
9ea37b5
feat: add encodeKey, refactor
yonadaa May 8, 2023
343d6b4
feat: remove encodekey
yonadaa May 9, 2023
77cc3e1
Merge branch 'main' into add-factories
yonadaa May 9, 2023
eadaa34
feat: add templates to examples
yonadaa May 9, 2023
6f40b75
feat: add TemplatesModule
yonadaa May 10, 2023
bfc8f14
test: add test and gas-report in world
yonadaa May 10, 2023
14b426a
feat: add gas report to cli
yonadaa May 10, 2023
1940c6a
refactor: remove gas report from cli
yonadaa May 10, 2023
a92cefe
Merge remote-tracking branch 'origin/main' into add-factories
yonadaa May 11, 2023
1e5be77
refactor: simplify config gen
yonadaa May 14, 2023
e7a8fc7
chore: run configgen on all repos
yonadaa May 14, 2023
bfeb51c
Merge remote-tracking branch 'origin/main' into add-factories
yonadaa May 15, 2023
af8f946
chore: remove unused vite.config files
yonadaa May 15, 2023
96e9fc6
fix: checkout docs package.json
yonadaa May 15, 2023
000614c
refactor: add createTemplate method
yonadaa May 15, 2023
105db5e
refactor: rename to FactoryModule
yonadaa May 15, 2023
221c5e9
chore: run init in example
yonadaa May 15, 2023
fca2ddd
refactor: delete outdated templateSystem
yonadaa May 15, 2023
f05b445
Merge remote-tracking branch 'origin/main' into add-factories
yonadaa May 30, 2023
1e5c7be
chore: update after merge
yonadaa May 30, 2023
62a433b
fix: use correct types after merge
yonadaa May 30, 2023
fe7077e
feat: remove config type codegen
yonadaa Jun 1, 2023
1561ce0
Merge remote-tracking branch 'origin/main' into add-factories
yonadaa Jun 1, 2023
63cca29
feat: remove seperate template config file
yonadaa Jun 2, 2023
944465c
feat: add factory plugin
yonadaa Jun 2, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 14 additions & 1 deletion examples/minimal/packages/contracts/mud.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,11 @@ import { mudConfig } from "@latticexyz/world/register";
* so we suggest using MODE for production deployments.
*/
import "@latticexyz/world/snapsync";
import "@latticexyz/world/factory";
import { resolveTableId } from "@latticexyz/config";
import { Templates } from "@latticexyz/store";

export default mudConfig({
const config = mudConfig({
snapSync: true,
systems: {
IncrementSystem: {
Expand Down Expand Up @@ -53,3 +55,14 @@ export default mudConfig({
},
],
});

const templates: Templates<typeof config> = {
Simple: {
CounterTable: { value: 420 },
},
};

export default {
...config,
templates,
};
3 changes: 2 additions & 1 deletion examples/minimal/packages/contracts/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,12 @@
"deploy:testnet": "pnpm run initialize && mud deploy --profile=lattice-testnet",
"dev": "pnpm mud dev-contracts --tsgenOutput ../client-react/src/mud",
"dev:phaser": "pnpm mud dev-contracts --tsgenOutput ../client-phaser/src/mud",
"initialize": "pnpm run tablegen && pnpm run worldgen && pnpm run build && pnpm run worldtypes && pnpm run tsgen",
"initialize": "pnpm run tablegen && pnpm run worldgen && pnpm run templategen && pnpm run build && pnpm run worldtypes && pnpm run tsgen",
"lint": "pnpm run prettier && pnpm run solhint",
"prettier": "prettier --write 'src/**/*.sol'",
"solhint": "solhint --config ./.solhint.json 'src/**/*.sol' --fix",
"tablegen": "mud tablegen",
"templategen": "mud templategen",
"test": "mud test",
"tsgen": "mud tsgen --configPath mud.config.ts --out ../client-vanilla/src/mud && mud tsgen --configPath mud.config.ts --out ../client-react/src/mud && mud tsgen --configPath mud.config.ts --out ../client-phaser/src/mud",
"worldgen": "mud worldgen",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { SimpleTemplate, SimpleTemplateId } from "./templates/SimpleTemplate.sol";
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { IStore } from "@latticexyz/store/src/IStore.sol";

import { SimpleTemplate } from "../Templates.sol";

function createTemplates() {
SimpleTemplate();
}

function createTemplates(IStore store) {
SimpleTemplate(store);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { IStore } from "@latticexyz/store/src/IStore.sol";
import { FactoryContent } from "@latticexyz/world/src/modules/factory/tables/FactoryContent.sol";
import { FactoryIndex } from "@latticexyz/world/src/modules/factory/tables/FactoryIndex.sol";

import { CounterTable, CounterTableTableId } from "../tables/CounterTable.sol";

bytes32 constant templateId = "Simple";
bytes32 constant SimpleTemplateId = templateId;
uint256 constant LENGTH = 1;

function SimpleTemplate() {
bytes32[] memory tableIds = new bytes32[](LENGTH);
tableIds[0] = CounterTableTableId;
FactoryIndex.set(templateId, tableIds);

FactoryContent.set(templateId, CounterTableTableId, CounterTable.encode(420));
}

function SimpleTemplate(IStore store) {
bytes32[] memory tableIds = new bytes32[](LENGTH);
tableIds[0] = CounterTableTableId;
FactoryIndex.set(store, templateId, tableIds);

FactoryContent.set(store, templateId, CounterTableTableId, CounterTable.encode(420));
}
39 changes: 39 additions & 0 deletions examples/minimal/packages/contracts/test/TemplateTest.t.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

import "forge-std/Test.sol";
import { MudV2Test } from "@latticexyz/std-contracts/src/test/MudV2Test.t.sol";
import { createInstance } from "@latticexyz/world/src/modules/factory/createInstance.sol";
import { FactoryContent } from "@latticexyz/world/src/modules/factory/tables/FactoryContent.sol";

import { createTemplates } from "../src/codegen/scripts/CreateTemplates.sol";

import { IWorld } from "../src/codegen/world/IWorld.sol";
import { CounterTable, CounterTableTableId } from "../src/codegen/Tables.sol";
import { SimpleTemplateId } from "../src/codegen/Templates.sol";

contract TemplateTest is MudV2Test {
IWorld world;

function setUp() public override {
super.setUp();
world = IWorld(worldAddress);
}

function testTemplates() public {
vm.startPrank(worldAddress);

// Create templates
createTemplates(world);

// Assert that the template content was set correctly
assertEq(FactoryContent.get(world, SimpleTemplateId, CounterTableTableId), CounterTable.encode(420));

bytes32[][] memory keys = new bytes32[][](1);
keys[0] = CounterTable.encodeKeyTuple("test");

createInstance(world, SimpleTemplateId, keys);

assertEq(CounterTable.get(world, keys[0][0]), 420);
}
}
6 changes: 6 additions & 0 deletions packages/cli/contracts/src/codegen/Templates.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { ExampleTemplate, ExampleTemplateId } from "./templates/ExampleTemplate.sol";
16 changes: 16 additions & 0 deletions packages/cli/contracts/src/codegen/scripts/CreateTemplates.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { IStore } from "@latticexyz/store/src/IStore.sol";

import { ExampleTemplate } from "../Templates.sol";

function createTemplates() {
ExampleTemplate();
}

function createTemplates(IStore store) {
ExampleTemplate(store);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

/* Autogenerated file. Do not edit manually. */

import { IStore } from "@latticexyz/store/src/IStore.sol";
import { FactoryContent } from "@latticexyz/world/src/modules/factory/tables/FactoryContent.sol";
import { FactoryIndex } from "@latticexyz/world/src/modules/factory/tables/FactoryIndex.sol";
import { Enum1, Enum2 } from "../Types.sol";

import { Statics, StaticsTableId } from "../tables/Statics.sol";

bytes32 constant templateId = "Example";
bytes32 constant ExampleTemplateId = templateId;
uint256 constant LENGTH = 1;

function ExampleTemplate() {
bytes32[] memory tableIds = new bytes32[](LENGTH);
tableIds[0] = StaticsTableId;
FactoryIndex.set(templateId, tableIds);

FactoryContent.set(
templateId,
StaticsTableId,
Statics.encode(1, 1, "0x0123", 0x71C7656EC7ab88b098defB751B7401B5f6d8976F, true, Enum1(uint8(1)), Enum2(uint8(0)))
);
}

function ExampleTemplate(IStore store) {
bytes32[] memory tableIds = new bytes32[](LENGTH);
tableIds[0] = StaticsTableId;
FactoryIndex.set(store, templateId, tableIds);

FactoryContent.set(
store,
templateId,
StaticsTableId,
Statics.encode(1, 1, "0x0123", 0x71C7656EC7ab88b098defB751B7401B5f6d8976F, true, Enum1(uint8(1)), Enum2(uint8(0)))
);
}
58 changes: 58 additions & 0 deletions packages/cli/contracts/test/Templategen.t.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;

import "forge-std/Test.sol";
import { StoreReadWithStubs } from "@latticexyz/store/src/StoreReadWithStubs.sol";
import { createInstance } from "@latticexyz/world/src/modules/factory/createInstance.sol";
import { FactoryContent } from "@latticexyz/world/src/modules/factory/tables/FactoryContent.sol";
import { FactoryIndex } from "@latticexyz/world/src/modules/factory/tables/FactoryIndex.sol";

import { Statics, StaticsTableId, StaticsData } from "../src/codegen/Tables.sol";
import { ExampleTemplateId } from "../src/codegen/Templates.sol";
import { createTemplates } from "../src/codegen/scripts/CreateTemplates.sol";

import { Enum1, Enum2 } from "../src/codegen/Types.sol";

contract TemplateTest is Test, StoreReadWithStubs {
function testTemplates() public {
Statics.registerSchema();
FactoryContent.registerSchema();
FactoryIndex.registerSchema();

// create a template
createTemplates();

// Assert that the template content was set correctly
assertEq(
FactoryContent.get(ExampleTemplateId, StaticsTableId),
Statics.encode(1, 1, "0x0123", 0x71C7656EC7ab88b098defB751B7401B5f6d8976F, true, Enum1.E2, Enum2.E1)
);

// Create a template instance
uint256 k1 = 1;
int32 k2 = -1;
bytes16 k3 = hex"02";
address k4 = address(123);
bool k5 = true;
Enum1 k6 = Enum1.E3;
Enum2 k7 = Enum2.E1;

bytes32[][] memory keys = new bytes32[][](1);
keys[0] = Statics.encodeKeyTuple(k1, k2, k3, k4, k5, k6, k7);

// create an instance of a template
createInstance(ExampleTemplateId, keys);

// Assert that the instance was created properly
StaticsData memory data = StaticsData(
1,
1,
"0x0123",
0x71C7656EC7ab88b098defB751B7401B5f6d8976F,
true,
Enum1.E2,
Enum2.E1
);
assertEq(abi.encode(Statics.get(k1, k2, k3, k4, k5, k6, k7)), abi.encode(data));
}
}
3 changes: 2 additions & 1 deletion packages/cli/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,9 @@
"clean:js": "rimraf dist",
"dev": "tsup --watch",
"generate-test-tables": "tsx ./scripts/generate-test-tables.ts",
"generate-test-templates": "tsx ./scripts/generate-test-templates.ts",
"lint": "eslint . --ext .ts",
"test": "tsc --noEmit && pnpm run generate-test-tables && forge test"
"test": "tsc --noEmit && pnpm run generate-test-tables && pnpm run generate-test-templates && forge test"
},
"dependencies": {
"@ethersproject/abi": "^5.7.0",
Expand Down
71 changes: 1 addition & 70 deletions packages/cli/scripts/generate-test-tables.ts
Original file line number Diff line number Diff line change
@@ -1,76 +1,7 @@
import path from "path";
import { tablegen } from "@latticexyz/store";
import { mudConfig } from "@latticexyz/world/register";
import { getSrcDirectory } from "@latticexyz/common/foundry";
import { logError } from "../src/utils/errors";

// This config is used only for tests.
// Aside from avoiding `mud.config.mts` in cli package (could cause issues),
// this also tests that mudConfig and tablegen can work as standalone functions
let config;
try {
config = mudConfig({
tables: {
Statics: {
keySchema: {
k1: "uint256",
k2: "int32",
k3: "bytes16",
k4: "address",
k5: "bool",
k6: "Enum1",
k7: "Enum2",
},
schema: {
v1: "uint256",
v2: "int32",
v3: "bytes16",
v4: "address",
v5: "bool",
v6: "Enum1",
v7: "Enum2",
},
},
Dynamics1: {
schema: {
staticB32: "bytes32[1]",
staticI32: "int32[2]",
staticU128: "uint128[3]",
staticAddrs: "address[4]",
staticBools: "bool[5]",
},
},
Dynamics2: {
schema: {
u64: "uint64[]",
str: "string",
b: "bytes",
},
},
Singleton: {
keySchema: {},
schema: {
v1: "int256",
v2: "uint32[2]",
v3: "uint32[2]",
v4: "uint32[1]",
},
dataStruct: false,
},
Ephemeral: {
schema: "uint256",
ephemeral: true,
},
},

enums: {
Enum1: ["E1", "E2", "E3"],
Enum2: ["E1"],
},
});
} catch (error: unknown) {
logError(error);
}
import config from "./test-config";

const srcDirectory = await getSrcDirectory();

Expand Down
31 changes: 31 additions & 0 deletions packages/cli/scripts/generate-test-templates.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import path from "path";
import { StoreConfig, Templates, templategen } from "@latticexyz/store";
import { getSrcDirectory } from "@latticexyz/common/foundry";
import config from "./test-config";

const templates: Templates<typeof config> = {
Example: {
Statics: {
v1: 1n,
v2: 1,
v3: "0x0123",
v4: "0x71C7656EC7ab88b098defB751B7401B5f6d8976F",
v5: true,
v6: 1,
v7: 0,
},
},
};

const srcDirectory = await getSrcDirectory();

const templateConfig: StoreConfig & { templates: any } = {
...config,
templates,
};

if (config !== undefined) {
templategen(templateConfig, path.join(srcDirectory, config.codegenDirectory));
} else {
process.exit(1);
}
Loading