@kubiklabs/wasmkit
Version:
Wasmkit is a development environment to compile, deploy, test, run cosmwasm contracts on different networks.
163 lines (162 loc) • 7.98 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.createArtifacts = exports.generateSchema = exports.compileContract = exports.readContractName = exports.compile = void 0;
const chalk_1 = __importDefault(require("chalk"));
const child_process_1 = require("child_process");
const fs_1 = require("fs");
const fs_extra_1 = __importDefault(require("fs-extra"));
const path_1 = __importDefault(require("path"));
const toml_1 = require("toml");
const errors_1 = require("../../internal/core/errors");
const errors_list_1 = require("../../internal/core/errors-list");
const project_structure_1 = require("../../internal/core/project-structure");
const strings_1 = require("../../internal/util/strings");
const tsSchema_1 = require("./tsSchema");
const utils_1 = require("./utils");
function parseProjectToml(contractsDirPrefix) {
// read Cargo.toml in project's root dir
const projectTomlFile = (0, fs_1.readFileSync)('Cargo.toml');
const tomlContent = (0, toml_1.parse)(projectTomlFile.toString());
const workspacesPath = [];
tomlContent.workspace.members.forEach((workspace) => {
if (path_1.default.parse(workspace).name === '*') {
const dirsInWorkspace = (0, fs_1.readdirSync)(path_1.default.parse(workspace).dir);
dirsInWorkspace.forEach((dir) => {
const dirPath = path_1.default.join(path_1.default.parse(workspace).dir, path_1.default.basename(dir));
workspacesPath.push(dirPath);
});
}
else {
workspacesPath.push(workspace);
}
});
return workspacesPath.filter((workspace) => {
return workspace.startsWith(contractsDirPrefix);
});
}
async function compile(docker, sourceDir, force, skipSchema, skipSchemaErrors, env) {
await (0, project_structure_1.assertDir)(project_structure_1.CACHE_DIR);
let contractDirs = [];
const toml = "Cargo.toml";
// Contract(s) path given
if (sourceDir.length > 0) {
contractDirs = sourceDir;
}
else {
const paths = parseProjectToml(project_structure_1.CONTRACTS_DIR);
// Only one contract in the contracts dir and compile in contracts dir only
if (paths.includes(toml)) {
contractDirs.push(project_structure_1.CONTRACTS_DIR);
}
else {
// Multiple contracts and each should be compiled by going inside each of them
const contractNames = new Set();
for (const contractPath of paths) {
const contractName = readContractName(path_1.default.join(contractPath, toml));
// Check for similar contract names before compiling contracts.
// For contract with same names raise an error.
if (contractNames.has(contractName)) {
throw new errors_1.WasmkitError(errors_list_1.ERRORS.GENERAL.SAME_CONTRACT_NAMES, {
contractName
});
}
else {
contractNames.add(contractName);
contractDirs.push(contractPath);
}
}
}
}
for (const dir of contractDirs) {
compileContract(dir, docker, env);
const contractName = readContractName(path_1.default.join(dir, toml));
if (!skipSchema) { // only generate schema if this flag is not passed
await generateSchema(contractName, dir, docker, skipSchemaErrors, env);
}
createArtifacts(project_structure_1.TARGET_DIR, path_1.default.join(project_structure_1.SCHEMA_DIR, contractName), path_1.default.join(project_structure_1.ARTIFACTS_DIR, project_structure_1.CONTRACTS_DIR), path_1.default.join(dir, "schema"), docker, skipSchema);
}
}
exports.compile = compile;
function readContractName(tomlFilePath) {
const tomlFileContent = (0, toml_1.parse)((0, fs_1.readFileSync)(tomlFilePath).toString());
return (0, strings_1.replaceAll)(tomlFileContent.package.name, '-', '_');
}
exports.readContractName = readContractName;
function compileContract(contractDir, docker, env) {
const cargoCommands = env.config.commands;
const currDir = process.cwd();
process.chdir(contractDir);
console.log(`🛠 Compiling your contract in directory: ${chalk_1.default.gray(contractDir)}`);
console.log("=============================================");
// Compiles the contract and creates .wasm file alongside others
try {
(0, child_process_1.execSync)(cargoCommands.compile, { stdio: 'inherit' });
}
catch (error) {
if (error instanceof Error) {
throw new errors_1.WasmkitError(errors_list_1.ERRORS.GENERAL.RUST_COMPILE_ERROR);
}
else {
throw error;
}
}
process.chdir(currDir);
}
exports.compileContract = compileContract;
async function generateSchema(contractName, contractDir, docker, skipSchemaErrors, env) {
const cargoCommands = env.config.commands;
const currDir = process.cwd();
process.chdir(contractDir);
console.log(`Creating schema for contract in directory: ${chalk_1.default.gray(contractDir)}`);
// Creates schema .json files
(0, child_process_1.execSync)(cargoCommands.schema, { stdio: 'inherit' });
process.chdir(currDir);
// Creates typescript objects for execute and query msgs from json schema files
const contractTsSchemaDir = project_structure_1.TS_SCHEMA_DIR;
// create nested dirs if not present
if (!fs_extra_1.default.existsSync(contractTsSchemaDir)) {
fs_extra_1.default.mkdirSync(contractTsSchemaDir, { recursive: true });
}
console.log(`Creating TS schema objects for contract in directory: ${chalk_1.default.gray(contractTsSchemaDir)}`);
const srcSchemas = (0, utils_1.readSchemas)(path_1.default.join(contractDir, "schema"), path_1.default.join(contractDir, "schema", "raw"));
await (0, tsSchema_1.generateTsSchema)(contractName, srcSchemas, contractTsSchemaDir, skipSchemaErrors);
}
exports.generateSchema = generateSchema;
function createArtifacts(targetDir, schemaDir, artifactsDir, sourceSchemaDir, docker, skipSchema) {
const paths = fs_extra_1.default.readdirSync(targetDir);
// create nested dirs if not present
if (!fs_extra_1.default.existsSync(artifactsDir)) {
fs_extra_1.default.mkdirSync(artifactsDir, { recursive: true });
}
if (!fs_extra_1.default.existsSync(schemaDir)) {
fs_extra_1.default.mkdirSync(schemaDir, { recursive: true });
}
for (const p of paths) {
const filename = path_1.default.basename(p);
if (filename.split('.')[filename.split('.').length - 1] !== "wasm") {
continue;
}
console.log(`Copying file ${filename} from ${chalk_1.default.gray(targetDir)} to ${chalk_1.default.gray(artifactsDir)}`);
const sourcePath = path_1.default.resolve(targetDir, filename);
const destPath = path_1.default.resolve(artifactsDir, filename);
fs_extra_1.default.copyFileSync(sourcePath, destPath);
}
if (skipSchema) { // do not copy schema to artifacts as there is none
return;
}
const schemaPaths = fs_extra_1.default.readdirSync(sourceSchemaDir);
for (const p of schemaPaths) {
const filename = path_1.default.basename(p);
if (filename.split('.')[filename.split('.').length - 1] !== "json") {
continue;
}
console.log(`Copying file ${filename} from ${chalk_1.default.gray(sourceSchemaDir)} to ${chalk_1.default.gray(schemaDir)}`);
const sourcePath = path_1.default.resolve(sourceSchemaDir, filename);
const destPath = path_1.default.resolve(schemaDir, filename);
fs_extra_1.default.copyFileSync(sourcePath, destPath);
}
}
exports.createArtifacts = createArtifacts;