Skip to content
New issue

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

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

Already on GitHub? Sign in to your account

Add localnet command #16

Merged
merged 28 commits into from
Sep 11, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
4ca6b76
chore(security): add workflow for leaked secrets monitoring
otani88 Feb 20, 2023
eeb45ec
Implement localnet subcommand
jpcenteno May 3, 2023
68a67ad
Use import instead of require to get type definitons.
jpcenteno May 4, 2023
a4c8d71
Cleanup
jpcenteno May 4, 2023
1a09eae
Point local-setup repo to our branch. Interface with docker-compose d…
jpcenteno May 11, 2023
cebc398
Merge pull request #2 from lambdaclass/feat-local-node
mationorato May 17, 2023
a8d342c
Add `localnet` subcommand to the README
jpcenteno May 30, 2023
1acd846
Merge pull request #5 from lambdaclass/document-localnet-subcommand
mationorato Jun 1, 2023
3973ee2
update docker compose from v1 to v2
mationorato Jun 1, 2023
d90245b
Update local-setup repo url to matter-labs main branch
mationorato Jun 5, 2023
5940293
update REPO_URL and REPO_BRANCH in ts file
mationorato Jun 5, 2023
4d44048
Merge branch 'upstream:main' into fix-merge-conflicts-with-matterlabs…
jpcenteno Jul 20, 2023
55b145c
Update help
jpcenteno Jul 20, 2023
860f415
Merge pull request #7 from lambdaclass/fix-merge-conflicts-with-matte…
jpcenteno Jul 20, 2023
edddec3
Update README.md
mationorato Aug 15, 2023
40b8aa8
Document why repoDirectory is using XDG_STATE_HOME
jpcenteno Sep 4, 2023
c58b62b
Remove new bin/ files introduced from our fork
jpcenteno Sep 4, 2023
f2a9ecf
Fix pkg version
jpcenteno Sep 4, 2023
724a224
Replace zksync 2.0 with Era for branding consistency
jpcenteno Sep 4, 2023
4dd22b2
Merge branch 'address-matterlabs-review-comments'
jpcenteno Sep 4, 2023
fcd11b1
Merge branch 'main' into main
jpcenteno Sep 4, 2023
21ea0bb
Update package lock
jpcenteno Sep 4, 2023
fbd18ed
Revert "Update package lock"
jpcenteno Sep 4, 2023
ec6a3e8
Fix messing newline at end of file
jpcenteno Sep 4, 2023
04eaa91
Address CI messages
jpcenteno Sep 4, 2023
cb5a4ba
Export localnet help function
jpcenteno Sep 4, 2023
38c14a3
Merge remote-tracking branch 'upstream/main'
jpcenteno Sep 6, 2023
7ffb3ea
fix: refactor localnet module to follow new project structure
jpcenteno Sep 6, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,14 @@ You can install this program globally with `npm i -g zksync-cli` or run the comm

- `zksync-cli --version`: Returns the current version

- `zksync-cli localnet`: Manages a local zkSync Era and Ethereum L1 testnet (it requires docker running on your system). It supports a set of sub-subcommands:
- `zksync-cli localnet up`: Bootstrap L1 and L2 localnets.
- `zksync-cli localnet down`: clear L1 and L2 localnets.
- `zksync-cli localnet start`: start L1 and L2 localnets.
- `zksync-cli localnet stop`: stop L1 and L2 localnets.
- `zksync-cli localnet logs`: Display logs.
- `zksync-cli localnet help`: Display this message and quit.
- `zksync-cli localnet wallets`: Display seeded wallet keys.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.


### 🔗 Supported chains

Expand Down
122 changes: 122 additions & 0 deletions src/commands/localnet.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
import { program } from "../setup";
import { execSync, ExecSyncOptions } from 'child_process';
import * as path from 'path';
import * as fs from 'fs';
import * as os from 'os';

