@latticexyz/cli 2.0.9 → 2.0.10-230513-threejs-template-use-namespace-d6ab6d80
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.
- package/dist/commands-RH47YCPC.js +39 -0
- package/dist/commands-RH47YCPC.js.map +1 -0
- package/dist/mud.js +1 -1
- package/package.json +14 -14
- package/src/commands/verify.ts +2 -12
- package/src/deploy/common.ts +0 -1
- package/src/deploy/configToModules.ts +81 -0
- package/src/deploy/deploy.ts +5 -3
- package/src/deploy/ensureModules.ts +3 -2
- package/src/deploy/getFunctions.ts +37 -31
- package/src/deploy/resolveConfig.ts +2 -46
- package/src/runDeploy.ts +3 -0
- package/src/utils/getContractArtifact.ts +73 -0
- package/src/utils/knownModuleArtifacts.ts +8 -0
- package/src/verify.ts +11 -13
- package/dist/commands-UILDTPAU.js +0 -38
- package/dist/commands-UILDTPAU.js.map +0 -1
- package/src/utils/defaultModuleContracts.ts +0 -39
@@ -0,0 +1,39 @@
|
|
1
|
+
import{a as J}from"./chunk-QXUPZVZL.js";import Xs from"@latticexyz/gas-report";import ea from"@latticexyz/abi-ts";import{loadConfig as tt}from"@latticexyz/config/node";import{getSrcDirectory as rt}from"@latticexyz/common/foundry";import Yo from"node:path";import{tablegen as Go}from"@latticexyz/store/codegen";import{worldgen as Qo}from"@latticexyz/world/node";import{worldToV1 as Zo}from"@latticexyz/world/config/v2";import{forge as Xo,getRemappings as et}from"@latticexyz/common/foundry";import Jo from"glob";import{basename as qo}from"path";function k(e){return Jo.sync(`${e}/**/*.sol`).map(o=>({path:o,basename:qo(o,".sol")}))}import{execa as ot}from"execa";async function q({config:e,srcDir:o,foundryProfile:n=process.env.FOUNDRY_PROFILE}){let r=Zo(e),t=Yo.join(o,r.codegenDirectory),s=await et(n);await Promise.all([Go(e,t,s),Qo(e,k(o),t)]),await Xo(["build"],{profile:n}),await ot("mud",["abi-ts"],{stdio:"inherit"})}var nt={command:"build",describe:"Build contracts and generate MUD artifacts (table libraries, world interface, ABI)",builder(e){return e.options({configPath:{type:"string",desc:"Path to the MUD config file"},profile:{type:"string",desc:"The foundry profile to use"}})},async handler({configPath:e,profile:o}){let n=await tt(e),r=await rt();await q({config:n,srcDir:r,foundryProfile:o}),process.exit(0)}},Se=nt;import{rmSync as st}from"fs";import{homedir as at}from"os";import it from"path";import{execa as ct}from"execa";var dt={command:"devnode",describe:"Start a local Ethereum node for development",builder(e){return e.options({blocktime:{type:"number",default:1,decs:"Interval in which new blocks are produced"}})},async handler({blocktime:e}){console.log("Clearing devnode history");let o=at();st(it.join(o,".foundry","anvil","tmp"),{recursive:!0,force:!0});let n=["-b",String(e),"--block-base-fee-per-gas","0"];console.log(`Running: anvil ${n.join(" ")}`);let r=ct("anvil",n,{stdio:["inherit","inherit","inherit"]});process.on("SIGINT",()=>{console.log(`
|
2
|
+
gracefully shutting down from SIGINT (Crtl-C)`),r.kill(),process.exit()}),await r}},Ce=dt;import{FaucetServiceDefinition as lt}from"@latticexyz/services/faucet";import{createChannel as mt,createClient as pt}from"nice-grpc-web";import De from"chalk";import{NodeHttpTransport as ft}from"@improbable-eng/grpc-web-node-http-transport";function yt(e){return pt(lt,mt(e,ft()))}var ut={command:"faucet",describe:"Interact with a MUD faucet",builder(e){return e.options({dripDev:{type:"boolean",desc:"Request a drip from the dev endpoint (requires faucet to have dev mode enabled)",default:!0},faucetUrl:{type:"string",desc:"URL of the MUD faucet",default:"https://faucet.testnet-mud-services.linfra.xyz"},address:{type:"string",desc:"Ethereum address to fund",required:!0}})},async handler({dripDev:e,faucetUrl:o,address:n}){let r=yt(o);e&&(console.log(De.yellow("Dripping to",n)),await r.dripDev({address:n}),console.log(De.yellow("Success"))),process.exit(0)}},ve=ut;var gt={command:"hello <name>",describe:"Greet <name> with Hello",builder(e){return e.options({upper:{type:"boolean"}}).positional("name",{type:"string",demandOption:!0})},handler({name:e}){let o=`Gm, ${e}!`;console.log(o),process.exit(0)}},Te=gt;import bt from"path";import{loadConfig as ht}from"@latticexyz/config/node";import{tablegen as wt}from"@latticexyz/store/codegen";import{getRemappings as xt,getSrcDirectory as St}from"@latticexyz/common/foundry";var Ct={command:"tablegen",describe:"Autogenerate MUD Store table libraries based on the config file",builder(e){return e.options({configPath:{type:"string",desc:"Path to the MUD config file"}})},async handler({configPath:e}){let o=await ht(e),n=await St(),r=await xt();await wt(o,bt.join(n,o.codegen.outputDirectory),r),process.exit(0)}},Ae=Ct;import ue from"node:path";import{existsSync as Sn,mkdirSync as Cn,readFileSync as Dn,writeFileSync as ge}from"node:fs";import{getBalance as Pt,sendRawTransaction as It,sendTransaction as Pe,waitForTransactionReceipt as Ie}from"viem/actions";var A={gasPrice:1e11,gasLimit:1e5,signerAddress:"3fab184622dc19b6109349b94811493bf2a45362",transaction:"f8a58085174876e800830186a08080b853604580600e600039806000f350fe7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe03601600081602082378035828234f58015156039578182fd5b8082525050506014600cf31ba02222222222222222222222222222222222222222222222222222222222222222a02222222222222222222222222222222222222222222222222222222222222222",address:"4e59b44847b379578588920ca78fbf26c0b4956c",creationCode:"604580600e600039806000f350fe7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe03601600081602082378035828234f58015156039578182fd5b8082525050506014600cf3"};import ke from"debug";var Y=ke("mud:cli"),vt=ke("mud:cli");Y.log=console.debug.bind(console);vt.log=console.error.bind(console);var l=Y.extend("deploy"),Tt=Y.extend("deploy");l.log=console.debug.bind(console);Tt.log=console.error.bind(console);import{sliceHex as At}from"viem";import{getBytecode as kt}from"viem/actions";var G=`0x${A.address}`;async function Q(e){let o=await kt(e,{address:G});if(o)return l("found CREATE2 deployer at",G),o!==At(`0x${A.creationCode}`,14)&&console.warn(`
|
3
|
+
\u26A0\uFE0F Bytecode for deployer at ${G} did not match the expected CREATE2 bytecode. You may have unexpected results.
|
4
|
+
`),G}var le=`0x${A.address}`;async function Oe(e){let o=await Q(e);if(o!==void 0)return o;let n=BigInt(A.gasLimit)*BigInt(A.gasPrice),r=await Pt(e,{address:`0x${A.signerAddress}`}),t=n-r;if(t>0){l("sending gas for CREATE2 deployer to signer at",A.signerAddress);let a=await Pe(e,{chain:e.chain??null,to:`0x${A.signerAddress}`,value:t}),d=await Ie(e,{hash:a});if(d.status!=="success")throw console.error("failed to send gas to deployer signer",d),new Error("failed to send gas to deployer signer")}l("deploying CREATE2 deployer at",le);let s=await It(e,{serializedTransaction:`0x${A.transaction}`}).catch(a=>{if(String(a).includes("only replay-protected (EIP-155) transactions allowed over RPC"))return console.warn(`
|
5
|
+
\u26A0\uFE0F Your chain or RPC does not allow for non EIP-155 signed transactions, so your deploys will not be determinstic and contract addresses may change between deploys.
|
6
|
+
|
7
|
+
We recommend running your chain's node with \`--rpc.allow-unprotected-txs\` to enable determinstic deployments.
|
8
|
+
`),l("deploying CREATE2 deployer"),Pe(e,{chain:e.chain??null,data:`0x${A.creationCode}`});throw a}),i=await Ie(e,{hash:s});if(!i.contractAddress)throw new Error("Deploy receipt did not have contract address, was the deployer not deployed?");return i.contractAddress!==le&&console.warn(`
|
9
|
+
\u26A0\uFE0F CREATE2 deployer created at ${i.contractAddress} does not match the CREATE2 determinstic deployer we expected (${le})`),i.contractAddress}import{waitForTransactionReceipt as cr}from"viem/actions";import{waitForTransactionReceipt as Kt}from"viem/actions";import{concatHex as zt,getCreate2Address as Nt}from"viem";import{getBytecode as Lt}from"viem/actions";import{padHex as Mt}from"viem";import Wt from"@latticexyz/store/mud.config";import Bt from"@latticexyz/world/mud.config";import jt from"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json"assert{type:"json"};import Rt from"@latticexyz/world-modules/out/IModule.sol/IModule.abi.json"assert{type:"json"};import{resourceToHex as Ot}from"@latticexyz/common";import{resolveUserTypes as Me}from"@latticexyz/store/internal";function z(e){let o={...e.userTypes,...Object.fromEntries(Object.entries(e.enums).map(([n])=>[n,{internalType:"uint8"}]))};return Object.fromEntries(Object.entries(e.tables).map(([n,r])=>[`${e.namespace}_${n}`,{namespace:e.namespace,name:r.name,tableId:Ot({type:r.offchainOnly?"offchainTable":"table",namespace:e.namespace,name:r.name}),keySchema:Me(r.keySchema,o),valueSchema:Me(r.valueSchema,o)}]))}import{helloStoreEvent as Ht}from"@latticexyz/store";import{helloWorldEvent as Et}from"@latticexyz/world";import{storeToV1 as $t}from"@latticexyz/store/config/v2";import{worldToV1 as Ft}from"@latticexyz/world/config/v2";var x=Mt("0x",{size:32}),N=parseInt("6000",16),j=z($t(Wt)),v=z(Ft(Bt)),Z=[Ht,Et],T=[...jt,...Rt],We=["2.0.0","2.0.1","2.0.2"],Be=["2.0.0","2.0.1","2.0.2"];import{sendTransaction as Ut}from"@latticexyz/common";import Vt from"p-retry";import{wait as _t}from"@latticexyz/common/utils";async function je({client:e,deployerAddress:o,bytecode:n,deployedBytecodeSize:r,label:t="contract"}){if(n.includes("__$"))throw new Error(`Found unlinked public library in ${t} bytecode`);let s=Nt({from:o,salt:x,bytecode:n});return await Lt(e,{address:s,blockTag:"pending"})?(l("found",t,"at",s),[]):(r>N?console.warn(`
|
10
|
+
Bytecode for ${t} (${r} bytes) is over the contract size limit (${N} bytes). Run \`forge build --sizes\` for more info.
|
11
|
+
`):r>N*.95&&console.warn(`
|
12
|
+
Bytecode for ${t} (${r} bytes) is almost over the contract size limit (${N} bytes). Run \`forge build --sizes\` for more info.
|
13
|
+
`),l("deploying",t,"at",s),[await Vt(()=>Ut(e,{chain:e.chain??null,to:o,data:zt([x,n])}),{retries:3,onFailedAttempt:async a=>{let d=a.attemptNumber*500;l(`failed to deploy ${t}, retrying in ${d}ms...`),await _t(d)}})])}import{uniqueBy as Jt}from"@latticexyz/common/utils";async function I({client:e,deployerAddress:o,contracts:n}){let r=Jt(n,s=>s.bytecode),t=(await Promise.all(r.map(s=>je({client:e,deployerAddress:o,...s})))).flat();if(t.length){l("waiting for contracts");for(let s of t)await Kt(e,{hash:s})}return t}import ze from"@latticexyz/world/out/WorldFactory.sol/WorldFactory.json"assert{type:"json"};import Gt from"@latticexyz/world/out/WorldFactory.sol/WorldFactory.abi.json"assert{type:"json"};import{getCreate2Address as Qt,encodeDeployData as Zt,size as Xt}from"viem";import Re from"@latticexyz/world/out/AccessManagementSystem.sol/AccessManagementSystem.json"assert{type:"json"};import He from"@latticexyz/world/out/BalanceTransferSystem.sol/BalanceTransferSystem.json"assert{type:"json"};import Ee from"@latticexyz/world/out/BatchCallSystem.sol/BatchCallSystem.json"assert{type:"json"};import $e from"@latticexyz/world/out/RegistrationSystem.sol/RegistrationSystem.json"assert{type:"json"};import Fe from"@latticexyz/world/out/InitModule.sol/InitModule.json"assert{type:"json"};import qt from"@latticexyz/world/out/InitModule.sol/InitModule.abi.json"assert{type:"json"};import{getCreate2Address as L,encodeDeployData as Yt,size as U}from"viem";function X(e){let o=U(Re.deployedBytecode.object),n=Re.bytecode.object,r=L({from:e,bytecode:n,salt:x}),t=U(He.deployedBytecode.object),s=He.bytecode.object,i=L({from:e,bytecode:s,salt:x}),a=U(Ee.deployedBytecode.object),d=Ee.bytecode.object,c=L({from:e,bytecode:d,salt:x}),f=U($e.deployedBytecode.object),y=$e.bytecode.object,p=L({from:e,bytecode:y,salt:x}),g=U(Fe.deployedBytecode.object),b=Yt({bytecode:Fe.bytecode.object,abi:qt,args:[r,i,c,p]}),w=L({from:e,bytecode:b,salt:x});return{AccessManagementSystem:{bytecode:n,deployedBytecodeSize:o,label:"access management system",address:r},BalanceTransferSystem:{bytecode:s,deployedBytecodeSize:t,label:"balance transfer system",address:i},BatchCallSystem:{bytecode:d,deployedBytecodeSize:a,label:"batch call system",address:c},RegistrationSystem:{bytecode:y,deployedBytecodeSize:f,label:"core registration system",address:p},InitModule:{bytecode:b,deployedBytecodeSize:g,label:"core module",address:w}}}function ee(e){let o=X(e),n=Xt(ze.deployedBytecode.object),r=Zt({bytecode:ze.bytecode.object,abi:Gt,args:[o.InitModule.address]}),t=Qt({from:e,bytecode:r,salt:x});return{...o,WorldFactory:{bytecode:r,deployedBytecodeSize:n,label:"world factory",address:t}}}import Ne from"@latticexyz/world/out/WorldProxyFactory.sol/WorldProxyFactory.json"assert{type:"json"};import er from"@latticexyz/world/out/WorldProxyFactory.sol/WorldProxyFactory.abi.json"assert{type:"json"};import{getCreate2Address as or,encodeDeployData as tr,size as rr}from"viem";function oe(e){let o=X(e),n=rr(Ne.deployedBytecode.object),r=tr({bytecode:Ne.bytecode.object,abi:er,args:[o.InitModule.address]}),t=or({from:e,bytecode:r,salt:x});return{...o,WorldProxyFactory:{bytecode:r,deployedBytecodeSize:n,label:"world proxy factory",address:t}}}async function te(e,o,n){if(n){let t=oe(o);return await I({client:e,deployerAddress:o,contracts:Object.values(t)}),t.WorldProxyFactory.address}let r=ee(o);return await I({client:e,deployerAddress:o,contracts:Object.values(r)}),r.WorldFactory.address}import dr from"@latticexyz/world/out/WorldFactory.sol/WorldFactory.abi.json"assert{type:"json"};import{writeContract as lr}from"@latticexyz/common";import{AbiEventSignatureNotFoundError as nr,decodeEventLog as sr,hexToString as Le,parseAbi as ar}from"viem";import{isDefined as ir}from"@latticexyz/common/utils";function re(e){let o=e.map(i=>{try{return{...i,...sr({strict:!0,abi:ar(Z),topics:i.topics,data:i.data})}}catch(a){if(a instanceof nr)return;throw a}}).filter(ir),{address:n,deployBlock:r,worldVersion:t,storeVersion:s}=o.reduce((i,a)=>({...i,address:a.address,deployBlock:a.blockNumber,...a.eventName==="HelloWorld"?{worldVersion:Le(a.args.worldVersion).replace(/\0+$/,"")}:null,...a.eventName==="HelloStore"?{storeVersion:Le(a.args.storeVersion).replace(/\0+$/,"")}:null}),{});if(n==null)throw new Error("could not find world address");if(r==null)throw new Error("could not find world deploy block number");if(t==null)throw new Error("could not find world version");if(s==null)throw new Error("could not find store version");return{address:n,deployBlock:r,worldVersion:t,storeVersion:s}}async function Ue(e,o,n,r){let t=await te(e,o,r);l("deploying world");let s=await lr(e,{chain:e.chain??null,address:t,abi:dr,functionName:"deployWorld",args:[n]});l("waiting for world deploy");let i=await cr(e,{hash:s});if(i.status!=="success")throw console.error("world deploy failed",i),new Error("world deploy failed");let a=re(i.logs);return l("deployed world to",a.address,"at block",a.deployBlock),{...a,stateBlock:a.deployBlock}}import{resourceToLabel as me,writeContract as br}from"@latticexyz/common";import{valueSchemaToFieldLayoutHex as hr,keySchemaToHex as wr,valueSchemaToHex as xr}from"@latticexyz/protocol-parser/internal";import{parseAbiItem as mr,decodeAbiParameters as Ve,parseAbiParameters as _e}from"viem";import{hexToResource as pr}from"@latticexyz/common";import{storeSetRecordEvent as fr}from"@latticexyz/store";import{getLogs as yr}from"viem/actions";import{decodeKey as ur,decodeValueArgs as gr,hexToSchema as Ke}from"@latticexyz/protocol-parser/internal";async function Je({client:e,worldDeploy:o}){l("looking up tables for",o.address);let r=(await yr(e,{strict:!0,fromBlock:o.deployBlock,toBlock:o.stateBlock,address:o.address,event:mr(fr),args:{tableId:j.store_Tables.tableId}})).map(t=>{let{tableId:s}=ur(j.store_Tables.keySchema,t.args.keyTuple),{namespace:i,name:a}=pr(s),d=gr(j.store_Tables.valueSchema,t.args),c=Ke(d.keySchema),f=Ke(d.valueSchema),y=Ve(_e("string[]"),d.abiEncodedKeyNames)[0],p=Ve(_e("string[]"),d.abiEncodedFieldNames)[0],g=[...f.staticFields,...f.dynamicFields],b=Object.fromEntries(c.staticFields.map((u,S)=>[y[S],u])),w=Object.fromEntries(g.map((u,S)=>[p[S],u]));return{namespace:i,name:a,tableId:s,keySchema:b,valueSchema:w}});return l("found",r.length,"tables for",o.address),r}import Sr from"p-retry";import{wait as Cr}from"@latticexyz/common/utils";async function qe({client:e,worldDeploy:o,tables:n}){let t=(await Je({client:e,worldDeploy:o})).map(a=>a.tableId),s=n.filter(a=>t.includes(a.tableId));s.length&&l("existing tables",s.map(me).join(", "));let i=n.filter(a=>!t.includes(a.tableId));return i.length?(l("registering tables",i.map(me).join(", ")),await Promise.all(i.map(a=>Sr(()=>br(e,{chain:e.chain??null,address:o.address,abi:T,functionName:"registerTable",args:[a.tableId,hr(a.valueSchema),wr(a.keySchema),xr(a.valueSchema),Object.keys(a.keySchema),Object.keys(a.valueSchema)]}),{retries:3,onFailedAttempt:async d=>{let c=d.attemptNumber*500;l(`failed to register table ${me(a)}, retrying in ${c}ms...`),await Cr(c)}})))):[]}import{getAddress as M}from"viem";import{writeContract as pe,resourceToLabel as V}from"@latticexyz/common";import{parseAbiItem as Dr,HttpRequestError as vr}from"viem";import{getLogs as Tr}from"viem/actions";import{storeSpliceStaticDataEvent as Ar}from"@latticexyz/store";import kr from"p-retry";async function ne({client:e,worldDeploy:o}){l("looking up resource IDs for",o.address);let r=(await kr(()=>Tr(e,{strict:!0,address:o.address,fromBlock:o.deployBlock,toBlock:o.stateBlock,event:Dr(Ar),args:{tableId:j.store_ResourceIds.tableId}}),{retries:3,onFailedAttempt:async t=>{if(!(t instanceof vr&&t.status===400&&t.message.includes("block is out of range")))throw t}})).map(t=>t.args.keyTuple[0]);return l("found",r.length,"resource IDs for",o.address),r}import{hexToResource as Hr,resourceToLabel as Er}from"@latticexyz/common";import{decodeValueArgs as Pr,encodeKey as Ir}from"@latticexyz/protocol-parser/internal";import{readContract as Or}from"viem/actions";async function R({client:e,worldDeploy:o,table:n,key:r}){let[t,s,i]=await Or(e,{blockNumber:o.stateBlock,address:o.address,abi:T,functionName:"getRecord",args:[n.tableId,Ir(n.keySchema,r)]});return Pr(n.valueSchema,{staticData:t,encodedLengths:s,dynamicData:i})}import{parseAbiItem as Ye}from"viem";import{storeSetRecordEvent as Ge}from"@latticexyz/store";import{getLogs as Qe}from"viem/actions";import{decodeKey as Ze,decodeValueArgs as Xe}from"@latticexyz/protocol-parser/internal";async function se({client:e,worldDeploy:o}){l("looking up function selectors for",o.address);let r=(await Qe(e,{strict:!0,fromBlock:o.deployBlock,toBlock:o.stateBlock,address:o.address,event:Ye(Ge),args:{tableId:v.world_FunctionSelectors.tableId}})).map(a=>({...Xe(v.world_FunctionSelectors.valueSchema,a.args),...Ze(v.world_FunctionSelectors.keySchema,a.args.keyTuple)}));l("found",r.length,"function selectors for",o.address),l("looking up function signatures for",o.address);let t=await Qe(e,{strict:!0,fromBlock:o.deployBlock,toBlock:o.stateBlock,address:o.address,event:Ye(Ge),args:{tableId:v.world_FunctionSignatures.tableId}}),s=Object.fromEntries(t.map(a=>[Ze(v.world_FunctionSignatures.keySchema,a.args.keyTuple).functionSelector,Xe(v.world_FunctionSignatures.valueSchema,a.args).functionSignature]));return l("found",t.length,"function signatures for",o.address),r.map(({worldFunctionSelector:a,systemFunctionSelector:d,systemId:c})=>({selector:a,signature:s[a],systemFunctionSelector:d,systemFunctionSignature:s[d],systemId:c}))}import{parseAbiItem as Mr,getAddress as Wr}from"viem";import{storeSpliceStaticDataEvent as Br}from"@latticexyz/store";import{getLogs as jr}from"viem/actions";import{decodeKey as Rr}from"@latticexyz/protocol-parser/internal";async function ae({client:e,worldDeploy:o}){l("looking up resource access for",o.address);let r=(await jr(e,{strict:!0,fromBlock:o.deployBlock,toBlock:o.stateBlock,address:o.address,event:Mr(Br),args:{tableId:v.world_ResourceAccess.tableId}})).map(s=>Rr(v.world_ResourceAccess.keySchema,s.args.keyTuple)),t=(await Promise.all(r.map(async s=>[s,await R({client:e,worldDeploy:o,table:v.world_ResourceAccess,key:s})]))).filter(([,s])=>s.access).map(([s])=>({resourceId:s.resourceId,address:Wr(s.caller)}));return l("found",t.length,"resource<>address access pairs"),t}async function eo({client:e,worldDeploy:o}){let[n,r,t]=await Promise.all([ne({client:e,worldDeploy:o}),se({client:e,worldDeploy:o}),ae({client:e,worldDeploy:o})]),s=n.map(Hr).filter(i=>i.type==="system");return l("looking up systems",s.map(Er).join(", ")),await Promise.all(s.map(async i=>{let{system:a,publicAccess:d}=await R({client:e,worldDeploy:o,table:v.world_Systems,key:{systemId:i.resourceId}}),c=r.filter(f=>f.systemId===i.resourceId);return{address:a,namespace:i.namespace,name:i.name,systemId:i.resourceId,allowAll:d,allowedAddresses:t.filter(({resourceId:f})=>f===i.resourceId).map(({address:f})=>f),functions:c}}))}import{wait as fe}from"@latticexyz/common/utils";import ye from"p-retry";async function oo({client:e,deployerAddress:o,libraries:n,worldDeploy:r,systems:t}){let[s,i]=await Promise.all([eo({client:e,worldDeploy:r}),ae({client:e,worldDeploy:r})]),a=t.filter(m=>s.some(h=>h.systemId===m.systemId&&M(h.address)===M(m.prepareDeploy(o,n).address)));a.length&&l("existing systems",a.map(V).join(", "));let d=a.map(m=>m.systemId),c=t.filter(m=>!d.includes(m.systemId));if(!c.length)return[];let f=c.filter(m=>s.some(h=>h.systemId===m.systemId&&M(h.address)!==M(m.prepareDeploy(o,n).address)));f.length&&l("upgrading systems",f.map(V).join(", "));let y=c.filter(m=>!s.some(h=>h.systemId===m.systemId));y.length&&l("registering new systems",y.map(V).join(", ")),await I({client:e,deployerAddress:o,contracts:c.map(m=>({bytecode:m.prepareDeploy(o,n).bytecode,deployedBytecodeSize:m.deployedBytecodeSize,label:`${V(m)} system`}))});let p=await Promise.all(c.map(m=>ye(()=>pe(e,{chain:e.chain??null,address:r.address,abi:T,functionName:"registerSystem",args:[m.systemId,m.prepareDeploy(o,n).address,m.allowAll]}),{retries:3,onFailedAttempt:async h=>{let C=h.attemptNumber*500;l(`failed to register system ${V(m)}, retrying in ${C}ms...`),await fe(C)}}))),g=t.map(m=>m.systemId),b=i.filter(({resourceId:m})=>g.includes(m)),w=[...t.flatMap(m=>m.allowedAddresses.map(h=>({resourceId:m.systemId,address:h}))),...t.flatMap(m=>m.allowedSystemIds.map(h=>({resourceId:m.systemId,address:s.find(C=>C.systemId===h)?.address??t.find(C=>C.systemId===h)?.prepareDeploy(o,n).address})).filter(h=>h.address!=null))],u=w.filter(m=>!b.some(({resourceId:h,address:C})=>h===m.resourceId&&M(C)===M(m.address))),S=b.filter(m=>!w.some(({resourceId:h,address:C})=>h===m.resourceId&&M(C)===M(m.address)));S.length&&l("revoking",S.length,"access grants"),u.length&&l("adding",u.length,"access grants");let D=await Promise.all([...S.map(m=>ye(()=>pe(e,{chain:e.chain??null,address:r.address,abi:T,functionName:"revokeAccess",args:[m.resourceId,m.address]}),{retries:3,onFailedAttempt:async h=>{let C=h.attemptNumber*500;l(`failed to revoke access, retrying in ${C}ms...`),await fe(C)}})),...u.map(m=>ye(()=>pe(e,{chain:e.chain??null,address:r.address,abi:T,functionName:"grantAccess",args:[m.resourceId,m.address]}),{retries:3,onFailedAttempt:async h=>{let C=h.attemptNumber*500;l(`failed to grant access, retrying in ${C}ms...`),await fe(C)}}))]);return[...p,...D]}import{waitForTransactionReceipt as uo}from"viem/actions";import{getAddress as $r,parseAbi as Fr}from"viem";import{getBlockNumber as zr,getLogs as Nr}from"viem/actions";var to=new Map;async function ro(e,o){let n=$r(o),r=to.get(n);if(r!=null)return r;l("looking up world deploy for",n);let t=await zr(e),s=await Nr(e,{strict:!0,address:n,events:Fr(Z),fromBlock:"earliest",toBlock:t});return r={...re(s),stateBlock:t},to.set(n,r),l("found world deploy for",n,"at block",r.deployBlock),r}import{hexToResource as Lr,writeContract as no}from"@latticexyz/common";import so from"p-retry";import{wait as ao}from"@latticexyz/common/utils";async function io({client:e,worldDeploy:o,functions:n}){let r=await se({client:e,worldDeploy:o}),t=Object.fromEntries(r.map(a=>[a.selector,a])),s=n.filter(a=>t[a.selector]),i=n.filter(a=>!s.includes(a));if(s.length){l("functions already registered:",s.map(d=>d.signature).join(", "));let a=s.filter(d=>d.systemId!==t[d.selector]?.systemId);a.length&&console.warn("found",a.length,"functions already registered but pointing at a different system ID:",a.map(d=>d.signature).join(", "))}return i.length?(l("registering functions:",i.map(a=>a.signature).join(", ")),Promise.all(i.map(a=>{let{namespace:d}=Lr(a.systemId);return d===""?so(()=>no(e,{chain:e.chain??null,address:o.address,abi:T,functionName:"registerRootFunctionSelector",args:[a.systemId,a.systemFunctionSignature,a.systemFunctionSignature]}),{retries:3,onFailedAttempt:async c=>{let f=c.attemptNumber*500;l(`failed to register function ${a.signature}, retrying in ${f}ms...`),await ao(f)}}):so(()=>no(e,{chain:e.chain??null,address:o.address,abi:T,functionName:"registerFunctionSelector",args:[a.systemId,a.systemFunctionSignature]}),{retries:3,onFailedAttempt:async c=>{let f=c.attemptNumber*500;l(`failed to register function ${a.signature}, retrying in ${f}ms...`),await ao(f)}})}))):[]}import{BaseError as Ur}from"viem";import{writeContract as co}from"@latticexyz/common";import{isDefined as Vr,wait as _r}from"@latticexyz/common/utils";import Kr from"p-retry";async function lo({client:e,deployerAddress:o,libraries:n,worldDeploy:r,modules:t}){return t.length?(await I({client:e,deployerAddress:o,contracts:t.map(s=>({bytecode:s.prepareDeploy(o,n).bytecode,deployedBytecodeSize:s.deployedBytecodeSize,label:`${s.name} module`}))}),l("installing modules:",t.map(s=>s.name).join(", ")),(await Promise.all(t.map(s=>Kr(async()=>{try{let i=[...T,...s.abi],a=s.prepareDeploy(o,n).address;return s.installAsRoot?await co(e,{chain:e.chain??null,address:r.address,abi:i,functionName:"installRootModule",args:[a,s.installData]}):await co(e,{chain:e.chain??null,address:r.address,abi:i,functionName:"installModule",args:[a,s.installData]})}catch(i){if(i instanceof Ur&&i.message.includes("Module_AlreadyInstalled")){l(`module ${s.name} already installed`);return}throw i}},{retries:3,onFailedAttempt:async i=>{let a=i.attemptNumber*500;l(`failed to install module ${s.name}, retrying in ${a}ms...`),await _r(a)}})))).filter(Vr)):[]}import{getAddress as mo}from"viem";import{hexToResource as po,resourceToHex as fo,writeContract as Jr}from"@latticexyz/common";async function yo({client:e,worldDeploy:o,resourceIds:n}){let r=Array.from(new Set(n.map(y=>po(y).namespace))),t=await ne({client:e,worldDeploy:o}),s=new Set(t.map(y=>po(y).namespace));s.size&&l("found",s.size,"existing namespaces:",Array.from(s).map(y=>y===""?"<root>":y).join(", "));let i=r.filter(y=>s.has(y)),d=(await Promise.all(i.map(async y=>{let{owner:p}=await R({client:e,worldDeploy:o,table:v.world_NamespaceOwner,key:{namespaceId:fo({type:"namespace",namespace:y,name:""})}});return[y,p]}))).filter(([,y])=>mo(y)!==mo(e.account.address)).map(([y])=>y);if(d.length)throw new Error(`You are attempting to deploy to namespaces you do not own: ${d.join(", ")}`);let c=r.filter(y=>!s.has(y));return c.length>0&&l("registering namespaces",Array.from(c).join(", ")),Promise.all(c.map(y=>Jr(e,{chain:e.chain??null,address:o.address,abi:T,functionName:"registerNamespace",args:[fo({namespace:y,type:"namespace",name:""})]})))}import{resourceToLabel as qr}from"@latticexyz/common";import{randomBytes as Yr}from"crypto";async function go({client:e,config:o,modules:n=[],salt:r,worldAddress:t,deployerAddress:s,withWorldProxy:i}){let a=Object.values(o.tables),d=s??await Oe(e);await te(e,d,i),await I({client:e,deployerAddress:d,contracts:[...o.libraries.map(u=>({bytecode:u.prepareDeploy(d,o.libraries).bytecode,deployedBytecodeSize:u.deployedBytecodeSize,label:`${u.path}:${u.name} library`})),...o.systems.map(u=>({bytecode:u.prepareDeploy(d,o.libraries).bytecode,deployedBytecodeSize:u.deployedBytecodeSize,label:`${qr(u)} system`})),...n.map(u=>({bytecode:u.prepareDeploy(d,o.libraries).bytecode,deployedBytecodeSize:u.deployedBytecodeSize,label:`${u.name} module`}))]});let c=t?await ro(e,t):await Ue(e,d,r??`0x${Yr(32).toString("hex")}`,i);if(!We.includes(c.storeVersion))throw new Error(`Unsupported Store version: ${c.storeVersion}`);if(!Be.includes(c.worldVersion))throw new Error(`Unsupported World version: ${c.worldVersion}`);let f=await yo({client:e,worldDeploy:c,resourceIds:[...a.map(u=>u.tableId),...o.systems.map(u=>u.systemId)]});l("waiting for all namespace registration transactions to confirm");for(let u of f)await uo(e,{hash:u});let y=await qe({client:e,worldDeploy:c,tables:a}),p=await oo({client:e,deployerAddress:d,libraries:o.libraries,worldDeploy:c,systems:o.systems}),g=await io({client:e,worldDeploy:c,functions:o.systems.flatMap(u=>u.functions)}),b=await lo({client:e,deployerAddress:d,libraries:o.libraries,worldDeploy:c,modules:n}),w=[...y,...p,...g,...b];l("waiting for all transactions to confirm");for(let u of w)await uo(e,{hash:u});return l("deploy complete"),c}import{createWalletClient as vn,http as Tn,isHex as An}from"viem";import{privateKeyToAccount as kn}from"viem/accounts";import{loadConfig as Pn}from"@latticexyz/config/node";import{worldToV1 as In}from"@latticexyz/world/config/v2";import{getOutDirectory as On,getRpcUrl as Mn,getSrcDirectory as Wn}from"@latticexyz/common/foundry";import E from"chalk";import{MUDError as be}from"@latticexyz/common/errors";import nn from"path";import{resolveWorldConfig as sn}from"@latticexyz/world/internal";import{resourceToHex as wo}from"@latticexyz/common";import{toFunctionSelector as xo,toFunctionSignature as So}from"viem";import{readFileSync as Gr}from"fs";import Qr from"path";import{MUDError as ce}from"@latticexyz/common/errors";import{size as Zr}from"viem";function ie(e){return Object.entries(e).flatMap(([o,n])=>Object.entries(n).flatMap(([r,t])=>t.map(s=>({path:o,name:r,start:s.start,length:s.length}))))}function H(e,o,n){let r,t=Qr.join(n,e,o+".json");try{r=JSON.parse(Gr(t,"utf8"))}catch{throw new ce(`Error reading file at ${t}`)}let s=r?.bytecode?.object;if(!s)throw new ce(`No bytecode found in ${t}`);let i=r?.deployedBytecode?.object;if(!i)throw new ce(`No deployed bytecode found in ${t}`);let a=r?.abi;if(!a)throw new ce(`No ABI found in ${t}`);let d=ie(r?.bytecode?.linkReferences??{});return{abi:a,bytecode:s,placeholders:d,deployedBytecodeSize:Zr(i)}}import{groupBy as an}from"@latticexyz/common/utils";import{readFileSync as en}from"fs";import on from"glob";import Xr from"toposort";function bo(e,o,n){let r=Xr(e.flatMap(t=>n(t).map(s=>[o(t),s])));return[...e].sort((t,s)=>r.indexOf(o(t))-r.indexOf(o(s)))}function ho(e){let n=on.sync(`${e}/**/*.json`,{ignore:"**/*.abi.json"}).map(r=>JSON.parse(en(r,"utf8"))).flatMap(r=>{if(!r.metadata)return[];let t=Object.keys(r.metadata.settings.compilationTarget)[0],s=r.metadata.settings.compilationTarget[t],i=r.bytecode.linkReferences;return Object.entries(i).flatMap(([a,d])=>Object.keys(d).map(c=>({path:a,name:c,dependentPath:t,dependentName:s})))});return bo(n,r=>`${r.path}:${r.name}`,r=>[`${r.dependentPath}:${r.dependentName}`])}import{spliceHex as tn}from"@latticexyz/common";import{getCreate2Address as rn}from"viem";function _(e,o){return function(r,t){let s=e;for(let i of o){let a=t.find(d=>d.path===i.path&&d.name===i.name);if(!a)throw new Error(`Could not find library for bytecode placeholder ${i.path}:${i.name}`);s=tn(s,i.start,i.length,a.prepareDeploy(r,t).address)}return{bytecode:s,address:rn({from:r,bytecode:s,salt:x})}}}function Co({config:e,forgeSourceDir:o,forgeOutDir:n}){let r=ho(n).map(p=>{let g=H(nn.basename(p.path),p.name,n);return{path:p.path,name:p.name,abi:g.abi,prepareDeploy:_(g.bytecode,g.placeholders),deployedBytecodeSize:g.deployedBytecodeSize}}),t=z(e),s=k(o).map(({basename:p})=>p),i=sn(e,s),d=H("System.sol","System",n).abi.filter(p=>p.type==="function").map(So),c=Object.entries(i.systems).map(([p,g])=>{let b=e.namespace,w=g.name,u=wo({type:"system",namespace:b,name:w}),S=H(`${p}.sol`,p,n),D=S.abi.filter(m=>m.type==="function").map(So).filter(m=>!d.includes(m)).map(m=>{let h=b===""?m:`${b}__${m}`;return{signature:h,selector:xo(h),systemId:u,systemFunctionSignature:m,systemFunctionSelector:xo(m)}});return{namespace:b,name:w,systemId:u,allowAll:g.openAccess,allowedAddresses:g.accessListAddresses,allowedSystemIds:g.accessListSystems.map(m=>wo({type:"system",namespace:b,name:i.systems[m].name})),prepareDeploy:_(S.bytecode,S.placeholders),deployedBytecodeSize:S.deployedBytecodeSize,abi:S.abi,functions:D}}),f=an(c,p=>p.systemId),y=Array.from(f.values()).filter(p=>p.length>1).flat();if(y.length){let p=y.map(g=>g.name);throw new Error(`Found systems with overlapping system ID: ${p.join(", ")}.
|
14
|
+
|
15
|
+
System IDs are generated from the first 16 bytes of the name, so you may need to rename them to avoid the overlap.`)}return{tables:t,systems:c,libraries:r}}import{getChainId as Bn}from"viem/actions";import{existsSync as cn}from"fs";import dn from"path";import ln from"chalk";import{getScriptDirectory as mn,forge as pn}from"@latticexyz/common/foundry";async function Do(e,o,n,r,t,s){let i=t?.replaceAll("\\","").split(" ")??[],a=dn.join(await mn(),e+".s.sol");if(!cn(a)){console.log(`No script at ${a}, skipping post deploy hook`);return}console.log(ln.blue(`Executing post deploy script at ${a}`)),await pn(["script",e,"--broadcast","--sig","run(address)",o,"--rpc-url",n,"-vvv",s?"--aws":"",...i],{profile:r})}import{kmsKeyToAccount as jn}from"@latticexyz/common/kms";import ko from"node:path";import{resolveWithContext as bn}from"@latticexyz/config/library";import{encodeField as hn}from"@latticexyz/protocol-parser/internal";import{bytesToHex as wn,hexToBytes as xn}from"viem";import{isHex as fn,size as yn}from"viem";import{z as O}from"zod";import{Abi as un}from"abitype/zod";var vo=O.object({object:O.string().refine(fn),linkReferences:O.record(O.record(O.array(O.object({start:O.number(),length:O.number()}))))}),gn=O.object({bytecode:vo,deployedBytecode:vo,abi:un});async function To({artifactPath:e}){let o;try{o=(await import(e,{with:{type:"json"},assert:{type:"json"}})).default}catch(t){throw console.error(),console.error("Could not import contract artifact at",e),console.error(),t}let n=gn.parse(o),r=ie(n.bytecode.linkReferences);return{abi:n.abi,bytecode:n.bytecode.object,placeholders:r,deployedBytecodeSize:yn(n.deployedBytecode.object)}}var Ao={KeysWithValueModule:"@latticexyz/world-modules/out/KeysWithValueModule.sol/KeysWithValueModule.json",KeysInTableModule:"@latticexyz/world-modules/out/KeysInTableModule.sol/KeysInTableModule.json",UniqueEntityModule:"@latticexyz/world-modules/out/UniqueEntityModule.sol/UniqueEntityModule.json",Unstable_CallWithSignatureModule:"@latticexyz/world-modules/out/Unstable_CallWithSignatureModule.sol/Unstable_CallWithSignatureModule.json"};async function de(e,o){let n={tableIds:Object.fromEntries(Object.entries(e.tables).map(([t,s])=>[t,xn(s.tableId)]))};return await Promise.all(e.modules.map(async t=>{let s=t.artifactPath;if(!s)if(t.name)s=Ao[t.name]??ko.join(o,`${t.name}.sol`,`${t.name}.json`),console.warn(["","\u26A0\uFE0F Your `mud.config.ts` is using a module with a `name`, but this option is deprecated.","","To resolve this, you can replace this:","",` name: ${JSON.stringify(t.name)}`,"","with this:","",` artifactPath: ${JSON.stringify(s)}`,""].join(`
|
16
|
+
`));else throw new Error("No `artifactPath` provided for module.");let i=ko.basename(s,".json"),a=await To({artifactPath:s}),d=t.args.map(c=>bn(c,n)).map(c=>{let f=c.value instanceof Uint8Array?wn(c.value):c.value;return hn(c.type,f)});if(d.length>1)throw new Error(`${i} module should only have 0-1 args, but had ${d.length} args.`);return{name:i,installAsRoot:t.root,installData:d.length===0?"0x":d[0],prepareDeploy:_(a.bytecode,a.placeholders),deployedBytecodeSize:a.deployedBytecodeSize,abi:a.abi}}))}var P={configPath:{type:"string",desc:"Path to the MUD config file"},printConfig:{type:"boolean",desc:"Print the resolved config"},profile:{type:"string",desc:"The foundry profile to use"},saveDeployment:{type:"boolean",desc:"Save the deployment info to a file",default:!0},rpc:{type:"string",desc:"The RPC URL to use. Defaults to the RPC url from the local foundry.toml"},rpcBatch:{type:"boolean",desc:"Enable batch processing of RPC requests in viem client (defaults to batch size of 100 and wait of 1s)"},deployerAddress:{type:"string",desc:"Deploy using an existing deterministic deployer (https://github.com/Arachnid/deterministic-deployment-proxy)"},worldAddress:{type:"string",desc:"Deploy to an existing World at the given address"},srcDir:{type:"string",desc:"Source directory. Defaults to foundry src directory."},skipBuild:{type:"boolean",desc:"Skip rebuilding the contracts before deploying"},alwaysRunPostDeploy:{type:"boolean",desc:"Always run PostDeploy.s.sol after each deploy (including during upgrades). By default, PostDeploy.s.sol is only run once after a new world is deployed."},forgeScriptOptions:{type:"string",description:"Options to pass to forge script PostDeploy.s.sol"},salt:{type:"string",desc:"The deployment salt to use. Defaults to a random salt."},kms:{type:"boolean",desc:"Deploy the World with an AWS KMS key instead of local private key."}};async function $(e){let o=e.salt;if(o!=null&&!An(o))throw new be("Expected hex string for salt");let n=e.profile??process.env.FOUNDRY_PROFILE,r=await Pn(e.configPath),t=In(r);e.printConfig&&console.log(E.green(`
|
17
|
+
Resolved config:
|
18
|
+
`),JSON.stringify(t,null,2));let s=e.srcDir??await Wn(n),i=await On(n),a=e.rpc??await Mn(n);console.log(E.bgBlue(E.whiteBright(`
|
19
|
+
Deploying MUD contracts${n?" with profile "+n:""} to RPC ${a}
|
20
|
+
`))),e.skipBuild||await q({config:r,srcDir:s,foundryProfile:n});let d=Co({config:t,forgeSourceDir:s,forgeOutDir:i}),c=await de(r,i),f=await(async()=>{if(e.kms){let w=process.env.AWS_KMS_KEY_ID;if(!w)throw new be("Missing `AWS_KMS_KEY_ID` environment variable. This is required when using with `--kms` option.");return await jn({keyId:w})}else{let w=process.env.PRIVATE_KEY;if(!w)throw new be(`Missing PRIVATE_KEY environment variable.
|
21
|
+
Run 'echo "PRIVATE_KEY=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80" > .env'
|
22
|
+
in your contracts directory to use the default anvil private key.`);return kn(w)}})(),y=vn({transport:Tn(a,{batch:e.rpcBatch?{batchSize:100,wait:1e3}:void 0}),account:f});console.log("Deploying from",y.account.address);let p=Date.now(),g=await go({deployerAddress:e.deployerAddress,salt:o,worldAddress:e.worldAddress,client:y,config:d,modules:c,withWorldProxy:r.deploy.upgradeableWorldImplementation});(e.worldAddress==null||e.alwaysRunPostDeploy)&&await Do(t.postDeployScript,g.address,a,n,e.forgeScriptOptions,!!e.kms),console.log(E.green("Deployment completed in",(Date.now()-p)/1e3,"seconds"));let b={worldAddress:g.address,blockNumber:Number(g.deployBlock)};if(e.saveDeployment){let w=await Bn(y),u=ue.join(t.deploysDirectory,w.toString());Cn(u,{recursive:!0}),ge(ue.join(u,"latest.json"),JSON.stringify(b,null,2)),ge(ue.join(u,Date.now()+".json"),JSON.stringify(b,null,2));let S=[1337,31337],D=Sn(t.worldsFile)?JSON.parse(Dn(t.worldsFile,"utf-8")):{};D[w]={address:b.worldAddress,blockNumber:S.includes(w)?void 0:b.blockNumber},ge(t.worldsFile,JSON.stringify(D,null,2)),console.log(E.bgGreen(E.whiteBright(`
|
23
|
+
Deployment result (written to ${t.worldsFile} and ${u}):
|
24
|
+
`)))}return console.log(b),g}var Rn={command:"deploy",describe:"Deploy MUD contracts",builder(e){return e.options(P)},async handler(e){try{await $(e)}catch(o){J(o),process.exit(1)}process.exit(0)}},Po=Rn;import{loadConfig as Hn}from"@latticexyz/config/node";import{worldgen as En}from"@latticexyz/world/node";import{getSrcDirectory as $n}from"@latticexyz/common/foundry";import Io from"path";import{rmSync as Fn}from"fs";var zn={command:"worldgen",describe:"Autogenerate interfaces for Systems and World based on existing contracts and the config file",builder(e){return e.options({configPath:{type:"string",desc:"Path to the MUD config file"},clean:{type:"boolean",desc:"Clear the worldgen directory before generating new interfaces (defaults to true)",default:!0}})},async handler(e){await Nn(e),process.exit(0)}};async function Nn(e){let o=e.srcDir??await $n(),n=k(o),r=e.config??await Hn(e.configPath),t=Io.join(o,r.codegen.outputDirectory);e.clean&&Fn(Io.join(t,r.codegen.worldgenDirectory),{recursive:!0,force:!0}),await En(r,n,t)}var Oo=zn;import K from"chalk";import{readFileSync as Kn,writeFileSync as Jn}from"fs";import we from"path";import{MUDError as F}from"@latticexyz/common/errors";var Mo={name:"@latticexyz/cli",version:"2.0.9",description:"Command line interface for mud",repository:{type:"git",url:"https://github.com/latticexyz/mud.git",directory:"packages/cli"},license:"MIT",type:"module",exports:{".":"./dist/index.js"},types:"src/index.ts",bin:{mud:"./dist/mud.js"},scripts:{build:"pnpm run build:js && pnpm run build:test-tables","build:js":"tsup && chmod +x ./dist/mud.js","build:test-tables":"tsx ./scripts/generate-test-tables.ts",clean:"pnpm run clean:js && pnpm run clean:test-tables","clean:js":"rimraf dist","clean:test-tables":"rimraf src/codegen",dev:"tsup --watch",lint:"eslint . --ext .ts",prepare:"mkdir -p ./dist && touch ./dist/mud.js",test:"tsc --noEmit && forge test","test:ci":"pnpm run test"},dependencies:{"@aws-sdk/client-kms":"^3.556.0","@ethersproject/abi":"^5.7.0","@ethersproject/providers":"^5.7.2","@improbable-eng/grpc-web":"^0.15.0","@improbable-eng/grpc-web-node-http-transport":"^0.15.0","@latticexyz/abi-ts":"workspace:*","@latticexyz/common":"workspace:*","@latticexyz/config":"workspace:*","@latticexyz/gas-report":"workspace:*","@latticexyz/protocol-parser":"workspace:*","@latticexyz/schema-type":"workspace:*","@latticexyz/services":"workspace:*","@latticexyz/store":"workspace:*","@latticexyz/utils":"workspace:*","@latticexyz/world":"workspace:*","@latticexyz/world-modules":"workspace:*",abitype:"1.0.0","asn1.js":"^5.4.1",chalk:"^5.0.1",chokidar:"^3.5.3",debug:"^4.3.4",dotenv:"^16.0.3",ethers:"^5.7.2",execa:"^7.0.0",glob:"^8.0.3","nice-grpc-web":"^2.0.1",openurl:"^1.1.1","p-queue":"^7.4.1","p-retry":"^5.1.2",path:"^0.12.7",rxjs:"7.5.5","throttle-debounce":"^5.0.0",toposort:"^2.0.2",typescript:"5.4.2",viem:"2.9.20",yargs:"^17.7.1",zod:"^3.22.2","zod-validation-error":"^1.3.0"},devDependencies:{"@types/debug":"^4.1.7","@types/ejs":"^3.1.1","@types/glob":"^7.2.0","@types/node":"^18.15.11","@types/openurl":"^1.0.0","@types/throttle-debounce":"^5.0.0","@types/toposort":"^2.0.6","@types/yargs":"^17.0.10","ds-test":"https://github.com/dapphub/ds-test.git#e282159d5170298eb2455a6c05280ab5a73a4ef0","forge-std":"https://github.com/foundry-rs/forge-std.git#74cfb77e308dd188d2f58864aaf44963ae6b88b1",tsup:"^6.7.0",tsx:"^3.12.6",vitest:"0.34.6"}};import qn from"glob";import{ZodError as Un,z as Wo}from"zod";var Vn=Wo.object({MUD_PACKAGES:Wo.string().transform(e=>JSON.parse(e))});function _n(){try{return Vn.parse({MUD_PACKAGES:'{"@latticexyz/abi-ts":{"localPath":"packages/abi-ts"},"@latticexyz/block-logs-stream":{"localPath":"packages/block-logs-stream"},"@latticexyz/cli":{"localPath":"packages/cli"},"@latticexyz/common":{"localPath":"packages/common"},"@latticexyz/config":{"localPath":"packages/config"},"create-mud":{"localPath":"packages/create-mud"},"@latticexyz/dev-tools":{"localPath":"packages/dev-tools"},"@latticexyz/faucet":{"localPath":"packages/faucet"},"@latticexyz/gas-report":{"localPath":"packages/gas-report"},"@latticexyz/protocol-parser":{"localPath":"packages/protocol-parser"},"@latticexyz/query":{"localPath":"packages/query"},"@latticexyz/react":{"localPath":"packages/react"},"@latticexyz/recs":{"localPath":"packages/recs"},"@latticexyz/schema-type":{"localPath":"packages/schema-type"},"@latticexyz/services":{"localPath":"packages/services"},"solhint-config-mud":{"localPath":"packages/solhint-config-mud"},"solhint-plugin-mud":{"localPath":"packages/solhint-plugin-mud"},"@latticexyz/store-indexer":{"localPath":"packages/store-indexer"},"@latticexyz/store-sync":{"localPath":"packages/store-sync"},"@latticexyz/store":{"localPath":"packages/store"},"@latticexyz/utils":{"localPath":"packages/utils"},"@latticexyz/world-modules":{"localPath":"packages/world-modules"},"@latticexyz/world":{"localPath":"packages/world"}}'})}catch(e){if(e instanceof Un){let{...o}=e.format();console.error(`
|
25
|
+
Missing or invalid environment variables:
|
26
|
+
|
27
|
+
${Object.keys(o).join(`
|
28
|
+
`)}
|
29
|
+
`),process.exit(1)}throw e}}var he=_n().MUD_PACKAGES;var Yn={command:"set-version",describe:"Set MUD version in all package.json files and optionally backup the previously installed version",builder(e){return e.options({mudVersion:{alias:"v",type:"string",description:"Set MUD to the given version"},tag:{alias:"t",type:"string",description:"Set MUD to the latest version with the given tag from npm"},commit:{alias:"c",type:"string",description:"Set MUD to the version based on a given git commit hash from npm"},link:{alias:"l",type:"string",description:"Relative path to the local MUD root directory to link"}})},async handler(e){try{let o=["mudVersion","link","tag","commit","restore"],n=o.reduce((t,s)=>e[s]?t+1:t,0);if(n===0)throw new F(`You need to provide one these options: ${o.join(", ")}`);if(n>1)throw new F(`These options are mutually exclusive: ${o.join(", ")}`);e.link||(e.mudVersion=await Gn(e));let r=qn.sync("**/package.json").filter(t=>!t.includes("node_modules"));for(let t of r)Qn(t,e)}catch(o){J(o)}finally{process.exit(0)}}};async function Gn(e){e.mudVersion==="canary"&&(e.tag="main");let o;try{console.log(K.blue("Fetching available versions")),o=await(await fetch(`https://registry.npmjs.org/${Mo.name}`)).json()}catch{throw new F("Could not fetch available MUD versions")}if(e.tag){let n=o["dist-tags"][e.tag];if(!n)throw new F(`Could not find npm version with tag "${e.tag}"`);return console.log(K.green(`Latest version with tag ${e.tag}: ${n}`)),n}if(e.commit){let n=e.commit.substring(0,8),r=Object.keys(o.versions).find(t=>t.includes(n));if(!r)throw new F(`Could not find npm version based on commit "${e.commit}"`);return console.log(K.green(`Version from commit ${e.commit}: ${r}`)),r}return e.mudVersion}function Qn(e,o){let{link:n}=o,{mudVersion:r}=o,t=Zn(e),s=Object.keys(he),i={};for(let c in t.dependencies)s.includes(c)&&(i[c]=t.dependencies[c]);let a={};for(let c in t.devDependencies)s.includes(c)&&(a[c]=t.devDependencies[c]);for(let c in t.dependencies)s.includes(c)&&(t.dependencies[c]=d(c,"dependencies"));for(let c in t.devDependencies)s.includes(c)&&(t.devDependencies[c]=d(c,"devDependencies"));return Jn(e,JSON.stringify(t,null,2)+`
|
30
|
+
`),console.log(`Updating ${e}`),Bo(i,t.dependencies),Bo(a,t.devDependencies),t;function d(c,f){return n&&(r=Xn(e,n,c)),r||t[f][c]}}function Zn(e){try{let o=Kn(e,"utf8");return JSON.parse(o)}catch{throw new F("Could not read JSON at "+e)}}function Bo(e,o){for(let n in e)e[n]!==o[n]&&console.log(`${n}: ${K.red(e[n])} -> ${K.green(o[n])}`)}function Xn(e,o,n){let r=we.relative(we.dirname(e),process.cwd());return"link:"+we.join(r,o,he[n].localPath)}var jo=Yn;import{anvil as es,forge as os,getRpcUrl as ts}from"@latticexyz/common/foundry";import rs from"chalk";var ns={...P,port:{type:"number",description:"Port to run internal node for fork testing on",default:4242},worldAddress:{type:"string",description:"Address of an existing world contract. If provided, deployment is skipped and the RPC provided in the foundry.toml is used for fork testing."},forgeOptions:{type:"string",description:"Options to pass to forge test"}},ss={command:"test",describe:"Run tests in MUD contracts",builder(e){return e.options(ns)},async handler(e){if(!e.worldAddress){let t=["--block-base-fee-per-gas","0","--port",String(e.port)];es(t)}let o=e.worldAddress?await ts(e.profile):`http://127.0.0.1:${e.port}`,n=e.worldAddress??(await $({...e,saveDeployment:!1,rpc:o})).address;console.log(rs.blue("World address",n));let r=e.forgeOptions?.replaceAll("\\","").split(" ")??[];try{await os(["test","--fork-url",o,...r],{profile:e.profile,env:{WORLD_ADDRESS:n}}),process.exit(0)}catch(t){console.error(t),process.exit(1)}}},Ro=ss;import{existsSync as as,readFileSync as is}from"fs";import{ethers as Ho}from"ethers";import{loadConfig as cs}from"@latticexyz/config/node";import{MUDError as Eo}from"@latticexyz/common/errors";import{cast as ds,getRpcUrl as ls,getSrcDirectory as ms}from"@latticexyz/common/foundry";import{resolveWorldConfig as ps}from"@latticexyz/world/internal";import fs from"@latticexyz/world/out/IBaseWorld.sol/IBaseWorld.abi.json"assert{type:"json"};import $o from"@latticexyz/world/mud.config";import{resourceToHex as zo}from"@latticexyz/common";import{createClient as ys,http as us}from"viem";import{getChainId as gs}from"viem/actions";import{worldToV1 as bs}from"@latticexyz/world/config/v2";var Fo=zo({type:"system",namespace:$o.namespace,name:$o.tables.world__Systems.name}),hs={command:"trace",describe:"Display the trace of a transaction",builder(e){return e.options({tx:{type:"string",required:!0,description:"Transaction hash to replay"},worldAddress:{type:"string",description:"World contract address. Defaults to the value from worlds.json, based on rpc's chainId"},configPath:{type:"string",description:"Path to the MUD config file"},profile:{type:"string",description:"The foundry profile to use"},srcDir:{type:"string",description:"Source directory. Defaults to foundry src directory."},rpc:{type:"string",description:"json rpc endpoint. Defaults to foundry's configured eth_rpc_url"}})},async handler(e){e.profile??=process.env.FOUNDRY_PROFILE;let{profile:o}=e;e.srcDir??=await ms(o),e.rpc??=await ls(o);let{tx:n,configPath:r,srcDir:t,rpc:s}=e,i=k(t),a=await cs(r),d=bs(a),c=ps(d,i.map(({basename:D})=>D)),f=e.worldAddress??await ws(d.worldsFile,s),y=new Ho.providers.StaticJsonRpcProvider(s),p=new Ho.Contract(f,fs,y),g=d.namespace,b=Object.values(c.systems).map(({name:D})=>D),w=await p.getFieldLayout(Fo),u=[];for(let D of b){let m=zo({type:"system",namespace:g,name:D}),h=await p.getField(Fo,[m],0,w);u.push({name:D,address:h})}let S=await ds(["run","--label",`${f}:World`,...u.map(({name:D,address:m})=>["--label",`${m}:${D}`]).flat(),`${n}`]);console.log(S),process.exit(0)}},No=hs;async function ws(e,o){if(as(e)){let n=ys({transport:us(o)}),r=await gs(n),t=JSON.parse(is(e,"utf-8"));if(!t[r])throw new Eo(`chainId ${r} is missing in worldsFile "${e}"`);return t[r].address}else throw new Eo("worldAddress is not specified and worldsFile is missing")}import{anvil as xs,getScriptDirectory as Ss,getSrcDirectory as Cs}from"@latticexyz/common/foundry";import W from"chalk";import Ds from"chokidar";import{loadConfig as vs,resolveConfigPath as Ts}from"@latticexyz/config/node";import As from"path";import{homedir as ks}from"os";import{rmSync as Ps}from"fs";import{BehaviorSubject as Is,debounceTime as Os,exhaustMap as Ms,filter as Ws}from"rxjs";import{isDefined as Bs}from"@latticexyz/common/utils";var js={rpc:P.rpc,configPath:P.configPath,alwaysRunPostDeploy:P.alwaysRunPostDeploy,forgeScriptOptions:P.forgeScriptOptions,worldAddress:P.worldAddress},Rs={command:"dev-contracts",describe:"Start a development server for MUD contracts",builder(e){return e.options(js)},async handler(e){let o=e.rpc,n=e.configPath??await Ts(e.configPath),r=await Cs(),t=await Ss(),s=await vs(n);if(!e.rpc){console.log(W.gray("Cleaning devnode cache"));let c=ks();Ps(As.join(c,".foundry","anvil","tmp"),{recursive:!0,force:!0}),xs(["--block-time","1","--block-base-fee-per-gas","0"]),o="http://127.0.0.1:8545"}let i=new Is(Date.now());Ds.watch([n,r,t],{ignoreInitial:!0}).on("all",async(c,f)=>{f.includes(n)&&(console.log(W.blue("Config changed, queuing deploy\u2026")),i.next(Date.now())),(f.includes(r)||f.includes(t))&&(f.includes(s.codegen.outputDirectory)||(console.log(W.blue("Contracts changed, queuing deploy\u2026")),i.next(Date.now())))});let a=e.worldAddress;i.pipe(Os(200),Ms(async c=>{a&&console.log(W.blue("Rebuilding and upgrading world\u2026"));try{let f=await $({...e,configPath:n,rpc:o,rpcBatch:!1,skipBuild:!1,printConfig:!1,profile:void 0,saveDeployment:!0,deployerAddress:void 0,worldAddress:a,srcDir:r,salt:"0x",kms:void 0});return a=f.address,c<i.value?i.next(i.value):console.log(W.gray(`
|
31
|
+
Waiting for file changes\u2026
|
32
|
+
`)),f}catch(f){console.error(W.bgRed(W.whiteBright(`
|
33
|
+
Error while attempting deploy
|
34
|
+
`))),console.error(f),console.log(W.gray(`
|
35
|
+
Waiting for file changes\u2026
|
36
|
+
`))}}),Ws(Bs)).subscribe()}},Lo=Rs;import{getCreate2Address as Uo,sliceHex as Es,zeroHash as $s}from"viem";import{forge as Hs}from"@latticexyz/common/foundry";async function B(e){let o=["verify-contract",e.address,e.name,"--rpc-url",e.rpc];e.verifier&&o.push("--verifier",e.verifier),e.verifierUrl&&o.push("--verifier-url",e.verifierUrl),await Hs(o,{cwd:e.cwd})}import Fs from"p-queue";import{MUDError as zs}from"@latticexyz/common/errors";import{getStorageAt as Ns}from"viem/actions";import{execa as xe}from"execa";var Ls="0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc";async function Vo({client:e,rpc:o,systems:n,modules:r,worldAddress:t,deployerAddress:s,verifier:i,verifierUrl:a}){let d=s??await Q(e);if(!d)throw new zs("No deployer address provided or found.");let c=await Ns(e,{address:t,slot:Ls}),f=c&&c!==$s,y=new Fs({concurrency:4});if(n.map(({name:p,bytecode:g})=>y.add(()=>B({name:p,rpc:o,verifier:i,verifierUrl:a,address:Uo({from:d,bytecode:g,salt:x})}).catch(b=>{console.error(`Error verifying system contract ${p}:`,b)}))),i==="sourcify")if(await xe("npm",["install"],{cwd:"node_modules/@latticexyz/store"}),await xe("npm",["install"],{cwd:"node_modules/@latticexyz/world"}),await xe("npm",["install"],{cwd:"node_modules/@latticexyz/world-modules"}),Object.entries(f?oe(d):ee(d)).map(([p,{bytecode:g}])=>y.add(()=>B({cwd:"node_modules/@latticexyz/world",name:p,rpc:o,verifier:i,verifierUrl:a,address:Uo({from:d,bytecode:g,salt:x})}).catch(b=>{console.error(`Error verifying world factory contract ${p}:`,b)}))),r.map(({name:p,prepareDeploy:g})=>{let{address:b}=g(d,[]);return y.add(()=>B({cwd:"node_modules/@latticexyz/world-modules",name:p,rpc:o,verifier:i,verifierUrl:a,address:b}).catch(w=>{console.error(`Error verifying module contract ${p}:`,w)}))}),f){let p=Es(c,-20);y.add(()=>B({cwd:"node_modules/@latticexyz/world",name:"WorldProxy",rpc:o,verifier:i,verifierUrl:a,address:t}).catch(g=>{console.error("Error verifying WorldProxy contract:",g)})),y.add(()=>B({cwd:"node_modules/@latticexyz/world",name:"World",rpc:o,verifier:i,verifierUrl:a,address:p}).catch(g=>{console.error("Error verifying World contract:",g)}))}else y.add(()=>B({cwd:"node_modules/@latticexyz/world",name:"World",rpc:o,verifier:i,verifierUrl:a,address:t}).catch(p=>{console.error("Error verifying World contract:",p)}));else console.log(""),console.log(`Note: MUD is currently unable to verify store, world, and world-modules contracts with ${i}. We are planning to expand support in a future version.`),console.log("")}import{loadConfig as Us}from"@latticexyz/config/node";import{resolveWorldConfig as Vs}from"@latticexyz/world/internal";import{worldToV1 as _s}from"@latticexyz/world/config/v2";import{getOutDirectory as Ks,getRpcUrl as Js,getSrcDirectory as qs}from"@latticexyz/common/foundry";import{createWalletClient as Ys,http as Gs}from"viem";import _o from"chalk";var Qs={deployerAddress:{type:"string",desc:"Deploy using an existing deterministic deployer (https://github.com/Arachnid/deterministic-deployment-proxy)"},worldAddress:{type:"string",required:!0,desc:"Verify an existing World at the given address"},configPath:{type:"string",desc:"Path to the MUD config file"},profile:{type:"string",desc:"The foundry profile to use"},rpc:{type:"string",desc:"The RPC URL to use. Defaults to the RPC url from the local foundry.toml"},rpcBatch:{type:"boolean",desc:"Enable batch processing of RPC requests in viem client (defaults to batch size of 100 and wait of 1s)"},srcDir:{type:"string",desc:"Source directory. Defaults to foundry src directory."},verifier:{type:"string",desc:"The verifier to use. Defaults to blockscout",default:"blockscout"},verifierUrl:{type:"string",desc:"The verification provider."}},Zs={command:"verify",describe:"Verify contracts",builder(e){return e.options(Qs)},async handler(e){let o=e.profile??process.env.FOUNDRY_PROFILE,n=await Us(e.configPath),r=_s(n),t=e.srcDir??await qs(o),s=await Ks(o),i=e.rpc??await Js(o);console.log(_o.bgBlue(_o.whiteBright(`
|
37
|
+
Verifying MUD contracts${o?" with profile "+o:""} to RPC ${i}
|
38
|
+
`)));let a=Ys({transport:Gs(i,{batch:e.rpcBatch?{batchSize:100,wait:1e3}:void 0})}),d=k(t).map(({basename:p})=>p),c=Vs(r,d),f=Object.keys(c.systems).map(p=>{let g=H(`${p}.sol`,p,s);return{name:p,bytecode:g.bytecode}}),y=await de(n,s);await Vo({client:a,rpc:i,systems:f,modules:y,deployerAddress:e.deployerAddress,worldAddress:e.worldAddress,verifier:e.verifier,verifierUrl:e.verifierUrl})}},Ko=Zs;var Ty=[Se,Po,Ce,ve,Xs,Te,Ae,Oo,jo,Ro,No,Lo,ea,Ko];export{Ty as commands};
|
39
|
+
//# sourceMappingURL=commands-RH47YCPC.js.map
|