@latticexyz/cli 2.0.0-snapshot-test-32d38619 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. package/dist/chunk-QXUPZVZL.js +4 -0
  2. package/dist/chunk-QXUPZVZL.js.map +1 -0
  3. package/dist/commands-WWEJJZV4.js +36 -0
  4. package/dist/commands-WWEJJZV4.js.map +1 -0
  5. package/dist/errors-MZURIB7V.js +2 -0
  6. package/dist/errors-MZURIB7V.js.map +1 -0
  7. package/dist/index.js +0 -1
  8. package/dist/mud.js +1 -14
  9. package/dist/mud.js.map +1 -1
  10. package/package.json +21 -15
  11. package/src/build.ts +48 -0
  12. package/src/commands/build.ts +35 -0
  13. package/src/commands/deploy.ts +8 -31
  14. package/src/commands/dev-contracts.ts +80 -141
  15. package/src/commands/index.ts +2 -0
  16. package/src/commands/set-version.ts +24 -62
  17. package/src/commands/tablegen.ts +2 -2
  18. package/src/commands/test.ts +30 -36
  19. package/src/commands/trace.ts +15 -11
  20. package/src/commands/worldgen.ts +7 -6
  21. package/src/common.ts +1 -0
  22. package/src/debug.ts +10 -0
  23. package/src/deploy/common.ts +122 -0
  24. package/src/deploy/configToTables.ts +70 -0
  25. package/src/deploy/create2/README.md +13 -0
  26. package/src/deploy/create2/deployment.json +8 -0
  27. package/src/deploy/createPrepareDeploy.ts +28 -0
  28. package/src/deploy/debug.ts +10 -0
  29. package/src/deploy/deploy.ts +133 -0
  30. package/src/deploy/deployWorld.ts +38 -0
  31. package/src/deploy/ensureContract.ts +66 -0
  32. package/src/deploy/ensureContractsDeployed.ts +33 -0
  33. package/src/deploy/ensureDeployer.ts +75 -0
  34. package/src/deploy/ensureFunctions.ts +86 -0
  35. package/src/deploy/ensureModules.ts +79 -0
  36. package/src/deploy/ensureNamespaceOwner.ts +71 -0
  37. package/src/deploy/ensureSystems.ts +187 -0
  38. package/src/deploy/ensureTables.ts +64 -0
  39. package/src/deploy/ensureWorldFactory.ts +105 -0
  40. package/src/deploy/findLibraries.ts +36 -0
  41. package/src/deploy/getFunctions.ts +58 -0
  42. package/src/deploy/getResourceAccess.ts +51 -0
  43. package/src/deploy/getResourceIds.ts +31 -0
  44. package/src/deploy/getSystems.ts +47 -0
  45. package/src/deploy/getTableValue.ts +30 -0
  46. package/src/deploy/getTables.ts +59 -0
  47. package/src/deploy/getWorldDeploy.ts +39 -0
  48. package/src/deploy/logsToWorldDeploy.ts +49 -0
  49. package/src/deploy/orderByDependencies.ts +12 -0
  50. package/src/deploy/resolveConfig.ts +148 -0
  51. package/src/index.ts +1 -1
  52. package/src/mud.ts +37 -31
  53. package/src/mudPackages.ts +24 -0
  54. package/src/runDeploy.ts +149 -0
  55. package/src/utils/defaultModuleContracts.ts +30 -0
  56. package/src/utils/errors.ts +1 -1
  57. package/src/utils/findPlaceholders.ts +27 -0
  58. package/src/utils/getContractData.ts +38 -0
  59. package/src/utils/{utils/postDeploy.ts → postDeploy.ts} +2 -2
  60. package/src/utils/printMUD.ts +1 -1
  61. package/dist/chunk-WERDORTY.js +0 -11
  62. package/dist/chunk-WERDORTY.js.map +0 -1
  63. package/src/utils/deploy.ts +0 -255
  64. package/src/utils/deployHandler.ts +0 -93
  65. package/src/utils/modules/constants.ts +0 -23
  66. package/src/utils/modules/getInstallModuleCallData.ts +0 -27
  67. package/src/utils/modules/getUserModules.ts +0 -5
  68. package/src/utils/modules/types.ts +0 -14
  69. package/src/utils/systems/getGrantAccessCallData.ts +0 -29
  70. package/src/utils/systems/getRegisterFunctionSelectorsCallData.ts +0 -57
  71. package/src/utils/systems/getRegisterSystemCallData.ts +0 -17
  72. package/src/utils/systems/types.ts +0 -9
  73. package/src/utils/systems/utils.ts +0 -42
  74. package/src/utils/tables/getRegisterTableCallData.ts +0 -49
  75. package/src/utils/tables/getTableIds.ts +0 -21
  76. package/src/utils/tables/types.ts +0 -12
  77. package/src/utils/utils/confirmNonce.ts +0 -24
  78. package/src/utils/utils/deployContract.ts +0 -33
  79. package/src/utils/utils/fastTxExecute.ts +0 -56
  80. package/src/utils/utils/getChainId.ts +0 -10
  81. package/src/utils/utils/getContractData.ts +0 -29
  82. package/src/utils/utils/setInternalFeePerGas.ts +0 -49
  83. package/src/utils/utils/toBytes16.ts +0 -16
  84. package/src/utils/utils/types.ts +0 -21
  85. package/src/utils/world.ts +0 -28