const REPO_URL: string = "https://github.com/matter-labs/local-setup.git";
const REPO_BRANCH: string = "main"

// ---------------------------------------------------------------------------------------
// Utilities
// ---------------------------------------------------------------------------------------

function runSystemCommand(command: string, options?: ExecSyncOptions): string {
const defaultOptions: ExecSyncOptions = { cwd: repoDirectory(), encoding: 'utf-8' };
const unifiedOptions: ExecSyncOptions = {...defaultOptions, ...options};
return execSync(command, unifiedOptions).toString();
}

/**
* Returns the path where the `zksync-cli/local-setup` repository, used
* internally to manage localnet deployments, should be located.
*
* **Why follow the XDG Base Directory Specification?**
*
* This function follows the XDG Base Directory Specification
* (https://specifications.freedesktop.org/basedir-spec/basedir-spec-latest.html)
* to determine the parent directory location:
*
* The XDG Base Directory Specification is widely accepted as a standard.
* The decision to place the files under `$XDG_STATE_HOME` is based on considering the
* presence or absence of this repository as part of the CLI tool's state.
*
* Alternative locations within the XDG Base Directory Specification were
* considered and ruled out for the following reasons:
*
* - `$XDG_DATA_HOME` was not chosen because these files aren't user-specific
* data files.
*
* - `$XDG_CACHE_HOME` was not chosen because these files aren't considered
* non-essential cached data files.
*
* @returns {string} The path where the `zksync-cli/local-setup` repository should be
* placed.
*/
function repoDirectory(): string {
// From the XDG Base Directory Specification:
// `$XDG_STATE_HOME` defines the base directory relative to which user-specific state files should be stored. If `$XDG_STATE_HOME` is either not set or empty, a default equal to `$HOME/.local/state` should be used.
const xdgStateHome = process.env.XDG_STATE_HOME || path.join(os.homedir(), ".local/state");
return path.join(xdgStateHome, "zksync-cli/local-setup");
}

function isRepoCloned(): boolean {
return fs.existsSync(repoDirectory());
}

function cloneRepo() {
const parentDirectory = path.join(repoDirectory(), "..");
runSystemCommand(`mkdir -p '${parentDirectory}'`, { cwd: "/" });
const options: ExecSyncOptions = { cwd: parentDirectory };
runSystemCommand(`git clone --branch '${REPO_BRANCH}' '${REPO_URL}'`, options);
}

function setUp() {
cloneRepo();
}

// ---------------------------------------------------------------------------------------
// Command handling
// ---------------------------------------------------------------------------------------

const localnet = program
.command("localnet")
.description("Manage local L1 and L2 chains");

localnet
.command("up")
.description("Startup L1 and L2 localnets")
.action(() => {
if (! isRepoCloned()) {
setUp();
}
runSystemCommand("docker compose up --detach");
});

localnet
.command("down")
.description("clear L1 and L2 localnets")
.action(() => {
runSystemCommand("docker compose down --volumes");
});

localnet
.command("start")
.description("start L1 and L2 localnets")
.action(() => {
runSystemCommand("docker compose start");
});

localnet
.command("stop")
.description("stop L1 and L2 localnets")
.action(() => {
runSystemCommand("docker compose stop");
});

localnet
.command("logs")
.description("Display logs")
.action(() => {
const options: ExecSyncOptions = { stdio: 'inherit' };
runSystemCommand("docker-compose logs --follow", options);
});

localnet
.command("wallets")
.description("Display rich wallet keys and addresses")
.action(() => {
const rawJSON = fs.readFileSync(path.join(repoDirectory(), "rich-wallets.json")).toString();
const wallets = JSON.parse(rawJSON);
console.log(wallets);
});
1 change: 1 addition & 0 deletions src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,6 @@ import "./commands/deposit";
import "./commands/withdraw";
import "./commands/withdraw-finalize";
import "./commands/create-project";
import "./commands/localnet";

program.parse();