Skip to content

Commit

Permalink
App + Subgraph: add Sepolia
Browse files Browse the repository at this point in the history
  • Loading branch information
bpierre committed Sep 24, 2024
1 parent 0a27c5b commit 0430cbf
Show file tree
Hide file tree
Showing 8 changed files with 132 additions and 86 deletions.
2 changes: 1 addition & 1 deletion frontend/app/.graphclient/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1305,7 +1305,7 @@ const liquity2Transforms = [];
const additionalTypeDefs = [] as any[];
const liquity2Handler = new GraphqlHandler({
name: "liquity2",
config: {"endpoint":"http://localhost:8000/subgraphs/name/liquity2/liquity2"},
config: {"endpoint":"https://api.studio.thegraph.com/query/42403/liquity2/version/latest"},
baseDir,
cache,
pubsub,
Expand Down
3 changes: 2 additions & 1 deletion frontend/app/.graphclientrc.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@ sources:
- name: liquity2
handler:
graphql:
endpoint: http://localhost:8000/subgraphs/name/liquity2/liquity2
# endpoint: http://localhost:8000/subgraphs/name/liquity2/liquity2
endpoint: https://api.studio.thegraph.com/query/42403/liquity2/version/latest

codegen:
strictScalars: true
Expand Down
11 changes: 4 additions & 7 deletions pnpm-lock.yaml

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

1 change: 1 addition & 0 deletions subgraph/.gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
/build/
/generated/
/networks-generated.json
162 changes: 93 additions & 69 deletions subgraph/cli/deploy-subgraph.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import YAML from "yaml";
import { $, echo, fs, minimist, path, question } from "zx";

const SUBGRAPH_PATH = path.join(__dirname, "../subgraph.yaml");
const LATEST_DEPLOYMENT_CONTEXT_PATH = path.join(__dirname, "../../contracts/deployment-context-latest.json");

const NETWORKS_JSON_PATH = path.join(__dirname, "../networks.json");
const GENERATED_NETWORKS_JSON_PATH = path.join(__dirname, "../networks-generated.json");

const HELP = `
deploy-subgraph - deploy the Liquity v2 subgraph
Expand All @@ -14,6 +14,7 @@ Arguments:
NETWORK_PRESET A network preset, which is a shorthand for setting certain options.
Options take precedence over network presets. Available presets:
- local: Deploy to a local network
- sepolia: Deploy to Ethereum Sepolia
- mainnet: Deploy to the Ethereum mainnet (not implemented)
- liquity-testnet: Deploy to the Liquity v2 testnet (not implemented)
Expand All @@ -25,6 +26,7 @@ Options:
--help, -h Show this help message.
--ipfs-node <IPFS_NODE_URL> The IPFS node URL to use.
--name <SUBGRAPH_NAME> The subgraph name to use.
--network <SUBGRAPH_NETWORK> The subgraph network to use.
--version <SUBGRAPH_VERSION> The subgraph version to use.
`;

Expand All @@ -41,24 +43,41 @@ const argv = minimist(process.argv.slice(2), {
"graph-node",
"ipfs-node",
"name",
"network",
"version",
],
});

export async function main() {
const { networkPreset, options } = await parseArgs();
const options = {
debug: argv["debug"],
help: argv["help"],
create: argv["create"],
graphNode: argv["graph-node"],
ipfsNode: argv["ipfs-node"],
name: argv["name"],
network: argv["network"], // subgraph network, not to be confused with the network preset
version: argv["version"],
};

const [networkPreset] = argv._;

if (options.help) {
echo`${HELP}`;
process.exit(0);
}

options.name ??= "liquity2/liquity2";

// network preset: local
if (networkPreset === "local") {
options.name ??= "liquity2/liquity2";
options.graphNode ??= "http://localhost:8020/";
options.ipfsNode ??= "http://localhost:5001/";
options.network ??= "local";
}

if (networkPreset === "sepolia") {
options.name ??= "liquity2";
options.network ??= "sepolia";
}

// network preset: liquity-testnet
Expand All @@ -71,41 +90,45 @@ export async function main() {
// TODO: implement
}

// handle missing options
if (!options.graphNode) {
throw new Error("--graph-node <GRAPH_NODE_URL> is required");
}
const isLocal = options.network === "local";
if (isLocal) options.network = "mainnet";

if (!options.name) {
throw new Error("--name <SUBGRAPH_NAME> is required");
}
if (!options.version) {
throw new Error("--version <SUBGRAPH_VERSION> is required");
if (!options.network) {
throw new Error("--network <SUBGRAPH_NETWORK> is required");
}
if (!options.ipfsNode) {
if (!options.graphNode && !options.network) {
throw new Error("--graph-node <GRAPH_NODE_URL> is required");
}
if (!options.ipfsNode && !options.network) {
throw new Error("--ipfs-node <IPFS_NODE_URL> is required");
}

const graphCreateCommand: null | string[] = !options.create ? null : [
const graphBuildCommand: string[] = [
"graph",
"create",
"--node",
options.graphNode,
options.name,
"build",
"--network",
options.network,
];

const graphDeployCommand: string[] = [
const graphCreateCommand: null | string[] = !options.create ? null : [
"graph",
"deploy",
"--node",
options.graphNode,
"--ipfs",
options.ipfsNode,
"create",
...(options.graphNode ? ["--node", options.graphNode] : []),
options.name,
"--version-label",
options.version,
];

await updateDeclarationWithLatestBoldToken();
const graphDeployCommand: string[] = ["graph", "deploy"];
if (options.graphNode) graphDeployCommand.push("--node", options.graphNode);
if (options.network) graphDeployCommand.push("--network", options.network);
if (options.version) graphDeployCommand.push("--version-label", options.version);
if (options.ipfsNode) graphDeployCommand.push("--ipfs", options.ipfsNode);
graphDeployCommand.push(options.name);

await updateNetworksWithLocalBoldToken();
await generateNetworksJson(isLocal);

echo`
Deploying subgraph:
Expand All @@ -120,6 +143,8 @@ Deploying subgraph:

$.verbose = options.debug;

await $`pnpm ${graphBuildCommand}`;

if (graphCreateCommand) {
await $`pnpm ${graphCreateCommand}`;
}
Expand All @@ -130,33 +155,32 @@ Deploying subgraph:
echo("");
}

async function parseArgs() {
const options = {
debug: argv["debug"],
help: argv["help"],
create: argv["create"],
graphNode: argv["graph-node"],
ipfsNode: argv["ipfs-node"],
name: argv["name"],
version: argv["version"],
};

const [networkPreset] = argv._;

return { options, networkPreset };
async function generateNetworksJson(isLocal = false) {
const networksJson = JSON.parse(await fs.readFile(NETWORKS_JSON_PATH, "utf8"));
return fs.writeFile(
GENERATED_NETWORKS_JSON_PATH,
JSON.stringify(
{
...networksJson,
mainnet: isLocal ? networksJson.local : networksJson.mainnet,
},
null,
2,
),
);
}

async function updateDeclarationWithLatestBoldToken() {
const declaration = subgraphDeclaration();
async function updateNetworksWithLocalBoldToken() {
const networksJson = JSON.parse(await fs.readFile(NETWORKS_JSON_PATH, "utf8"));
const latestDeploymentContext = getLatestDeploymentContext();

const deployedAddress = latestDeploymentContext?.protocolContracts.BoldToken;
if (!deployedAddress || (declaration.boldTokenAddress === deployedAddress)) {
if (!deployedAddress || (networksJson.local.BoldToken.address === deployedAddress)) {
return;
}

const answer = await question(
`\nNew BoldToken detected (${deployedAddress}). Update subgraph.yaml? [Y/n] `,
`\nNew BoldToken detected (${deployedAddress}) for local network. Update networks.json? [Y/n] `,
);

const confirmed = answer === "" || answer.toLowerCase() === "y" || answer.toLowerCase() === "yes";
Expand All @@ -165,31 +189,11 @@ async function updateDeclarationWithLatestBoldToken() {
return;
}

declaration.updateBoldTokenAddress(deployedAddress);
console.log("");
console.log("Subgraph declaration updated with CollateralRegistry:", deployedAddress);
}
networksJson.local.BoldToken.address = deployedAddress;
await fs.writeFile(NETWORKS_JSON_PATH, JSON.stringify(networksJson, null, 2));

function subgraphDeclaration() {
const declaration = YAML.parse(fs.readFileSync(SUBGRAPH_PATH, "utf8"));
const boldToken = declaration.dataSources.find((ds: any) => ds.name === "BoldToken");
return {
boldTokenAddress: boldToken.source.address,
updateBoldTokenAddress: (address: string) => {
const updatedDeclaration = {
...declaration,
dataSources: declaration.dataSources.map((ds: any) => (
ds.name === "BoldToken"
? { ...ds, source: { ...ds.source, address } }
: ds
)),
};
fs.writeFileSync(
SUBGRAPH_PATH,
YAML.stringify(updatedDeclaration, { lineWidth: 120 }),
);
},
};
console.log("");
console.log("networks.json updated with local BoldToken:", deployedAddress);
}

function getLatestDeploymentContext() {
Expand All @@ -199,3 +203,23 @@ function getLatestDeploymentContext() {
return null;
}
}

declare module "zx" {
type MinimistOptions<B extends string, S extends string> = {
string?: readonly S[];
boolean?: readonly B[];
alias?: { [key: string]: B | S };
default?: { [key in B | S]?: boolean | string };
};

type MinimistResult<B extends string, S extends string> =
& { _: string[] }
& { [K in B]: boolean }
& { [K in S]: string | undefined }
& { [K in string]: boolean | string | string[] };

function minimist<B extends string, S extends string>(
args: string[],
options?: MinimistOptions<B, S>,
): MinimistResult<B, S>;
}
19 changes: 19 additions & 0 deletions subgraph/networks.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
{
"local": {
"BoldToken": {
"address": "0x6112a1c20272a6fcc06abb8e8118e494993041ba"
}
},
"mainnet": {
"BoldToken": {
"address": "0x0000000000000000000000000000000000000000",
"startBlock": 0
}
},
"sepolia": {
"BoldToken": {
"address": "0x8b6142b0469bad2a695a25caa2d40778e06ada10",
"startBlock": 6631293
}
}
}
1 change: 0 additions & 1 deletion subgraph/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
"dependencies": {
"@graphprotocol/graph-ts": "^0.35.1",
"tsx": "^4.16.5",
"yaml": "^2.5.0",
"zx": "^8.1.4"
}
}
19 changes: 12 additions & 7 deletions subgraph/subgraph.yaml
Original file line number Diff line number Diff line change
@@ -1,13 +1,15 @@
specVersion: 1.2.0
indexerHints:
prune: auto
schema:
file: ./schema.graphql
dataSources:
- name: BoldToken
kind: ethereum/contract
network: mainnet
- kind: ethereum/contract
name: BoldToken
source:
address: "0x13a209a7c8d0ce1c6fd37aefbf65448519f6d3ce"
abi: BoldToken
address: "0x8b6142b0469bad2a695a25caa2d40778e06ada10"
startBlock: 6631293
mapping:
kind: ethereum/events
apiVersion: 0.0.9
Expand All @@ -31,10 +33,11 @@ dataSources:
- event: CollateralRegistryAddressChanged(address)
handler: handleCollateralRegistryAddressChanged
file: ./src/BoldToken.mapping.ts
network: sepolia
templates:
- name: TroveManager
kind: ethereum/contract
network: mainnet
network: sepolia
source:
abi: TroveManager
mapping:
Expand All @@ -50,7 +53,9 @@ templates:
- name: TroveNFT
file: ../contracts/out/TroveNFT.sol/TroveNFT.json
eventHandlers:
- event: TroveOperation(indexed uint256,uint8,uint256,uint256,uint256,int256,uint256,int256)
- event: TroveOperation(indexed
uint256,uint8,uint256,uint256,uint256,int256,uint256,int256)
handler: handleTroveOperation
- event: TroveUpdated(indexed uint256,uint256,uint256,uint256,uint256,uint256,uint256)
- event: TroveUpdated(indexed
uint256,uint256,uint256,uint256,uint256,uint256,uint256)
handler: handleTroveUpdated

0 comments on commit 0430cbf

Please sign in to comment.