stratumn-cli
Version:
CLI tools for Stratumn
210 lines (185 loc) • 5.81 kB
JavaScript
import util from 'util';
import { exec } from 'child_process';
import commander from 'commander';
import chalk from 'chalk';
import readPackageSync from '../utils/readPackageSync';
import get from '../utils/get';
import config from '../config';
function collect(val, memo) {
memo.push(val);
return memo;
}
commander
.version(readPackageSync('version'))
/*eslint-disable*/
.usage('<app-name> [show-app|create-map|show-map|show-link|create-link|show-branches] [mapId|hash] [func] [...args]')
/*eslint-enable*/
.option('-x, --exec', 'execute route')
.option('-p, --pretty', 'pretty output when executing')
.option('-d, --debug', 'add debug flag to urls')
.option('-t, --tags <string>', 'filter by tags (can be used multiple times)', collect, [])
.parse(process.argv);
if (commander.args.length < 1) {
commander.help();
}
if (commander.exec && commander.args.length > 1) {
chalk.enabled = false;
}
function handleError(err) {
process.stderr.write(err.message + '\n', () => process.exit(1));
}
const baseUrl = util.format(config.applicationUrl, commander.args[0]);
function makeRoute(method, path, args, desc) {
const parsedArgs = args ? args.map(val => {
if (['null', 'true', 'false'].indexOf(val) > -1 || val.match(/^[0-9]+$/)) {
/*eslint-disable*/
return eval(val);
/*eslint-enable*/
}
return val;
}) : [];
let str = '';
str += chalk.cyan(`curl -X ${method}`);
str += chalk.cyan(` "${baseUrl}${path}`);
if (commander.debug) {
str += chalk.cyan('?debug');
}
str += chalk.cyan('"');
if (parsedArgs.length) {
str += chalk.cyan(' -d ');
str += chalk.green.bold(`"${JSON.stringify(parsedArgs).replace(/"/g, '\\"')}"`);
}
if (desc) {
str += `\n\t${desc}\n`;
}
return str;
}
if (commander.args.length > 1) {
let route;
let path;
switch (commander.args[1]) {
case 'show-app':
if (commander.args.length !== 2) {
commander.help();
}
route = makeRoute('GET', '/');
break;
case 'show-map':
if (commander.args.length !== 3) {
commander.help();
}
path = `/maps/${commander.args[2]}`;
if (commander.tags) {
path += `?tags=${commander.tags.join('&tags=')}`;
}
route = makeRoute('GET', path);
break;
case 'create-map':
route = makeRoute('POST', '/maps', commander.args.slice(2));
break;
case 'show-link':
if (commander.args.length !== 3) {
commander.help();
}
route = makeRoute('GET', `/links/${commander.args[2]}`);
break;
case 'create-link':
if (commander.args.length < 4) {
commander.help();
}
route = makeRoute(
'POST',
`/links/${commander.args[2]}/${commander.args[3]}`,
commander.args.slice(4)
);
break;
case 'show-branches':
if (commander.args.length !== 3) {
commander.help();
}
path = `/branches/${commander.args[2]}`;
if (commander.tags) {
path += `?tags=${commander.tags.join('&tags=')}`;
}
route = makeRoute('GET', path);
break;
default:
handleError(new Error(`Unknown route: ${commander.args[1]}`));
}
if (commander.exec) {
exec(route, {
env: process.env,
cwd: process.cwd()
}, (err, stdout) => {
if (err) {
handleError(err);
return;
}
const output = commander.pretty ?
JSON.stringify(JSON.parse(stdout), null, ' ') :
stdout;
process.stdout.write(`${output}\n`, () => process.exit(0));
});
} else {
process.stdout.write(`${route}\n`, process.exit);
}
} else {
get('/', false, commander.args[0])
.then(({ agentInfo }) => {
const { functions } = agentInfo;
const routes = [];
functions.init = functions.init || { args: [] };
routes.push(makeRoute('GET', '/', null, 'Shows application information.'));
routes.push(makeRoute(
'POST',
'/maps',
functions.init.args,
`Executes function Agent#init(${functions.init.args.join(', ')}) to create a new map.`
));
routes.push(makeRoute(
'GET',
`/maps/${chalk.green.bold(':mapId')}?tags=${chalk.green.bold(':tag')}`,
null,
`Shows the links (meta only) of the map for the given ID, optionally filter by tags.`
));
routes.push(makeRoute(
'GET',
`/links/${chalk.green.bold(':hash')}`,
null,
'Shows the link and evidence for the given hash.'
));
routes.push(makeRoute(
'GET',
`/branches/${chalk.green.bold(':hash')}?tags=${chalk.green.bold(':tag')}`,
null,
/*eslint-disable*/
`Shows the links (meta only) whose previous hash is the given hash, optionally filter by tags.`
/*eslint-enable*/
));
Object.keys(functions)
.filter(name => ['init', 'catchAll'].indexOf(name) === -1)
.forEach(name => {
const func = functions[name];
routes.push(makeRoute(
'POST',
`/links/${chalk.green.bold(':hash')}/${name}`,
func.args,
/*eslint-disable*/
`Executes function Agent#${name}(${func.args.join(', ')}) on the link for the given hash.`
/*eslint-enable*/
));
});
if (functions.catchAll) {
routes.push(makeRoute(
'POST',
`/links/${chalk.green.bold(':hash')}/${chalk.green.bold('*')}`,
[],
/*eslint-disable*/
`Executes function Agent#catchAll(${functions.catchAll.args.join(', ')}) on the given hash for all unhandled functions.`
/*eslint-enable*/
));
}
process.stdout.write(routes.join('\n'), process.exit);
})
.catch(handleError);
}