everything-dev
Version:
A consolidated product package for building Module Federation apps with oRPC APIs.
176 lines (174 loc) • 5.97 kB
JavaScript
const require_runtime = require('./_virtual/_rolldown/runtime.cjs');
let node_crypto = require("node:crypto");
let effect = require("effect");
let execa = require("execa");
//#region src/near-cli.ts
const INSTALLER_URL = `https://github.com/near/near-cli-rs/releases/download/v0.23.5/near-cli-rs-installer.sh`;
const BASE58_ALPHABET = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz";
var NearCliNotFoundError = class extends Error {
_tag = "NearCliNotFoundError";
constructor() {
super("NEAR CLI not found");
}
};
var NearCliInstallError = class extends Error {
_tag = "NearCliInstallError";
constructor(message) {
super(`Failed to install NEAR CLI: ${message}`);
}
};
var NearTransactionError = class extends Error {
_tag = "NearTransactionError";
};
function base64UrlToBytes(input) {
const normalized = input.replace(/-/g, "+").replace(/_/g, "/");
return new Uint8Array(Buffer.from(normalized, "base64"));
}
function base58Encode(input) {
if (input.length === 0) return "";
const digits = [0];
for (const byte of input) {
let carry = byte;
for (let i = 0; i < digits.length; i++) {
carry += digits[i] << 8;
digits[i] = carry % 58;
carry = Math.floor(carry / 58);
}
while (carry > 0) {
digits.push(carry % 58);
carry = Math.floor(carry / 58);
}
}
let output = "";
for (const byte of input) if (byte === 0) output += BASE58_ALPHABET[0];
else break;
for (let i = digits.length - 1; i >= 0; i--) output += BASE58_ALPHABET[digits[i]];
return output;
}
function generateNearKeyPair() {
const { publicKey, privateKey } = (0, node_crypto.generateKeyPairSync)("ed25519");
const publicJwk = publicKey.export({ format: "jwk" });
const privateJwk = privateKey.export({ format: "jwk" });
if (!publicJwk.x || !privateJwk.d) throw new Error("Failed to generate NEAR keypair");
const publicBytes = base64UrlToBytes(publicJwk.x);
const privateSeed = base64UrlToBytes(privateJwk.d);
const secretBytes = new Uint8Array(privateSeed.length + publicBytes.length);
secretBytes.set(privateSeed, 0);
secretBytes.set(publicBytes, privateSeed.length);
return {
publicKey: `ed25519:${base58Encode(publicBytes)}`,
privateKey: `ed25519:${base58Encode(secretBytes)}`
};
}
const checkNearCliInstalled = effect.Effect.tryPromise({
try: async () => {
try {
await (0, execa.execa)("near", ["--version"], { stdio: "pipe" });
return true;
} catch {
return false;
}
},
catch: () => /* @__PURE__ */ new Error("Failed to check NEAR CLI")
});
const installNearCli = effect.Effect.tryPromise({
try: async () => {
await (0, execa.execa)("sh", ["-c", `curl --proto '=https' --tlsv1.2 -LsSf ${INSTALLER_URL} | sh`], { stdio: "inherit" });
},
catch: (error) => {
if (error instanceof Error && "exitCode" in error) return new NearCliInstallError(`Installer exited with code ${error.exitCode}`);
return new NearCliInstallError(error instanceof Error ? error.message : String(error));
}
});
async function runNearCommand(args) {
await (0, execa.execa)("near", args, { stdio: "inherit" });
}
const ensureNearCli = effect.Effect.gen(function* () {
if (yield* checkNearCliInstalled) return;
if (process.env.BOS_INSTALL_NEAR_CLI === "true") {
yield* installNearCli;
return;
}
console.log();
console.log(" NEAR CLI not found");
console.log();
console.log(` To install manually: curl --proto '=https' --tlsv1.2 -LsSf ${INSTALLER_URL} | sh`);
console.log();
yield* effect.Effect.fail(new NearCliNotFoundError());
});
const executeTransaction = (config) => effect.Effect.gen(function* () {
const gas = (config.gas || "300Tgas").replace(/\s+/g, "");
const deposit = (config.deposit || "0NEAR").replace(/\s+/g, "");
const network = config.network || (config.account.endsWith(".testnet") ? "testnet" : "mainnet");
const args = [
"contract",
"call-function",
"as-transaction",
config.contract,
config.method,
"base64-args",
config.argsBase64,
"prepaid-gas",
gas,
"attached-deposit",
deposit,
"sign-as",
config.account,
"network-config",
network
];
if (config.privateKey) args.push("sign-with-plaintext-private-key", config.privateKey, "send");
else args.push("sign-with-keychain", "send");
return {
success: true,
txHash: (yield* effect.Effect.tryPromise({
try: async () => {
const result = await (0, execa.execa)("near", args, {
stdin: "inherit",
stdout: "pipe",
stderr: "pipe",
reject: false
});
process.stdout.write(result.stdout);
const combined = `${result.stdout}\n${result.stderr}`;
const txHashMatch = combined.match(/Transaction ID:\s*([A-Za-z0-9]+)/i);
const hasCodeDoesNotExist = /CodeDoesNotExist/i.test(combined);
const hasTransactionFailed = /Transaction failed/i.test(combined);
const softSuccess = Boolean(txHashMatch?.[1]) && hasCodeDoesNotExist && hasTransactionFailed;
if (result.exitCode === 0 || softSuccess) {
if (softSuccess) console.log(` ${txHashMatch?.[1]} — FastDATA CodeDoesNotExist (expected)`);
return combined;
}
throw new NearTransactionError(result.stderr || `Transaction failed with code ${result.exitCode}`);
},
catch: (error) => error
})).match(/Transaction ID:\s*([A-Za-z0-9]+)/i)?.[1]
};
});
async function addFunctionCallAccessKey(config) {
const keyPair = generateNearKeyPair();
await runNearCommand([
"account",
"add-key",
config.account,
"grant-function-call-access",
"--allowance",
config.allowance,
"--contract-account-id",
config.contract,
"--function-names",
config.functionNames.join(", "),
"use-manually-provided-public-key",
keyPair.publicKey,
"network-config",
config.network || (config.account.endsWith(".testnet") ? "testnet" : "mainnet"),
"sign-with-keychain",
"send"
]);
return keyPair;
}
//#endregion
exports.addFunctionCallAccessKey = addFunctionCallAccessKey;
exports.ensureNearCli = ensureNearCli;
exports.executeTransaction = executeTransaction;
//# sourceMappingURL=near-cli.cjs.map