@@ -1,11 +0,0 @@
1
- import S from"chalk";import B from"path";import{MUDError as it}from"@latticexyz/common/errors";import{loadConfig as ct}from"@latticexyz/config/node";import d from"chalk";import ze from"path";import{ethers as $}from"ethers";import{getOutDirectory as Qe,cast as Xe,getSrcDirectory as Ze,getRemappings as et}from"@latticexyz/common/foundry";import{resolveWorldConfig as tt}from"@latticexyz/world";import Ie from"chalk";import Me from"@latticexyz/world/out/World.sol/World.json"assert{type:"json"};import ve from"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json"assert{type:"json"};import U from"chalk";import{ethers as Se}from"ethers";import{MUDError as K}from"@latticexyz/common/errors";async function I(e){let{signer:o,nonce:t,maxPriorityFeePerGas:r,maxFeePerGas:n,debug:a,gasPrice:l,confirmations:p,contract:m}=e;try{let i=new Se.ContractFactory(m.abi,m.bytecode,o);console.log(U.gray(`executing deployment of ${m.name} with nonce ${t}`));let g=i.deploy({nonce:t,maxPriorityFeePerGas:r,maxFeePerGas:n,gasPrice:l}).then(s=>p?s:s.deployed()),{address:f}=await g;return console.log(U.green("Deployed",m.name,"to",f)),f}catch(i){throw a&&console.error(i),i?.message.includes("invalid bytecode")?new K(`Error deploying ${m.name}: invalid bytecode. Note that linking of public libraries is not supported yet, make sure none of your libraries use "external" functions.`):i?.message.includes("CreateContractLimit")?new K(`Error deploying ${m.name}: CreateContractLimit exceeded.`):i}}import{readFileSync as Te}from"fs";import Fe from"path";import{MUDError as R}from"@latticexyz/common/errors";function w(e,o){let t,r=Fe.join(o,e+".sol",e+".json");try{t=JSON.parse(Te(r,"utf8"))}catch{throw new R(`Error reading file at ${r}`)}let n=t?.bytecode?.object;if(!n)throw new R(`No bytecode found in ${r}`);let a=t?.abi;if(!a)throw new R(`No ABI found in ${r}`);return{abi:a,bytecode:n}}async function L(e){console.log(Ie.blue("Deploying World"));let o=e.worldContractName?{name:"World",...w(e.worldContractName,e.forgeOutDirectory)}:{abi:ve,bytecode:Me.bytecode,name:"World"};return I({...e,nonce:e.nonce,contract:o})}import ot from"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json"assert{type:"json"};import le from"@latticexyz/world/out/CoreModule.sol/CoreModule.json"assert{type:"json"};import H from"@latticexyz/world-modules/out/KeysWithValueModule.sol/KeysWithValueModule.json"assert{type:"json"};import J from"@latticexyz/world-modules/out/KeysInTableModule.sol/KeysInTableModule.json"assert{type:"json"};import _ from"@latticexyz/world-modules/out/UniqueEntityModule.sol/UniqueEntityModule.json"assert{type:"json"};var N=[{name:"KeysWithValueModule",abi:H.abi,bytecode:H.bytecode},{name:"KeysInTableModule",abi:J.abi,bytecode:J.bytecode},{name:"UniqueEntityModule",abi:_.abi,bytecode:_.bytecode}];import{defaultAbiCoder as Re}from"ethers/lib/utils.js";import{resolveWithContext as Ne}from"@latticexyz/config";async function q(e,o,t){let r=await e[o.name];if(!r)throw new Error(`Module ${o.name} not found`);let n=o.args.map(p=>Ne(p,{tableIds:t})),a=n.map(p=>p.value),l=n.map(p=>p.type);return{func:o.root?"installRootModule":"installModule",args:[r,Re.encode(l,a)]}}function V(e,o){return o.filter(t=>!e.some(r=>r.name===t.name))}import{resourceIdToHex as Ae}from"@latticexyz/common";async function z(e){let{systems:o,namespace:t,systemContracts:r}=e,n=[];for(let{name:a,accessListAddresses:l,accessListSystems:p}of o)l.map(async m=>n.push(Y(a,t,m))),p.map(async m=>n.push(Y(a,t,await r[m])));return n}function Y(e,o,t){return{func:"grantAccess",args:[Ae({type:"system",namespace:o,name:e}),t]}}import{resourceIdToHex as Z}from"@latticexyz/common";import{ethers as A}from"ethers";function k(e,o){let{abi:t}=w(e,o);return t.filter(r=>["fallback","function"].includes(r.type)).map(r=>`${r.name}${X(r.inputs)}`)}function Q(e){return ke(e)}function X(e){return`(${e.map(t=>{let r=t.type.match(/tuple(.*)/);return r?X(t.components)+r[1]:t.type})})`}function ke(e){return A.utils.hexDataSlice(A.utils.keccak256(A.utils.toUtf8Bytes(e)),0,4)}function ee(e){let o=[],{systemContractName:t,namespace:r,forgeOutDirectory:n,system:a}=e;if(a.registerFunctionSelectors){let l=k("System",n),p=k(t,n).filter(i=>t==="System"||!l.includes(i)),m=r==="";for(let i of p)o.push(je({namespace:r,name:a.name,systemFunctionSignature:i,isRoot:m}))}return o}function je(e){let{namespace:o,name:t,systemFunctionSignature:r,isRoot:n}=e;if(n){let a=Q(r);return{func:"registerRootFunctionSelector",args:[Z({type:"system",namespace:o,name:t}),r,a]}}else return{func:"registerFunctionSelector",args:[Z({type:"system",namespace:o,name:t}),r]}}import{resourceIdToHex as Oe}from"@latticexyz/common";async function te(e){let{namespace:o,systemContracts:t,systemKey:r,system:n}=e,a=await t[r];return{func:"registerSystem",args:[Oe({type:"system",namespace:o,name:n.name}),a,n.openAccess]}}import{encodeSchema as oe,getStaticByteLength as $e}from"@latticexyz/schema-type/deprecated";import{resolveAbiOrUserType as re}from"@latticexyz/store/codegen";import{resourceIdToHex as Be}from"@latticexyz/common";import{fieldLayoutToHex as Ee}from"@latticexyz/protocol-parser";import{loadAndExtractUserTypes as We}from"@latticexyz/common/codegen";function ne(e,o,t,r){let{name:n,valueSchema:a,keySchema:l}=e;if(!n)throw Error("Table missing name");let p=We(o.userTypes,t,r),m=Object.values(a).map(s=>{let{schemaType:u}=re(s,o,p);return u}),i=m.map(s=>$e(s)),g={staticFieldLengths:i.filter(s=>s>0),numDynamicFields:i.filter(s=>s===0).length},f=Object.values(l).map(s=>{let{schemaType:u}=re(s,o,p);return u});return{func:"registerTable",args:[Be({type:e.offchainOnly?"offchainTable":"table",namespace:o.namespace,name:n}),Ee(g),oe(f),oe(m),Object.keys(l),Object.keys(a)]}}function j(e){if(e.length>16)throw new Error("String does not fit into 16 bytes");let o=new Uint8Array(16);for(let t=0;t<e.length;t++)o[t]=e.charCodeAt(t);for(let t=e.length;t<16;t++)o[t]=0;return o}function ae(e){let o={};for(let[t,{name:r}]of Object.entries(e.tables))o[t]=Ge(e.namespace,r);return o}function Ge(e,o){let t=j(e),r=j(o),n=new Uint8Array(32);return n.set(t),n.set(r,16),n}import Ue from"chalk";import{MUDError as Ke}from"@latticexyz/common/errors";async function se(e,o,t){let r=await e.getTransactionCount(),n=0,a=100;for(;r!==o&&n<a;)console.log(Ue.gray(`Waiting for transactions to be included before executing postDeployScript (local nonce: ${o}, remote nonce: ${r}, retry number ${n}/${a})`)),await new Promise(l=>setTimeout(l,t)),n++,r=await e.getTransactionCount();if(r!==o)throw new Ke("Remote nonce doesn't match local nonce, indicating that not all deploy transactions were included.")}import Le from"chalk";import{MUDError as He}from"@latticexyz/common/errors";async function h(e){let{func:o,args:t,contract:r,signer:n,nonce:a,maxPriorityFeePerGas:l,maxFeePerGas:p,gasPrice:m,confirmations:i=1,debug:g}=e,f=`${o}(${t.map(s=>`'${s}'`).join(",")})`;try{let s=r.connect(n),u=await s.estimateGas[o].apply(null,t);return console.log(Le.gray(`executing transaction: ${f} with nonce ${a}`)),s[o].apply(null,[...t,{gasLimit:u,nonce:a,maxPriorityFeePerGas:l,maxFeePerGas:p,gasPrice:m}]).then(D=>i===0?D:D.wait(i))}catch(s){throw g&&console.error(s),new He(`Gas estimation error for ${f}: ${s?.reason}`)}}import{existsSync as Je}from"fs";import _e from"path";import qe from"chalk";import{getScriptDirectory as Ve,forge as Ye}from"@latticexyz/common/foundry";async function ie(e,o,t,r){let n=_e.join(await Ve(),e+".s.sol");Je(n)?(console.log(qe.blue(`Executing post deploy script at ${n}`)),await Ye(["script",e,"--sig","run(address)",o,"--broadcast","--rpc-url",t,"-vvv"],{profile:r})):console.log(`No script at ${n}, skipping post deploy hook`)}import{MUDError as O}from"@latticexyz/common/errors";async function ce(e,o){let t=await e.provider.getFeeData(),r,n,a;if(t.lastBaseFeePerGas){if(!t.lastBaseFeePerGas.eq(0)&&(await e.getBalance()).eq(0))throw new O(`Attempting to deploy to a chain with non-zero base fee with an account that has no balance.
2
- If you're deploying to the Lattice testnet, you can fund your account by running 'pnpm mud faucet --address ${await e.getAddress()}'`);r=t.lastBaseFeePerGas.eq(0)?0:Math.floor(15e8*o),n=t.lastBaseFeePerGas.mul(2).add(r)}else if(t.gasPrice){if(!t.gasPrice.eq(0)&&(await e.getBalance()).eq(0))throw new O("Attempting to deploy to a chain with non-zero gas price with an account that has no balance.");a=t.gasPrice}else throw new O("Can not fetch fee data from RPC");return{maxPriorityFeePerGas:r,maxFeePerGas:n,gasPrice:a}}import{resourceIdToHex as rt}from"@latticexyz/common";async function me(e,o,t){let r=Date.now(),{profile:n,rpc:a,privateKey:l,priorityFeeMultiplier:p,debug:m,worldAddress:i,disableTxWait:g,pollInterval:f}=t,s=tt(e,o),u=await Qe(n),D=await et(n),T=ze.join(await Ze(n),e.codegenDirectory),W=new $.providers.StaticJsonRpcProvider(a);W.pollingInterval=f;let P=new $.Wallet(l,W);console.log("Deploying from",P.address);let y=await P.getTransactionCount();console.log("Initial nonce",y);let C={...await ce(P,p),signer:P,debug:!!m,disableTxWait:g,confirmations:g?0:1},G=Number(await Xe(["block-number","--rpc-url",a],{profile:n}));console.log("Start deployment at block",G);let de=i?Promise.resolve(i):L({...C,nonce:y++,worldContractName:e.worldContractName,forgeOutDirectory:u}),ge=V(N,e.modules),ye=Object.keys(ge).map(c=>{let{abi:b,bytecode:v}=w(c,u);return{name:c,abi:b,bytecode:v}}),be=Object.keys(s.systems).map(c=>{let{abi:b,bytecode:v}=w(c,u);return{name:c,abi:b,bytecode:v}}),F=[{name:"CoreModule",abi:le.abi,bytecode:le.bytecode},...N,...ye,...be].reduce((c,b)=>(c[b.name]=I({...C,nonce:y++,contract:b}),c),{}),M=await de,x=new $.Contract(M,ot);i||(console.log(d.blue("Installing CoreModule")),await h({...C,nonce:y++,contract:x,func:"initialize",args:[await F.CoreModule]}),console.log(d.green("Installed CoreModule"))),e.namespace&&(console.log(d.blue("Registering Namespace")),await h({...C,nonce:y++,contract:x,func:"registerNamespace",args:[rt({type:"namespace",namespace:e.namespace,name:""})]}),console.log(d.green("Namespace registered")));let Ce=ae(e),we=Object.values(e.tables).map(c=>ne(c,e,T,D));console.log(d.blue("Registering tables")),await Promise.all(we.map(c=>h({...C,nonce:y++,contract:x,...c}))),console.log(d.green("Tables registered")),console.log(d.blue("Registering Systems and Functions"));let he=await Promise.all(Object.entries(s.systems).map(([c,b])=>te({systemContracts:F,systemKey:c,system:b,namespace:e.namespace}))),De=Object.entries(s.systems).flatMap(([c,b])=>ee({systemContractName:c,system:b,namespace:e.namespace,forgeOutDirectory:u}));await Promise.all([...he,...De].map(c=>h({...C,nonce:y++,contract:x,...c}))),console.log(d.green("Systems and Functions registered"));let xe=await z({systems:Object.values(s.systems),systemContracts:F,namespace:e.namespace});console.log(d.blue("Granting Access")),await Promise.all(xe.map(c=>h({...C,nonce:y++,contract:x,...c}))),console.log(d.green("Access granted"));let Pe=await Promise.all(e.modules.map(c=>q(F,c,Ce)));return console.log(d.blue("Installing User Modules")),await Promise.all(Pe.map(c=>h({...C,nonce:y++,contract:x,...c}))),console.log(d.green("User Modules Installed")),await se(P,y,f),await ie(e.postDeployScript,M,a,n),console.log(d.green("Deployment completed in",(Date.now()-r)/1e3,"seconds")),{worldAddress:M,blockNumber:G}}import{forge as ue,getRpcUrl as lt,getSrcDirectory as mt}from"@latticexyz/common/foundry";import{existsSync as pt,mkdirSync as ft,readFileSync as ut,writeFileSync as E}from"fs";import nt from"glob";import{basename as at}from"path";function pe(e){return nt.sync(`${e}/**/*.sol`).map(o=>({path:o,basename:at(o,".sol")}))}import{execa as dt}from"execa";import{ethers as st}from"ethers";async function fe(e){let{result:o}=await st.utils.fetchJson(e,'{ "id": 42, "jsonrpc": "2.0", "method": "eth_chainId", "params": [ ] }');return Number(o)}async function nr(e){e.profile??=process.env.FOUNDRY_PROFILE;let{configPath:o,printConfig:t,profile:r,clean:n,skipBuild:a}=e,l=e.rpc??await lt(r);console.log(S.bgBlue(S.whiteBright(`
3
- Deploying MUD contracts${r?" with profile "+r:""} to RPC ${l}
4
- `))),n&&await ue(["clean"],{profile:r}),a||(await ue(["build","--skip","test","script"],{profile:r}),await dt("mud",["abi-ts"],{stdio:"inherit"}));let p=e?.srcDir??await mt(),m=pe(p).map(({basename:s})=>s),i=await ct(o);t&&console.log(S.green(`
5
- Resolved config:
6
- `),JSON.stringify(i,null,2));let g=process.env.PRIVATE_KEY;if(!g)throw new it(`Missing PRIVATE_KEY environment variable.
7
- Run 'echo "PRIVATE_KEY=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80" > .env'
8
- in your contracts directory to use the default anvil private key.`);let f=await me(i,m,{...e,rpc:l,privateKey:g});if(e.saveDeployment){let s=await fe(l),u=B.join(i.deploysDirectory,s.toString());ft(u,{recursive:!0}),E(B.join(u,"latest.json"),JSON.stringify(f,null,2)),E(B.join(u,Date.now()+".json"),JSON.stringify(f,null,2));let D=[1337,31337],T=pt(i.worldsFile)?JSON.parse(ut(i.worldsFile,"utf-8")):{};T[s]={address:f.worldAddress,blockNumber:D.includes(s)?void 0:f.blockNumber},E(i.worldsFile,JSON.stringify(T,null,2)),console.log(S.bgGreen(S.whiteBright(`
9
- Deployment result (written to ${i.worldsFile} and ${u}):
10
- `)))}return console.log(f),f}export{pe as a,fe as b,nr as c};
11
- //# sourceMappingURL=chunk-WERDORTY.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/utils/deployHandler.ts","../src/utils/deploy.ts","../src/utils/world.ts","../src/utils/utils/deployContract.ts","../src/utils/utils/getContractData.ts","../src/utils/modules/constants.ts","../src/utils/modules/getInstallModuleCallData.ts","../src/utils/modules/getUserModules.ts","../src/utils/systems/getGrantAccessCallData.ts","../src/utils/systems/getRegisterFunctionSelectorsCallData.ts","../src/utils/systems/utils.ts","../src/utils/systems/getRegisterSystemCallData.ts","../src/utils/tables/getRegisterTableCallData.ts","../src/utils/utils/toBytes16.ts","../src/utils/tables/getTableIds.ts","../src/utils/utils/confirmNonce.ts","../src/utils/utils/fastTxExecute.ts","../src/utils/utils/postDeploy.ts","../src/utils/utils/setInternalFeePerGas.ts","../src/utils/getExistingContracts.ts","../src/utils/utils/getChainId.ts"],"sourcesContent":["import chalk from \"chalk\";\nimport path from \"path\";\nimport { MUDError } from \"@latticexyz/common/errors\";\nimport { loadConfig } from \"@latticexyz/config/node\";\nimport { StoreConfig } from \"@latticexyz/store\";\nimport { WorldConfig } from \"@latticexyz/world\";\nimport { deploy } from \"../utils/deploy\";\nimport { forge, getRpcUrl, getSrcDirectory } from \"@latticexyz/common/foundry\";\nimport { existsSync, mkdirSync, readFileSync, writeFileSync } from \"fs\";\nimport { getExistingContracts } from \"./getExistingContracts\";\nimport { execa } from \"execa\";\nimport { getChainId } from \"./utils/getChainId\";\n\nexport type DeployOptions = {\n configPath?: string;\n printConfig?: boolean;\n profile?: string;\n priorityFeeMultiplier: number;\n clean?: boolean;\n debug?: boolean;\n saveDeployment: boolean;\n rpc?: string;\n worldAddress?: string;\n srcDir?: string;\n disableTxWait: boolean;\n pollInterval: number;\n skipBuild?: boolean;\n};\n\nexport async function deployHandler(args: DeployOptions) {\n args.profile ??= process.env.FOUNDRY_PROFILE;\n const { configPath, printConfig, profile, clean, skipBuild } = args;\n\n const rpc = args.rpc ?? (await getRpcUrl(profile));\n console.log(\n chalk.bgBlue(\n chalk.whiteBright(`\\n Deploying MUD contracts${profile ? \" with profile \" + profile : \"\"} to RPC ${rpc} \\n`)\n )\n );\n\n if (clean) {\n await forge([\"clean\"], { profile });\n }\n\n // Run forge build\n if (!skipBuild) {\n await forge([\"build\", \"--skip\", \"test\", \"script\"], { profile });\n await execa(\"mud\", [\"abi-ts\"], { stdio: \"inherit\" });\n }\n\n // Get a list of all contract names\n const srcDir = args?.srcDir ?? (await getSrcDirectory());\n const existingContractNames = getExistingContracts(srcDir).map(({ basename }) => basename);\n\n // Load the config\n const mudConfig = (await loadConfig(configPath)) as StoreConfig & WorldConfig;\n\n if (printConfig) console.log(chalk.green(\"\\nResolved config:\\n\"), JSON.stringify(mudConfig, null, 2));\n\n const privateKey = process.env.PRIVATE_KEY;\n if (!privateKey)\n throw new MUDError(\n `Missing PRIVATE_KEY environment variable.\nRun 'echo \"PRIVATE_KEY=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80\" > .env'\nin your contracts directory to use the default anvil private key.`\n );\n const deploymentInfo = await deploy(mudConfig, existingContractNames, { ...args, rpc, privateKey });\n\n if (args.saveDeployment) {\n // Write deployment result to file (latest and timestamp)\n const chainId = await getChainId(rpc);\n const outputDir = path.join(mudConfig.deploysDirectory, chainId.toString());\n mkdirSync(outputDir, { recursive: true });\n writeFileSync(path.join(outputDir, \"latest.json\"), JSON.stringify(deploymentInfo, null, 2));\n writeFileSync(path.join(outputDir, Date.now() + \".json\"), JSON.stringify(deploymentInfo, null, 2));\n\n const localChains = [1337, 31337];\n const deploys = existsSync(mudConfig.worldsFile) ? JSON.parse(readFileSync(mudConfig.worldsFile, \"utf-8\")) : {};\n deploys[chainId] = {\n address: deploymentInfo.worldAddress,\n // We expect the worlds file to be committed and since local deployments are often a consistent address but different block number, we'll ignore the block number.\n blockNumber: localChains.includes(chainId) ? undefined : deploymentInfo.blockNumber,\n };\n writeFileSync(mudConfig.worldsFile, JSON.stringify(deploys, null, 2));\n\n console.log(\n chalk.bgGreen(chalk.whiteBright(`\\n Deployment result (written to ${mudConfig.worldsFile} and ${outputDir}): \\n`))\n );\n }\n\n console.log(deploymentInfo);\n return deploymentInfo;\n}\n","import chalk from \"chalk\";\nimport path from \"path\";\nimport { ethers } from \"ethers\";\nimport { getOutDirectory, cast, getSrcDirectory, getRemappings } from \"@latticexyz/common/foundry\";\nimport { StoreConfig } from \"@latticexyz/store\";\nimport { WorldConfig, resolveWorldConfig } from \"@latticexyz/world\";\nimport { deployWorldContract } from \"./world\";\nimport IBaseWorldAbi from \"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json\" assert { type: \"json\" };\nimport CoreModuleData from \"@latticexyz/world/out/CoreModule.sol/CoreModule.json\" assert { type: \"json\" };\nimport { defaultModuleContracts } from \"./modules/constants\";\nimport { getInstallModuleCallData } from \"./modules/getInstallModuleCallData\";\nimport { getUserModules } from \"./modules/getUserModules\";\nimport { getGrantAccessCallData } from \"./systems/getGrantAccessCallData\";\nimport { getRegisterFunctionSelectorsCallData } from \"./systems/getRegisterFunctionSelectorsCallData\";\nimport { getRegisterSystemCallData } from \"./systems/getRegisterSystemCallData\";\nimport { getRegisterTableCallData } from \"./tables/getRegisterTableCallData\";\nimport { getTableIds } from \"./tables/getTableIds\";\nimport { confirmNonce } from \"./utils/confirmNonce\";\nimport { deployContract } from \"./utils/deployContract\";\nimport { fastTxExecute } from \"./utils/fastTxExecute\";\nimport { getContractData } from \"./utils/getContractData\";\nimport { postDeploy } from \"./utils/postDeploy\";\nimport { setInternalFeePerGas } from \"./utils/setInternalFeePerGas\";\nimport { toBytes16 } from \"./utils/toBytes16\";\nimport { ContractCode } from \"./utils/types\";\nimport { resourceIdToHex } from \"@latticexyz/common\";\n\nexport interface DeployConfig {\n profile?: string;\n rpc: string;\n privateKey: string;\n priorityFeeMultiplier: number;\n debug?: boolean;\n worldAddress?: string;\n disableTxWait: boolean;\n pollInterval: number;\n}\n\nexport interface DeploymentInfo {\n blockNumber: number;\n worldAddress: string;\n}\n\nexport async function deploy(\n mudConfig: StoreConfig & WorldConfig,\n existingContractNames: string[],\n deployConfig: DeployConfig\n): Promise<DeploymentInfo> {\n const startTime = Date.now();\n const { profile, rpc, privateKey, priorityFeeMultiplier, debug, worldAddress, disableTxWait, pollInterval } =\n deployConfig;\n const resolvedConfig = resolveWorldConfig(mudConfig, existingContractNames);\n const forgeOutDirectory = await getOutDirectory(profile);\n const remappings = await getRemappings(profile);\n const outputBaseDirectory = path.join(await getSrcDirectory(profile), mudConfig.codegenDirectory);\n\n // Set up signer for deployment\n const provider = new ethers.providers.StaticJsonRpcProvider(rpc);\n provider.pollingInterval = pollInterval;\n const signer = new ethers.Wallet(privateKey, provider);\n console.log(\"Deploying from\", signer.address);\n\n let nonce = await signer.getTransactionCount();\n console.log(\"Initial nonce\", nonce);\n\n const txParams = await setInternalFeePerGas(signer, priorityFeeMultiplier);\n\n const txConfig = {\n ...txParams,\n signer,\n debug: Boolean(debug),\n disableTxWait,\n confirmations: disableTxWait ? 0 : 1,\n };\n\n // Get block number before deploying\n const blockNumber = Number(await cast([\"block-number\", \"--rpc-url\", rpc], { profile }));\n console.log(\"Start deployment at block\", blockNumber);\n\n // Deploy the World contract. Non-blocking.\n const worldPromise: Promise<string> = worldAddress\n ? Promise.resolve(worldAddress)\n : deployWorldContract({\n ...txConfig,\n nonce: nonce++,\n worldContractName: mudConfig.worldContractName,\n forgeOutDirectory,\n });\n\n // Filters any default modules from config\n const userModules = getUserModules(defaultModuleContracts, mudConfig.modules);\n const userModuleContracts = Object.keys(userModules).map((name) => {\n const { abi, bytecode } = getContractData(name, forgeOutDirectory);\n return {\n name,\n abi,\n bytecode,\n } as ContractCode;\n });\n\n const systemContracts = Object.keys(resolvedConfig.systems).map((name) => {\n const { abi, bytecode } = getContractData(name, forgeOutDirectory);\n return {\n name,\n abi,\n bytecode,\n } as ContractCode;\n });\n\n const contracts: ContractCode[] = [\n {\n name: \"CoreModule\",\n abi: CoreModuleData.abi,\n bytecode: CoreModuleData.bytecode,\n },\n ...defaultModuleContracts,\n ...userModuleContracts,\n ...systemContracts,\n ];\n\n // Deploy the System and Module contracts\n const deployedContracts = contracts.reduce<Record<string, Promise<string>>>((acc, contract) => {\n acc[contract.name] = deployContract({\n ...txConfig,\n nonce: nonce++,\n contract,\n });\n return acc;\n }, {});\n\n // Wait for world to be deployed\n const deployedWorldAddress = await worldPromise;\n const worldContract = new ethers.Contract(deployedWorldAddress, IBaseWorldAbi);\n\n // If an existing World is passed assume its coreModule is already installed - blocking to install if not\n if (!worldAddress) {\n console.log(chalk.blue(\"Installing CoreModule\"));\n await fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n func: \"initialize\",\n args: [await deployedContracts[\"CoreModule\"]],\n });\n console.log(chalk.green(\"Installed CoreModule\"));\n }\n\n if (mudConfig.namespace) {\n console.log(chalk.blue(\"Registering Namespace\"));\n await fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n func: \"registerNamespace\",\n args: [resourceIdToHex({ type: \"namespace\", namespace: mudConfig.namespace, name: \"\" })],\n });\n console.log(chalk.green(\"Namespace registered\"));\n }\n\n const tableIds = getTableIds(mudConfig);\n\n const registerTableCalls = Object.values(mudConfig.tables).map((table) =>\n getRegisterTableCallData(table, mudConfig, outputBaseDirectory, remappings)\n );\n\n console.log(chalk.blue(\"Registering tables\"));\n await Promise.all(\n registerTableCalls.map((call) =>\n fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n ...call,\n })\n )\n );\n console.log(chalk.green(`Tables registered`));\n\n console.log(chalk.blue(\"Registering Systems and Functions\"));\n const systemCalls = await Promise.all(\n Object.entries(resolvedConfig.systems).map(([systemKey, system]) =>\n getRegisterSystemCallData({\n systemContracts: deployedContracts,\n systemKey,\n system,\n namespace: mudConfig.namespace,\n })\n )\n );\n const functionCalls = Object.entries(resolvedConfig.systems).flatMap(([systemKey, system]) =>\n getRegisterFunctionSelectorsCallData({\n systemContractName: systemKey,\n system,\n namespace: mudConfig.namespace,\n forgeOutDirectory,\n })\n );\n await Promise.all(\n [...systemCalls, ...functionCalls].map((call) =>\n fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n ...call,\n })\n )\n );\n console.log(chalk.green(`Systems and Functions registered`));\n\n // Wait for System access to be granted before installing modules\n const grantCalls = await getGrantAccessCallData({\n systems: Object.values(resolvedConfig.systems),\n systemContracts: deployedContracts,\n namespace: mudConfig.namespace,\n });\n\n console.log(chalk.blue(\"Granting Access\"));\n await Promise.all(\n grantCalls.map((call) =>\n fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n ...call,\n })\n )\n );\n console.log(chalk.green(`Access granted`));\n\n const moduleCalls = await Promise.all(\n mudConfig.modules.map((m) => getInstallModuleCallData(deployedContracts, m, tableIds))\n );\n\n console.log(chalk.blue(\"Installing User Modules\"));\n await Promise.all(\n moduleCalls.map((call) =>\n fastTxExecute({\n ...txConfig,\n nonce: nonce++,\n contract: worldContract,\n ...call,\n })\n )\n );\n console.log(chalk.green(`User Modules Installed`));\n\n // Double check that all transactions have been included by confirming the current nonce is the expected nonce\n await confirmNonce(signer, nonce, pollInterval);\n\n await postDeploy(mudConfig.postDeployScript, deployedWorldAddress, rpc, profile);\n\n console.log(chalk.green(\"Deployment completed in\", (Date.now() - startTime) / 1000, \"seconds\"));\n\n return { worldAddress: deployedWorldAddress, blockNumber };\n}\n","import chalk from \"chalk\";\n\nimport WorldData from \"@latticexyz/world/out/World.sol/World.json\" assert { type: \"json\" };\nimport IBaseWorldAbi from \"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json\" assert { type: \"json\" };\nimport { deployContract } from \"./utils/deployContract\";\nimport { getContractData } from \"./utils/getContractData\";\nimport { TxConfig } from \"./utils/types\";\n\nexport async function deployWorldContract(\n ip: TxConfig & {\n nonce: number;\n worldContractName: string | undefined;\n forgeOutDirectory: string;\n }\n): Promise<string> {\n console.log(chalk.blue(`Deploying World`));\n const contractData = ip.worldContractName\n ? {\n name: \"World\",\n ...getContractData(ip.worldContractName, ip.forgeOutDirectory),\n }\n : { abi: IBaseWorldAbi, bytecode: WorldData.bytecode, name: \"World\" };\n return deployContract({\n ...ip,\n nonce: ip.nonce,\n contract: contractData,\n });\n}\n","import chalk from \"chalk\";\nimport { ethers } from \"ethers\";\nimport { MUDError } from \"@latticexyz/common/errors\";\nimport { TxConfig, ContractCode } from \"./types\";\n\nexport async function deployContract(input: TxConfig & { nonce: number; contract: ContractCode }): Promise<string> {\n const { signer, nonce, maxPriorityFeePerGas, maxFeePerGas, debug, gasPrice, confirmations, contract } = input;\n\n try {\n const factory = new ethers.ContractFactory(contract.abi, contract.bytecode, signer);\n console.log(chalk.gray(`executing deployment of ${contract.name} with nonce ${nonce}`));\n const deployPromise = factory\n .deploy({\n nonce,\n maxPriorityFeePerGas,\n maxFeePerGas,\n gasPrice,\n })\n .then((c) => (confirmations ? c : c.deployed()));\n const { address } = await deployPromise;\n console.log(chalk.green(\"Deployed\", contract.name, \"to\", address));\n return address;\n } catch (error: any) {\n if (debug) console.error(error);\n if (error?.message.includes(\"invalid bytecode\")) {\n throw new MUDError(\n `Error deploying ${contract.name}: invalid bytecode. Note that linking of public libraries is not supported yet, make sure none of your libraries use \"external\" functions.`\n );\n } else if (error?.message.includes(\"CreateContractLimit\")) {\n throw new MUDError(`Error deploying ${contract.name}: CreateContractLimit exceeded.`);\n } else throw error;\n }\n}\n","import { readFileSync } from \"fs\";\nimport path from \"path\";\nimport { Fragment } from \"ethers/lib/utils.js\";\nimport { MUDError } from \"@latticexyz/common/errors\";\n\n/**\n * Load the contract's abi and bytecode from the file system\n * @param contractName: Name of the contract to load\n */\nexport function getContractData(\n contractName: string,\n forgeOutDirectory: string\n): { bytecode: string; abi: Fragment[] } {\n let data: any;\n const contractDataPath = path.join(forgeOutDirectory, contractName + \".sol\", contractName + \".json\");\n try {\n data = JSON.parse(readFileSync(contractDataPath, \"utf8\"));\n } catch (error: any) {\n throw new MUDError(`Error reading file at ${contractDataPath}`);\n }\n\n const bytecode = data?.bytecode?.object;\n if (!bytecode) throw new MUDError(`No bytecode found in ${contractDataPath}`);\n\n const abi = data?.abi;\n if (!abi) throw new MUDError(`No ABI found in ${contractDataPath}`);\n\n return { abi, bytecode };\n}\n","import KeysWithValueModuleData from \"@latticexyz/world-modules/out/KeysWithValueModule.sol/KeysWithValueModule.json\" assert { type: \"json\" };\nimport KeysInTableModuleData from \"@latticexyz/world-modules/out/KeysInTableModule.sol/KeysInTableModule.json\" assert { type: \"json\" };\nimport UniqueEntityModuleData from \"@latticexyz/world-modules/out/UniqueEntityModule.sol/UniqueEntityModule.json\" assert { type: \"json\" };\nimport { ContractCode } from \"../utils/types\";\n\n// These modules are always deployed\nexport const defaultModuleContracts: ContractCode[] = [\n {\n name: \"KeysWithValueModule\",\n abi: KeysWithValueModuleData.abi,\n bytecode: KeysWithValueModuleData.bytecode,\n },\n {\n name: \"KeysInTableModule\",\n abi: KeysInTableModuleData.abi,\n bytecode: KeysInTableModuleData.bytecode,\n },\n {\n name: \"UniqueEntityModule\",\n abi: UniqueEntityModuleData.abi,\n bytecode: UniqueEntityModuleData.bytecode,\n },\n];\n","import { defaultAbiCoder } from \"ethers/lib/utils.js\";\nimport { resolveWithContext } from \"@latticexyz/config\";\nimport { Module } from \"./types\";\nimport { CallData } from \"../utils/types\";\nimport { TableIds } from \"../tables/types\";\n\nexport async function getInstallModuleCallData(\n moduleContracts: Record<string, Promise<string>>,\n module: Module,\n tableIds: TableIds\n): Promise<CallData> {\n const moduleAddress = await moduleContracts[module.name];\n if (!moduleAddress) throw new Error(`Module ${module.name} not found`);\n // Resolve arguments\n const resolvedArgs = module.args.map((arg) =>\n resolveWithContext(arg, {\n tableIds,\n })\n );\n const values = resolvedArgs.map((arg) => arg.value);\n const types = resolvedArgs.map((arg) => arg.type);\n\n return {\n func: module.root ? \"installRootModule\" : \"installModule\",\n args: [moduleAddress, defaultAbiCoder.encode(types, values)],\n };\n}\n","import { Module } from \"./types\";\n\nexport function getUserModules(defaultModules: { name: string }[], configModules: Module[]): Omit<Module, \"address\">[] {\n return configModules.filter((module) => !defaultModules.some((m) => m.name === module.name));\n}\n","import { System } from \"./types\";\nimport { CallData } from \"../utils/types\";\nimport { resourceIdToHex } from \"@latticexyz/common\";\n\nexport async function getGrantAccessCallData(input: {\n systems: System[];\n systemContracts: Record<string, Promise<string>>;\n namespace: string;\n}): Promise<CallData[]> {\n const { systems, namespace, systemContracts } = input;\n const calls: CallData[] = [];\n for (const { name, accessListAddresses, accessListSystems } of systems) {\n // Grant access to addresses\n accessListAddresses.map(async (address) => calls.push(getGrantSystemAccessCallData(name, namespace, address)));\n\n // Grant access to other systems\n accessListSystems.map(async (granteeSystem) =>\n calls.push(getGrantSystemAccessCallData(name, namespace, await systemContracts[granteeSystem]))\n );\n }\n return calls;\n}\n\nfunction getGrantSystemAccessCallData(name: string, namespace: string, address: string): CallData {\n return {\n func: \"grantAccess\",\n args: [resourceIdToHex({ type: \"system\", namespace, name }), address],\n };\n}\n","import { resourceIdToHex } from \"@latticexyz/common\";\nimport { System } from \"./types\";\nimport { loadFunctionSignatures, toFunctionSelector } from \"./utils\";\nimport { CallData } from \"../utils/types\";\n\nexport function getRegisterFunctionSelectorsCallData(input: {\n systemContractName: string;\n system: System;\n namespace: string;\n forgeOutDirectory: string;\n}): CallData[] {\n // Register system at route\n const callData: CallData[] = [];\n const { systemContractName, namespace, forgeOutDirectory, system } = input;\n\n if (system.registerFunctionSelectors) {\n const baseSystemFunctionSignatures = loadFunctionSignatures(\"System\", forgeOutDirectory);\n const systemFunctionSignatures = loadFunctionSignatures(systemContractName, forgeOutDirectory).filter(\n (functionSignature) =>\n systemContractName === \"System\" || !baseSystemFunctionSignatures.includes(functionSignature)\n );\n const isRoot = namespace === \"\";\n for (const systemFunctionSignature of systemFunctionSignatures) {\n callData.push(\n getRegisterFunctionSelectorCallData({\n namespace,\n name: system.name,\n systemFunctionSignature,\n isRoot,\n })\n );\n }\n }\n return callData;\n}\n\nfunction getRegisterFunctionSelectorCallData(input: {\n namespace: string;\n name: string;\n systemFunctionSignature: string;\n isRoot: boolean;\n}): CallData {\n const { namespace, name, systemFunctionSignature, isRoot } = input;\n\n if (isRoot) {\n const functionSelector = toFunctionSelector(systemFunctionSignature);\n return {\n func: \"registerRootFunctionSelector\",\n args: [resourceIdToHex({ type: \"system\", namespace, name }), systemFunctionSignature, functionSelector],\n };\n } else {\n return {\n func: \"registerFunctionSelector\",\n args: [resourceIdToHex({ type: \"system\", namespace, name }), systemFunctionSignature],\n };\n }\n}\n","import { ethers } from \"ethers\";\nimport { ParamType } from \"ethers/lib/utils.js\";\nimport { getContractData } from \"../utils/getContractData\";\n\nexport function loadFunctionSignatures(contractName: string, forgeOutDirectory: string): string[] {\n const { abi } = getContractData(contractName, forgeOutDirectory);\n\n return abi\n .filter((item) => [\"fallback\", \"function\"].includes(item.type))\n .map((item) => {\n return `${item.name}${parseComponents(item.inputs)}`;\n });\n}\n\n// TODO: move this to utils as soon as utils are usable inside cli\n// (see https://github.com/latticexyz/mud/issues/499)\nexport function toFunctionSelector(functionSignature: string): string {\n return sigHash(functionSignature);\n}\n\n/**\n * Recursively turn (nested) structs in signatures into tuples\n */\nfunction parseComponents(params: ParamType[]): string {\n const components = params.map((param) => {\n const tupleMatch = param.type.match(/tuple(.*)/);\n if (tupleMatch) {\n // there can be arrays of tuples,\n // `tupleMatch[1]` preserves the array brackets (or is empty string for non-arrays)\n return parseComponents(param.components) + tupleMatch[1];\n } else {\n return param.type;\n }\n });\n return `(${components})`;\n}\n\n// TODO: move this to utils as soon as utils are usable inside cli\n// (see https://github.com/latticexyz/mud/issues/499)\nfunction sigHash(signature: string) {\n return ethers.utils.hexDataSlice(ethers.utils.keccak256(ethers.utils.toUtf8Bytes(signature)), 0, 4);\n}\n","import { resourceIdToHex } from \"@latticexyz/common\";\nimport { System } from \"./types\";\nimport { CallData } from \"../utils/types\";\n\nexport async function getRegisterSystemCallData(input: {\n systemContracts: Record<string, Promise<string>>;\n systemKey: string;\n system: System;\n namespace: string;\n}): Promise<CallData> {\n const { namespace, systemContracts, systemKey, system } = input;\n const systemAddress = await systemContracts[systemKey];\n return {\n func: \"registerSystem\",\n args: [resourceIdToHex({ type: \"system\", namespace, name: system.name }), systemAddress, system.openAccess],\n };\n}\n","import { encodeSchema, getStaticByteLength } from \"@latticexyz/schema-type/deprecated\";\nimport { StoreConfig } from \"@latticexyz/store\";\nimport { resolveAbiOrUserType } from \"@latticexyz/store/codegen\";\nimport { resourceIdToHex } from \"@latticexyz/common\";\nimport { Table } from \"./types\";\nimport { fieldLayoutToHex } from \"@latticexyz/protocol-parser\";\nimport { CallData } from \"../utils/types\";\nimport { loadAndExtractUserTypes } from \"@latticexyz/common/codegen\";\n\nexport function getRegisterTableCallData(\n table: Table,\n storeConfig: StoreConfig,\n outputBaseDirectory: string,\n remappings: [string, string][]\n): CallData {\n const { name, valueSchema, keySchema } = table;\n if (!name) throw Error(\"Table missing name\");\n\n const solidityUserTypes = loadAndExtractUserTypes(storeConfig.userTypes, outputBaseDirectory, remappings);\n\n const schemaTypes = Object.values(valueSchema).map((abiOrUserType) => {\n const { schemaType } = resolveAbiOrUserType(abiOrUserType, storeConfig, solidityUserTypes);\n return schemaType;\n });\n\n const schemaTypeLengths = schemaTypes.map((schemaType) => getStaticByteLength(schemaType));\n const fieldLayout = {\n staticFieldLengths: schemaTypeLengths.filter((schemaTypeLength) => schemaTypeLength > 0),\n numDynamicFields: schemaTypeLengths.filter((schemaTypeLength) => schemaTypeLength === 0).length,\n };\n\n const keyTypes = Object.values(keySchema).map((abiOrUserType) => {\n const { schemaType } = resolveAbiOrUserType(abiOrUserType, storeConfig, solidityUserTypes);\n return schemaType;\n });\n\n return {\n func: \"registerTable\",\n args: [\n // TODO: add support for table namespaces (https://github.com/latticexyz/mud/issues/994)\n resourceIdToHex({ type: table.offchainOnly ? \"offchainTable\" : \"table\", namespace: storeConfig.namespace, name }),\n fieldLayoutToHex(fieldLayout),\n encodeSchema(keyTypes),\n encodeSchema(schemaTypes),\n Object.keys(keySchema),\n Object.keys(valueSchema),\n ],\n };\n}\n","// TODO: use stringToBytes16 from utils as soon as utils are usable inside cli\n// (see https://github.com/latticexyz/mud/issues/499)\nexport function toBytes16(input: string) {\n if (input.length > 16) throw new Error(\"String does not fit into 16 bytes\");\n\n const result = new Uint8Array(16);\n // Set ascii bytes\n for (let i = 0; i < input.length; i++) {\n result[i] = input.charCodeAt(i);\n }\n // Set the remaining bytes to 0\n for (let i = input.length; i < 16; i++) {\n result[i] = 0;\n }\n return result;\n}\n","import { StoreConfig } from \"@latticexyz/store\";\nimport { TableIds } from \"./types\";\nimport { toBytes16 } from \"../utils/toBytes16\";\n\nexport function getTableIds(storeConfig: StoreConfig): TableIds {\n const tableIds: TableIds = {};\n for (const [tableName, { name }] of Object.entries(storeConfig.tables)) {\n tableIds[tableName] = toResourceSelector(storeConfig.namespace, name);\n }\n return tableIds;\n}\n\n// (see https://github.com/latticexyz/mud/issues/499)\nfunction toResourceSelector(namespace: string, file: string): Uint8Array {\n const namespaceBytes = toBytes16(namespace);\n const fileBytes = toBytes16(file);\n const result = new Uint8Array(32);\n result.set(namespaceBytes);\n result.set(fileBytes, 16);\n return result;\n}\n","import chalk from \"chalk\";\nimport { Wallet } from \"ethers\";\nimport { MUDError } from \"@latticexyz/common/errors\";\n\nexport async function confirmNonce(signer: Wallet, nonce: number, pollInterval: number): Promise<void> {\n let remoteNonce = await signer.getTransactionCount();\n let retryCount = 0;\n const maxRetries = 100;\n while (remoteNonce !== nonce && retryCount < maxRetries) {\n console.log(\n chalk.gray(\n `Waiting for transactions to be included before executing postDeployScript (local nonce: ${nonce}, remote nonce: ${remoteNonce}, retry number ${retryCount}/${maxRetries})`\n )\n );\n await new Promise((resolve) => setTimeout(resolve, pollInterval));\n retryCount++;\n remoteNonce = await signer.getTransactionCount();\n }\n if (remoteNonce !== nonce) {\n throw new MUDError(\n \"Remote nonce doesn't match local nonce, indicating that not all deploy transactions were included.\"\n );\n }\n}\n","import chalk from \"chalk\";\nimport { TransactionReceipt, TransactionResponse } from \"@ethersproject/providers\";\nimport { MUDError } from \"@latticexyz/common/errors\";\nimport { TxConfig } from \"./types\";\n\n/**\n * Only await gas estimation (for speed), only execute if gas estimation succeeds (for safety)\n */\nexport async function fastTxExecute<\n C extends { connect: any; estimateGas: any; [key: string]: any },\n F extends keyof C\n>(\n input: TxConfig & {\n nonce: number;\n contract: C;\n func: F;\n args: Parameters<C[F]>;\n confirmations: number;\n }\n): Promise<TransactionResponse | TransactionReceipt> {\n const {\n func,\n args,\n contract,\n signer,\n nonce,\n maxPriorityFeePerGas,\n maxFeePerGas,\n gasPrice,\n confirmations = 1,\n debug,\n } = input;\n const functionName = `${func as string}(${args.map((arg) => `'${arg}'`).join(\",\")})`;\n try {\n const contractWithSigner = contract.connect(signer);\n const gasLimit = await contractWithSigner.estimateGas[func].apply(null, args);\n console.log(chalk.gray(`executing transaction: ${functionName} with nonce ${nonce}`));\n return contractWithSigner[func]\n .apply(null, [\n ...args,\n {\n gasLimit,\n nonce: nonce,\n maxPriorityFeePerGas: maxPriorityFeePerGas,\n maxFeePerGas: maxFeePerGas,\n gasPrice: gasPrice,\n },\n ])\n .then((tx: TransactionResponse) => {\n return confirmations === 0 ? tx : tx.wait(confirmations);\n });\n } catch (error: any) {\n if (debug) console.error(error);\n throw new MUDError(`Gas estimation error for ${functionName}: ${error?.reason}`);\n }\n}\n","import { existsSync } from \"fs\";\nimport path from \"path\";\nimport chalk from \"chalk\";\nimport { getScriptDirectory, forge } from \"@latticexyz/common/foundry\";\n\nexport async function postDeploy(\n postDeployScript: string,\n worldAddress: string,\n rpc: string,\n profile: string | undefined\n): Promise<void> {\n // Execute postDeploy forge script\n const postDeployPath = path.join(await getScriptDirectory(), postDeployScript + \".s.sol\");\n if (existsSync(postDeployPath)) {\n console.log(chalk.blue(`Executing post deploy script at ${postDeployPath}`));\n await forge(\n [\"script\", postDeployScript, \"--sig\", \"run(address)\", worldAddress, \"--broadcast\", \"--rpc-url\", rpc, \"-vvv\"],\n {\n profile: profile,\n }\n );\n } else {\n console.log(`No script at ${postDeployPath}, skipping post deploy hook`);\n }\n}\n","import { BigNumber, Wallet } from \"ethers\";\nimport { MUDError } from \"@latticexyz/common/errors\";\n\n/**\n * Set the maxFeePerGas and maxPriorityFeePerGas based on the current base fee and the given multiplier.\n * The multiplier is used to allow replacing pending transactions.\n * @param multiplier Multiplier to apply to the base fee\n */\nexport async function setInternalFeePerGas(\n signer: Wallet,\n multiplier: number\n): Promise<{\n maxPriorityFeePerGas: number | undefined;\n maxFeePerGas: BigNumber | undefined;\n gasPrice: BigNumber | undefined;\n}> {\n // Compute maxFeePerGas and maxPriorityFeePerGas like ethers, but allow for a multiplier to allow replacing pending transactions\n const feeData = await signer.provider.getFeeData();\n let maxPriorityFeePerGas: number | undefined;\n let maxFeePerGas: BigNumber | undefined;\n let gasPrice: BigNumber | undefined;\n\n if (feeData.lastBaseFeePerGas) {\n if (!feeData.lastBaseFeePerGas.eq(0) && (await signer.getBalance()).eq(0)) {\n throw new MUDError(`Attempting to deploy to a chain with non-zero base fee with an account that has no balance.\n If you're deploying to the Lattice testnet, you can fund your account by running 'pnpm mud faucet --address ${await signer.getAddress()}'`);\n }\n\n // Set the priority fee to 0 for development chains with no base fee, to allow transactions from unfunded wallets\n maxPriorityFeePerGas = feeData.lastBaseFeePerGas.eq(0) ? 0 : Math.floor(1_500_000_000 * multiplier);\n maxFeePerGas = feeData.lastBaseFeePerGas.mul(2).add(maxPriorityFeePerGas);\n } else if (feeData.gasPrice) {\n // Legacy chains with gasPrice instead of maxFeePerGas\n if (!feeData.gasPrice.eq(0) && (await signer.getBalance()).eq(0)) {\n throw new MUDError(\n `Attempting to deploy to a chain with non-zero gas price with an account that has no balance.`\n );\n }\n\n gasPrice = feeData.gasPrice;\n } else {\n throw new MUDError(\"Can not fetch fee data from RPC\");\n }\n return {\n maxPriorityFeePerGas,\n maxFeePerGas,\n gasPrice,\n };\n}\n","import glob from \"glob\";\nimport { basename } from \"path\";\n\n/**\n * Get a list of all contract paths/names within the provided src directory\n */\nexport function getExistingContracts(srcDir: string) {\n return glob.sync(`${srcDir}/**/*.sol`).map((path) => ({\n path,\n basename: basename(path, \".sol\"),\n }));\n}\n","import { ethers } from \"ethers\";\n\n// TODO: Use viem's getChainId\nexport async function getChainId(rpc: string) {\n const { result: chainId } = await ethers.utils.fetchJson(\n rpc,\n '{ \"id\": 42, \"jsonrpc\": \"2.0\", \"method\": \"eth_chainId\", \"params\": [ ] }'\n );\n return Number(chainId);\n}\n"],"mappings":"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","names":["chalk","path","MUDError","loadConfig","chalk","path","ethers","getOutDirectory","cast","getSrcDirectory","getRemappings","resolveWorldConfig","chalk","WorldData","IBaseWorldAbi","chalk","ethers","MUDError","deployContract","input","signer","nonce","maxPriorityFeePerGas","maxFeePerGas","debug","gasPrice","confirmations","contract","factory","deployPromise","c","address","error","readFileSync","path","MUDError","getContractData","contractName","forgeOutDirectory","data","contractDataPath","bytecode","abi","deployWorldContract","ip","chalk","contractData","getContractData","IBaseWorldAbi","WorldData","deployContract","IBaseWorldAbi","CoreModuleData","KeysWithValueModuleData","KeysInTableModuleData","UniqueEntityModuleData","defaultModuleContracts","defaultAbiCoder","resolveWithContext","getInstallModuleCallData","moduleContracts","module","tableIds","moduleAddress","resolvedArgs","arg","values","types","getUserModules","defaultModules","configModules","module","m","resourceIdToHex","getGrantAccessCallData","input","systems","namespace","systemContracts","calls","name","accessListAddresses","accessListSystems","address","getGrantSystemAccessCallData","granteeSystem","resourceIdToHex","ethers","loadFunctionSignatures","contractName","forgeOutDirectory","abi","getContractData","item","parseComponents","toFunctionSelector","functionSignature","sigHash","params","param","tupleMatch","signature","ethers","getRegisterFunctionSelectorsCallData","input","callData","systemContractName","namespace","forgeOutDirectory","system","baseSystemFunctionSignatures","loadFunctionSignatures","systemFunctionSignatures","functionSignature","isRoot","systemFunctionSignature","getRegisterFunctionSelectorCallData","name","functionSelector","toFunctionSelector","resourceIdToHex","resourceIdToHex","getRegisterSystemCallData","input","namespace","systemContracts","systemKey","system","systemAddress","encodeSchema","getStaticByteLength","resolveAbiOrUserType","resourceIdToHex","fieldLayoutToHex","loadAndExtractUserTypes","getRegisterTableCallData","table","storeConfig","outputBaseDirectory","remappings","name","valueSchema","keySchema","solidityUserTypes","schemaTypes","abiOrUserType","schemaType","schemaTypeLengths","fieldLayout","schemaTypeLength","keyTypes","toBytes16","input","result","i","getTableIds","storeConfig","tableIds","tableName","name","toResourceSelector","namespace","file","namespaceBytes","toBytes16","fileBytes","result","chalk","MUDError","confirmNonce","signer","nonce","pollInterval","remoteNonce","retryCount","maxRetries","resolve","chalk","MUDError","fastTxExecute","input","func","args","contract","signer","nonce","maxPriorityFeePerGas","maxFeePerGas","gasPrice","confirmations","debug","functionName","arg","contractWithSigner","gasLimit","tx","error","existsSync","path","chalk","getScriptDirectory","forge","postDeploy","postDeployScript","worldAddress","rpc","profile","postDeployPath","MUDError","setInternalFeePerGas","signer","multiplier","feeData","maxPriorityFeePerGas","maxFeePerGas","gasPrice","resourceIdToHex","deploy","mudConfig","existingContractNames","deployConfig","startTime","profile","rpc","privateKey","priorityFeeMultiplier","debug","worldAddress","disableTxWait","pollInterval","resolvedConfig","resolveWorldConfig","forgeOutDirectory","getOutDirectory","remappings","getRemappings","outputBaseDirectory","path","getSrcDirectory","provider","ethers","signer","nonce","txConfig","setInternalFeePerGas","blockNumber","cast","worldPromise","deployWorldContract","userModules","getUserModules","defaultModuleContracts","userModuleContracts","name","abi","bytecode","getContractData","systemContracts","deployedContracts","CoreModuleData","acc","contract","deployContract","deployedWorldAddress","worldContract","IBaseWorldAbi","chalk","fastTxExecute","tableIds","getTableIds","registerTableCalls","table","getRegisterTableCallData","call","systemCalls","systemKey","system","getRegisterSystemCallData","functionCalls","getRegisterFunctionSelectorsCallData","grantCalls","getGrantAccessCallData","moduleCalls","m","getInstallModuleCallData","confirmNonce","postDeploy","forge","getRpcUrl","getSrcDirectory","existsSync","mkdirSync","readFileSync","writeFileSync","glob","basename","getExistingContracts","srcDir","path","execa","ethers","getChainId","rpc","chainId","deployHandler","args","configPath","printConfig","profile","clean","skipBuild","rpc","getRpcUrl","chalk","forge","execa","srcDir","getSrcDirectory","existingContractNames","getExistingContracts","basename","mudConfig","loadConfig","privateKey","MUDError","deploymentInfo","deploy","chainId","getChainId","outputDir","path","mkdirSync","writeFileSync","localChains","deploys","existsSync","readFileSync"]}
@@ -1,255 +0,0 @@
1
- import chalk from "chalk";
2
- import path from "path";
3
- import { ethers } from "ethers";
4
- import { getOutDirectory, cast, getSrcDirectory, getRemappings } from "@latticexyz/common/foundry";
5
- import { StoreConfig } from "@latticexyz/store";
6
- import { WorldConfig, resolveWorldConfig } from "@latticexyz/world";
7
- import { deployWorldContract } from "./world";
8
- import IBaseWorldAbi from "@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json" assert { type: "json" };
9
- import CoreModuleData from "@latticexyz/world/out/CoreModule.sol/CoreModule.json" assert { type: "json" };
10
- import { defaultModuleContracts } from "./modules/constants";
11
- import { getInstallModuleCallData } from "./modules/getInstallModuleCallData";
12
- import { getUserModules } from "./modules/getUserModules";
13
- import { getGrantAccessCallData } from "./systems/getGrantAccessCallData";
14
- import { getRegisterFunctionSelectorsCallData } from "./systems/getRegisterFunctionSelectorsCallData";
15
- import { getRegisterSystemCallData } from "./systems/getRegisterSystemCallData";
16
- import { getRegisterTableCallData } from "./tables/getRegisterTableCallData";
17
- import { getTableIds } from "./tables/getTableIds";
18
- import { confirmNonce } from "./utils/confirmNonce";
19
- import { deployContract } from "./utils/deployContract";
20
- import { fastTxExecute } from "./utils/fastTxExecute";
21
- import { getContractData } from "./utils/getContractData";
22
- import { postDeploy } from "./utils/postDeploy";
23
- import { setInternalFeePerGas } from "./utils/setInternalFeePerGas";
24
- import { toBytes16 } from "./utils/toBytes16";
25
- import { ContractCode } from "./utils/types";
26
- import { resourceIdToHex } from "@latticexyz/common";
27
-
28
- export interface DeployConfig {
29
- profile?: string;
30
- rpc: string;
31
- privateKey: string;
32
- priorityFeeMultiplier: number;
33
- debug?: boolean;
34
- worldAddress?: string;
35
- disableTxWait: boolean;
36
- pollInterval: number;
37
- }
38
-
39
- export interface DeploymentInfo {
40
- blockNumber: number;
41
- worldAddress: string;
42
- }
43
-
44
- export async function deploy(
45
- mudConfig: StoreConfig & WorldConfig,
46
- existingContractNames: string[],
47
- deployConfig: DeployConfig
48
- ): Promise<DeploymentInfo> {
49
- const startTime = Date.now();
50
- const { profile, rpc, privateKey, priorityFeeMultiplier, debug, worldAddress, disableTxWait, pollInterval } =
51
- deployConfig;
52
- const resolvedConfig = resolveWorldConfig(mudConfig, existingContractNames);
53
- const forgeOutDirectory = await getOutDirectory(profile);
54
- const remappings = await getRemappings(profile);
55
- const outputBaseDirectory = path.join(await getSrcDirectory(profile), mudConfig.codegenDirectory);
56
-
57
- // Set up signer for deployment
58
- const provider = new ethers.providers.StaticJsonRpcProvider(rpc);
59
- provider.pollingInterval = pollInterval;
60
- const signer = new ethers.Wallet(privateKey, provider);
61
- console.log("Deploying from", signer.address);
62
-
63
- let nonce = await signer.getTransactionCount();
64
- console.log("Initial nonce", nonce);
65
-
66
- const txParams = await setInternalFeePerGas(signer, priorityFeeMultiplier);
67
-
68
- const txConfig = {
69
- ...txParams,
70
- signer,
71
- debug: Boolean(debug),
72
- disableTxWait,
73
- confirmations: disableTxWait ? 0 : 1,
74
- };
75
-
76
- // Get block number before deploying
77
- const blockNumber = Number(await cast(["block-number", "--rpc-url", rpc], { profile }));
78
- console.log("Start deployment at block", blockNumber);
79
-
80
- // Deploy the World contract. Non-blocking.
81
- const worldPromise: Promise<string> = worldAddress
82
- ? Promise.resolve(worldAddress)
83
- : deployWorldContract({
84
- ...txConfig,
85
- nonce: nonce++,
86
- worldContractName: mudConfig.worldContractName,
87
- forgeOutDirectory,
88
- });
89
-
90
- // Filters any default modules from config
91
- const userModules = getUserModules(defaultModuleContracts, mudConfig.modules);
92
- const userModuleContracts = Object.keys(userModules).map((name) => {
93
- const { abi, bytecode } = getContractData(name, forgeOutDirectory);
94
- return {
95
- name,
96
- abi,
97
- bytecode,
98
- } as ContractCode;
99
- });
100
-
101
- const systemContracts = Object.keys(resolvedConfig.systems).map((name) => {
102
- const { abi, bytecode } = getContractData(name, forgeOutDirectory);
103
- return {
104
- name,
105
- abi,
106
- bytecode,
107
- } as ContractCode;
108
- });
109
-
110
- const contracts: ContractCode[] = [
111
- {
112
- name: "CoreModule",
113
- abi: CoreModuleData.abi,
114
- bytecode: CoreModuleData.bytecode,
115
- },
116
- ...defaultModuleContracts,
117
- ...userModuleContracts,
118
- ...systemContracts,
119
- ];
120
-
121
- // Deploy the System and Module contracts
122
- const deployedContracts = contracts.reduce<Record<string, Promise<string>>>((acc, contract) => {
123
- acc[contract.name] = deployContract({
124
- ...txConfig,
125
- nonce: nonce++,
126
- contract,
127
- });
128
- return acc;
129
- }, {});
130
-
131
- // Wait for world to be deployed
132
- const deployedWorldAddress = await worldPromise;
133
- const worldContract = new ethers.Contract(deployedWorldAddress, IBaseWorldAbi);
134
-
135
- // If an existing World is passed assume its coreModule is already installed - blocking to install if not
136
- if (!worldAddress) {
137
- console.log(chalk.blue("Installing CoreModule"));
138
- await fastTxExecute({
139
- ...txConfig,
140
- nonce: nonce++,
141
- contract: worldContract,
142
- func: "initialize",
143
- args: [await deployedContracts["CoreModule"]],
144
- });
145
- console.log(chalk.green("Installed CoreModule"));
146
- }
147
-
148
- if (mudConfig.namespace) {
149
- console.log(chalk.blue("Registering Namespace"));
150
- await fastTxExecute({
151
- ...txConfig,
152
- nonce: nonce++,
153
- contract: worldContract,
154
- func: "registerNamespace",
155
- args: [resourceIdToHex({ type: "namespace", namespace: mudConfig.namespace, name: "" })],
156
- });
157
- console.log(chalk.green("Namespace registered"));
158
- }
159
-
160
- const tableIds = getTableIds(mudConfig);
161
-
162
- const registerTableCalls = Object.values(mudConfig.tables).map((table) =>
163
- getRegisterTableCallData(table, mudConfig, outputBaseDirectory, remappings)
164
- );
165
-
166
- console.log(chalk.blue("Registering tables"));
167
- await Promise.all(
168
- registerTableCalls.map((call) =>
169
- fastTxExecute({
170
- ...txConfig,
171
- nonce: nonce++,
172
- contract: worldContract,
173
- ...call,
174
- })
175
- )
176
- );
177
- console.log(chalk.green(`Tables registered`));
178
-
179
- console.log(chalk.blue("Registering Systems and Functions"));
180
- const systemCalls = await Promise.all(
181
- Object.entries(resolvedConfig.systems).map(([systemKey, system]) =>
182
- getRegisterSystemCallData({
183
- systemContracts: deployedContracts,
184
- systemKey,
185
- system,
186
- namespace: mudConfig.namespace,
187
- })
188
- )
189
- );
190
- const functionCalls = Object.entries(resolvedConfig.systems).flatMap(([systemKey, system]) =>
191
- getRegisterFunctionSelectorsCallData({
192
- systemContractName: systemKey,
193
- system,
194
- namespace: mudConfig.namespace,
195
- forgeOutDirectory,
196
- })
197
- );
198
- await Promise.all(
199
- [...systemCalls, ...functionCalls].map((call) =>
200
- fastTxExecute({
201
- ...txConfig,
202
- nonce: nonce++,
203
- contract: worldContract,
204
- ...call,
205
- })
206
- )
207
- );
208
- console.log(chalk.green(`Systems and Functions registered`));
209
-
210
- // Wait for System access to be granted before installing modules
211
- const grantCalls = await getGrantAccessCallData({
212
- systems: Object.values(resolvedConfig.systems),
213
- systemContracts: deployedContracts,
214
- namespace: mudConfig.namespace,
215
- });
216
-
217
- console.log(chalk.blue("Granting Access"));
218
- await Promise.all(
219
- grantCalls.map((call) =>
220
- fastTxExecute({
221
- ...txConfig,
222
- nonce: nonce++,
223
- contract: worldContract,
224
- ...call,
225
- })
226
- )
227
- );
228
- console.log(chalk.green(`Access granted`));
229
-
230
- const moduleCalls = await Promise.all(
231
- mudConfig.modules.map((m) => getInstallModuleCallData(deployedContracts, m, tableIds))
232
- );
233
-
234
- console.log(chalk.blue("Installing User Modules"));
235
- await Promise.all(
236
- moduleCalls.map((call) =>
237
- fastTxExecute({
238
- ...txConfig,
239
- nonce: nonce++,
240
- contract: worldContract,
241
- ...call,
242
- })
243
- )
244
- );
245
- console.log(chalk.green(`User Modules Installed`));
246
-
247
- // Double check that all transactions have been included by confirming the current nonce is the expected nonce
248
- await confirmNonce(signer, nonce, pollInterval);
249
-
250
- await postDeploy(mudConfig.postDeployScript, deployedWorldAddress, rpc, profile);
251
-
252
- console.log(chalk.green("Deployment completed in", (Date.now() - startTime) / 1000, "seconds"));
253
-
254
- return { worldAddress: deployedWorldAddress, blockNumber };
255
- }
@@ -1,93 +0,0 @@
1
- import chalk from "chalk";
2
- import path from "path";
3
- import { MUDError } from "@latticexyz/common/errors";
4
- import { loadConfig } from "@latticexyz/config/node";
5
- import { StoreConfig } from "@latticexyz/store";
6
- import { WorldConfig } from "@latticexyz/world";
7
- import { deploy } from "../utils/deploy";
8
- import { forge, getRpcUrl, getSrcDirectory } from "@latticexyz/common/foundry";
9
- import { existsSync, mkdirSync, readFileSync, writeFileSync } from "fs";
10
- import { getExistingContracts } from "./getExistingContracts";
11
- import { execa } from "execa";
12
- import { getChainId } from "./utils/getChainId";
13
-
14
- export type DeployOptions = {
15
- configPath?: string;
16
- printConfig?: boolean;
17
- profile?: string;
18
- priorityFeeMultiplier: number;
19
- clean?: boolean;
20
- debug?: boolean;
21
- saveDeployment: boolean;
22
- rpc?: string;
23
- worldAddress?: string;
24
- srcDir?: string;
25
- disableTxWait: boolean;
26
- pollInterval: number;
27
- skipBuild?: boolean;
28
- };
29
-
30
- export async function deployHandler(args: DeployOptions) {
31
- args.profile ??= process.env.FOUNDRY_PROFILE;
32
- const { configPath, printConfig, profile, clean, skipBuild } = args;
33
-
34
- const rpc = args.rpc ?? (await getRpcUrl(profile));
35
- console.log(
36
- chalk.bgBlue(
37
- chalk.whiteBright(`\n Deploying MUD contracts${profile ? " with profile " + profile : ""} to RPC ${rpc} \n`)
38
- )
39
- );
40
-
41
- if (clean) {
42
- await forge(["clean"], { profile });
43
- }
44
-
45
- // Run forge build
46
- if (!skipBuild) {
47
- await forge(["build", "--skip", "test", "script"], { profile });
48
- await execa("mud", ["abi-ts"], { stdio: "inherit" });
49
- }
50
-
51
- // Get a list of all contract names
52
- const srcDir = args?.srcDir ?? (await getSrcDirectory());
53
- const existingContractNames = getExistingContracts(srcDir).map(({ basename }) => basename);
54
-
55
- // Load the config
56
- const mudConfig = (await loadConfig(configPath)) as StoreConfig & WorldConfig;
57
-
58
- if (printConfig) console.log(chalk.green("\nResolved config:\n"), JSON.stringify(mudConfig, null, 2));
59
-
60
- const privateKey = process.env.PRIVATE_KEY;
61
- if (!privateKey)
62
- throw new MUDError(
63
- `Missing PRIVATE_KEY environment variable.
64
- Run 'echo "PRIVATE_KEY=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80" > .env'
65
- in your contracts directory to use the default anvil private key.`
66
- );
67
- const deploymentInfo = await deploy(mudConfig, existingContractNames, { ...args, rpc, privateKey });
68
-
69
- if (args.saveDeployment) {
70
- // Write deployment result to file (latest and timestamp)
71
- const chainId = await getChainId(rpc);
72
- const outputDir = path.join(mudConfig.deploysDirectory, chainId.toString());
73
- mkdirSync(outputDir, { recursive: true });
74
- writeFileSync(path.join(outputDir, "latest.json"), JSON.stringify(deploymentInfo, null, 2));
75
- writeFileSync(path.join(outputDir, Date.now() + ".json"), JSON.stringify(deploymentInfo, null, 2));
76
-
77
- const localChains = [1337, 31337];
78
- const deploys = existsSync(mudConfig.worldsFile) ? JSON.parse(readFileSync(mudConfig.worldsFile, "utf-8")) : {};
79
- deploys[chainId] = {
80
- address: deploymentInfo.worldAddress,
81
- // We expect the worlds file to be committed and since local deployments are often a consistent address but different block number, we'll ignore the block number.
82
- blockNumber: localChains.includes(chainId) ? undefined : deploymentInfo.blockNumber,
83
- };
84
- writeFileSync(mudConfig.worldsFile, JSON.stringify(deploys, null, 2));
85
-
86
- console.log(
87
- chalk.bgGreen(chalk.whiteBright(`\n Deployment result (written to ${mudConfig.worldsFile} and ${outputDir}): \n`))
88
- );
89
- }
90
-
91
- console.log(deploymentInfo);
92
- return deploymentInfo;
93
- }
@@ -1,23 +0,0 @@
1
- import KeysWithValueModuleData from "@latticexyz/world-modules/out/KeysWithValueModule.sol/KeysWithValueModule.json" assert { type: "json" };
2
- import KeysInTableModuleData from "@latticexyz/world-modules/out/KeysInTableModule.sol/KeysInTableModule.json" assert { type: "json" };
3
- import UniqueEntityModuleData from "@latticexyz/world-modules/out/UniqueEntityModule.sol/UniqueEntityModule.json" assert { type: "json" };
4
- import { ContractCode } from "../utils/types";
5
-
6
- // These modules are always deployed
7
- export const defaultModuleContracts: ContractCode[] = [
8
- {
9
- name: "KeysWithValueModule",
10
- abi: KeysWithValueModuleData.abi,
11
- bytecode: KeysWithValueModuleData.bytecode,
12
- },
13
- {
14
- name: "KeysInTableModule",
15
- abi: KeysInTableModuleData.abi,
16
- bytecode: KeysInTableModuleData.bytecode,
17
- },
18
- {
19
- name: "UniqueEntityModule",
20
- abi: UniqueEntityModuleData.abi,
21
- bytecode: UniqueEntityModuleData.bytecode,
22
- },
23
- ];
@@ -1,27 +0,0 @@
1
- import { defaultAbiCoder } from "ethers/lib/utils.js";
2
- import { resolveWithContext } from "@latticexyz/config";
3
- import { Module } from "./types";
4
- import { CallData } from "../utils/types";
5
- import { TableIds } from "../tables/types";
6
-
7
- export async function getInstallModuleCallData(
8
- moduleContracts: Record<string, Promise<string>>,
9
- module: Module,
10
- tableIds: TableIds
11
- ): Promise<CallData> {
12
- const moduleAddress = await moduleContracts[module.name];
13
- if (!moduleAddress) throw new Error(`Module ${module.name} not found`);
14
- // Resolve arguments
15
- const resolvedArgs = module.args.map((arg) =>
16
- resolveWithContext(arg, {
17
- tableIds,
18
- })
19
- );
20
- const values = resolvedArgs.map((arg) => arg.value);
21
- const types = resolvedArgs.map((arg) => arg.type);
22
-
23
- return {
24
- func: module.root ? "installRootModule" : "installModule",
25
- args: [moduleAddress, defaultAbiCoder.encode(types, values)],
26
- };
27
- }
@@ -1,5 +0,0 @@
1
- import { Module } from "./types";
2
-
3
- export function getUserModules(defaultModules: { name: string }[], configModules: Module[]): Omit<Module, "address">[] {
4
- return configModules.filter((module) => !defaultModules.some((m) => m.name === module.name));
5
- }
@@ -1,14 +0,0 @@
1
- export type Module = {
2
- name: string;
3
- root: boolean;
4
- args: (
5
- | {
6
- value: (string | number | Uint8Array) & (string | number | Uint8Array | undefined);
7
- type: string;
8
- }
9
- | {
10
- type: any;
11
- input: string;
12
- }
13
- )[];
14
- };
@@ -1,29 +0,0 @@
1
- import { System } from "./types";
2
- import { CallData } from "../utils/types";
3
- import { resourceIdToHex } from "@latticexyz/common";
4
-
5
- export async function getGrantAccessCallData(input: {
6
- systems: System[];
7
- systemContracts: Record<string, Promise<string>>;
8
- namespace: string;
9
- }): Promise<CallData[]> {
10
- const { systems, namespace, systemContracts } = input;
11
- const calls: CallData[] = [];
12
- for (const { name, accessListAddresses, accessListSystems } of systems) {
13
- // Grant access to addresses
14
- accessListAddresses.map(async (address) => calls.push(getGrantSystemAccessCallData(name, namespace, address)));
15
-
16
- // Grant access to other systems
17
- accessListSystems.map(async (granteeSystem) =>
18
- calls.push(getGrantSystemAccessCallData(name, namespace, await systemContracts[granteeSystem]))
19
- );
20
- }
21
- return calls;
22
- }
23
-
24
- function getGrantSystemAccessCallData(name: string, namespace: string, address: string): CallData {
25
- return {
26
- func: "grantAccess",
27
- args: [resourceIdToHex({ type: "system", namespace, name }), address],
28
- };
29
- }