Refactor and fixes
This commit is contained in:
parent
8d825c4284
commit
513862648d
|
@ -212,7 +212,7 @@ applyRoutines() {
|
||||||
ROUTINE_TYPE=${SPLIT[1]}
|
ROUTINE_TYPE=${SPLIT[1]}
|
||||||
case "$ROUTINE_TYPE" in
|
case "$ROUTINE_TYPE" in
|
||||||
events)
|
events)
|
||||||
ROUTINE_TYPE=EVENTS
|
ROUTINE_TYPE=EVENT
|
||||||
;;
|
;;
|
||||||
functions)
|
functions)
|
||||||
ROUTINE_TYPE=FUNCTION
|
ROUTINE_TYPE=FUNCTION
|
||||||
|
|
|
@ -1,15 +1,22 @@
|
||||||
#!/bin/node
|
|
||||||
const execFileSync = require('child_process').execFileSync;
|
const path = require('path');
|
||||||
|
const execFile = require('child_process').execFile;
|
||||||
const spawn = require('child_process').spawn;
|
const spawn = require('child_process').spawn;
|
||||||
|
|
||||||
module.exports = function(command, workdir, ...args) {
|
module.exports = async function(command, workdir, ...args) {
|
||||||
const buildArgs = [
|
const buildArgs = [
|
||||||
'build',
|
'build',
|
||||||
'-t', 'myvc/client',
|
'-t', 'myvc/client',
|
||||||
'-f', `${__dirname}/Dockerfile.client`,
|
'-f', path.join(__dirname, 'Dockerfile.client'),
|
||||||
`${__dirname}/`
|
__dirname
|
||||||
];
|
];
|
||||||
execFileSync('docker', buildArgs);
|
await new Promise((resolve, reject) => {
|
||||||
|
execFile('docker', buildArgs, (err, stdout, stderr) => {
|
||||||
|
if (err)
|
||||||
|
return reject(err);
|
||||||
|
resolve({stdout, stderr});
|
||||||
|
});
|
||||||
|
})
|
||||||
|
|
||||||
let runArgs = [
|
let runArgs = [
|
||||||
'run',
|
'run',
|
||||||
|
@ -19,6 +26,7 @@ module.exports = function(command, workdir, ...args) {
|
||||||
];
|
];
|
||||||
runArgs = runArgs.concat(args);
|
runArgs = runArgs.concat(args);
|
||||||
|
|
||||||
|
await new Promise((resolve, reject) => {
|
||||||
const child = spawn('docker', runArgs, {
|
const child = spawn('docker', runArgs, {
|
||||||
stdio: [
|
stdio: [
|
||||||
process.stdin,
|
process.stdin,
|
||||||
|
@ -26,5 +34,6 @@ module.exports = function(command, workdir, ...args) {
|
||||||
process.stderr
|
process.stderr
|
||||||
]
|
]
|
||||||
});
|
});
|
||||||
child.on('exit', code => process.exit(code));
|
child.on('exit', code => resolve(code));
|
||||||
|
})
|
||||||
};
|
};
|
||||||
|
|
89
docker.js
89
docker.js
|
@ -1,9 +1,7 @@
|
||||||
|
|
||||||
const cwd = process.cwd();
|
const execFile = require('child_process').execFile;
|
||||||
const exec = require('child_process').exec;
|
|
||||||
const log = require('fancy-log');
|
const log = require('fancy-log');
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
const serverImage = require(`${cwd}/myvc.config.json`).serverImage;
|
|
||||||
|
|
||||||
module.exports = class Docker {
|
module.exports = class Docker {
|
||||||
constructor(name, context) {
|
constructor(name, context) {
|
||||||
|
@ -32,33 +30,52 @@ module.exports = class Docker {
|
||||||
*/
|
*/
|
||||||
async run(ci) {
|
async run(ci) {
|
||||||
let dockerfilePath = path.join(__dirname, 'Dockerfile');
|
let dockerfilePath = path.join(__dirname, 'Dockerfile');
|
||||||
await this.execP(`docker build -t myvc/server -f ${dockerfilePath}.server ${__dirname}`);
|
|
||||||
|
await this.execFile('docker', [
|
||||||
|
'build',
|
||||||
|
'-t', 'myvc/server',
|
||||||
|
'-f', `${dockerfilePath}.server`,
|
||||||
|
__dirname
|
||||||
|
]);
|
||||||
|
|
||||||
let d = new Date();
|
let d = new Date();
|
||||||
let pad = v => v < 10 ? '0' + v : v;
|
let pad = v => v < 10 ? '0' + v : v;
|
||||||
let stamp = `${d.getFullYear()}-${pad(d.getMonth() + 1)}-${pad(d.getDate())}`;
|
let stamp = `${d.getFullYear()}-${pad(d.getMonth() + 1)}-${pad(d.getDate())}`;
|
||||||
await this.execP(`docker build --build-arg STAMP=${stamp} -f ${dockerfilePath}.dump -t ${this.serverImage} ${this.context}`);
|
|
||||||
|
await this.execFile('docker', [
|
||||||
|
'build',
|
||||||
|
'-t', this.imageTag,
|
||||||
|
'-f', `${dockerfilePath}.dump`,
|
||||||
|
'--build-arg', `STAMP=${stamp}`,
|
||||||
|
this.context
|
||||||
|
]);
|
||||||
|
|
||||||
let dockerArgs;
|
let dockerArgs;
|
||||||
|
|
||||||
if (this.isRandom)
|
if (this.isRandom)
|
||||||
dockerArgs = '-p 3306';
|
dockerArgs = ['-p', '3306'];
|
||||||
else {
|
else {
|
||||||
try {
|
try {
|
||||||
await this.rm();
|
await this.rm();
|
||||||
} catch (e) {}
|
} catch (e) {}
|
||||||
dockerArgs = `--name ${this.name} -p 3306:${this.dbConf.port}`;
|
dockerArgs = ['--name', this.name, '-p', `3306:${this.dbConf.port}`];
|
||||||
}
|
}
|
||||||
|
|
||||||
let runChown = process.platform != 'linux';
|
let runChown = process.platform != 'linux';
|
||||||
|
const container = await this.execFile('docker', [
|
||||||
const container = await this.execP(`docker run --env RUN_CHOWN=${runChown} -d ${dockerArgs} ${this.serverImage}`);
|
'run',
|
||||||
|
'--env', `RUN_CHOWN=${runChown}`,
|
||||||
|
'-d',
|
||||||
|
...dockerArgs,
|
||||||
|
this.imageTag
|
||||||
|
]);
|
||||||
this.id = container.stdout.trim();
|
this.id = container.stdout.trim();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (this.isRandom) {
|
if (this.isRandom) {
|
||||||
let inspect = await this.execP(`docker inspect -f "{{json .NetworkSettings}}" ${this.id}`);
|
let netSettings = await this.execJson('docker', [
|
||||||
let netSettings = JSON.parse(inspect.stdout);
|
'inspect', '-f', '{{json .NetworkSettings}}', this.id
|
||||||
|
]);
|
||||||
|
|
||||||
if (ci)
|
if (ci)
|
||||||
this.dbConf.host = netSettings.Gateway;
|
this.dbConf.host = netSettings.Gateway;
|
||||||
|
@ -83,8 +100,9 @@ module.exports = class Docker {
|
||||||
async start() {
|
async start() {
|
||||||
let state;
|
let state;
|
||||||
try {
|
try {
|
||||||
let result = await this.execP(`docker inspect -f "{{json .State}}" ${this.id}`);
|
state = await this.execJson('docker', [
|
||||||
state = JSON.parse(result.stdout);
|
'inspect', '-f', '{{json .State}}', this.id
|
||||||
|
]);
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
return await this.run();
|
return await this.run();
|
||||||
}
|
}
|
||||||
|
@ -93,7 +111,7 @@ module.exports = class Docker {
|
||||||
case 'running':
|
case 'running':
|
||||||
return;
|
return;
|
||||||
case 'exited':
|
case 'exited':
|
||||||
await this.execP(`docker start ${this.id}`);
|
await this.execFile('docker', ['start', this.id]);
|
||||||
await this.wait();
|
await this.wait();
|
||||||
return;
|
return;
|
||||||
default:
|
default:
|
||||||
|
@ -107,15 +125,17 @@ module.exports = class Docker {
|
||||||
let elapsedTime = 0;
|
let elapsedTime = 0;
|
||||||
let maxInterval = 4 * 60 * 1000;
|
let maxInterval = 4 * 60 * 1000;
|
||||||
|
|
||||||
log('Waiting for MySQL init process...');
|
log('Waiting for container to be ready...');
|
||||||
|
|
||||||
async function checker() {
|
async function checker() {
|
||||||
elapsedTime += interval;
|
elapsedTime += interval;
|
||||||
let status;
|
let status;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
let result = await this.execP(`docker inspect -f "{{.State.Health.Status}}" ${this.id}`);
|
let status = await this.execJson('docker', [
|
||||||
status = result.stdout.trimEnd();
|
'inspect', '-f', '{{.State.Health.Status}}', this.id
|
||||||
|
]);
|
||||||
|
status = status.trimEnd();
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
return reject(new Error(err.message));
|
return reject(new Error(err.message));
|
||||||
}
|
}
|
||||||
|
@ -124,12 +144,12 @@ module.exports = class Docker {
|
||||||
return reject(new Error('Docker exited, please see the docker logs for more info'));
|
return reject(new Error('Docker exited, please see the docker logs for more info'));
|
||||||
|
|
||||||
if (status == 'healthy') {
|
if (status == 'healthy') {
|
||||||
log('MySQL process ready.');
|
log('Container ready.');
|
||||||
return resolve();
|
return resolve();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (elapsedTime >= maxInterval)
|
if (elapsedTime >= maxInterval)
|
||||||
reject(new Error(`MySQL not initialized whithin ${elapsedTime / 1000} secs`));
|
reject(new Error(`Container initialized whithin ${elapsedTime / 1000} secs`));
|
||||||
else
|
else
|
||||||
setTimeout(bindedChecker, interval);
|
setTimeout(bindedChecker, interval);
|
||||||
}
|
}
|
||||||
|
@ -160,8 +180,9 @@ module.exports = class Docker {
|
||||||
let state;
|
let state;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
let result = await this.execP(`docker inspect -f "{{json .State}}" ${this.id}`);
|
state = await this.execJson('docker', [
|
||||||
state = JSON.parse(result.stdout);
|
'inspect', '-f', '{{json .State}}', this.id
|
||||||
|
]);
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
return reject(new Error(err.message));
|
return reject(new Error(err.message));
|
||||||
}
|
}
|
||||||
|
@ -189,19 +210,23 @@ module.exports = class Docker {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
rm() {
|
async rm() {
|
||||||
return this.execP(`docker stop ${this.id} && docker rm -v ${this.id}`);
|
try {
|
||||||
|
await this.execFile('docker', ['stop', this.id]);
|
||||||
|
await this.execFile('docker', ['rm', '-v', this.id]);
|
||||||
|
} catch (e) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Promisified version of exec().
|
* Promisified version of execFile().
|
||||||
*
|
*
|
||||||
* @param {String} command The exec command
|
* @param {String} command The exec command
|
||||||
|
* @param {Array} args The command arguments
|
||||||
* @return {Promise} The promise
|
* @return {Promise} The promise
|
||||||
*/
|
*/
|
||||||
execP(command) {
|
execFile(command, args) {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
exec(command, (err, stdout, stderr) => {
|
execFile(command, args, (err, stdout, stderr) => {
|
||||||
if (err)
|
if (err)
|
||||||
reject(err);
|
reject(err);
|
||||||
else {
|
else {
|
||||||
|
@ -213,4 +238,16 @@ module.exports = class Docker {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Executes a command whose return is json.
|
||||||
|
*
|
||||||
|
* @param {String} command The exec command
|
||||||
|
* @param {Array} args The command arguments
|
||||||
|
* @return {Object} The parsed JSON
|
||||||
|
*/
|
||||||
|
async execJson(command, args) {
|
||||||
|
const result = await this.execFile(command, args);
|
||||||
|
return JSON.parse(result.stdout);
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
#!/usr/bin/node
|
|
||||||
const fs = require('fs-extra');
|
const fs = require('fs-extra');
|
||||||
const mysql = require('mysql2/promise');
|
const mysql = require('mysql2/promise');
|
||||||
const ejs = require('ejs');
|
const ejs = require('ejs');
|
||||||
|
@ -48,9 +48,7 @@ const exporters = [
|
||||||
|
|
||||||
// Exports objects for all schemas
|
// Exports objects for all schemas
|
||||||
|
|
||||||
module.exports = async function main(opts, config, dbConf) {
|
module.exports = async function main(workdir, schemas, dbConf) {
|
||||||
const exportDir = `${opts.workdir}/routines`;
|
|
||||||
|
|
||||||
const conn = await mysql.createConnection(dbConf);
|
const conn = await mysql.createConnection(dbConf);
|
||||||
conn.queryFromFile = function(file, params) {
|
conn.queryFromFile = function(file, params) {
|
||||||
return this.execute(
|
return this.execute(
|
||||||
|
@ -60,12 +58,12 @@ module.exports = async function main(opts, config, dbConf) {
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
const exportDir = `${workdir}/routines`;
|
||||||
if (fs.existsSync(exportDir))
|
if (fs.existsSync(exportDir))
|
||||||
fs.removeSync(exportDir, {recursive: true});
|
fs.removeSync(exportDir, {recursive: true});
|
||||||
|
|
||||||
fs.mkdirSync(exportDir);
|
fs.mkdirSync(exportDir);
|
||||||
|
|
||||||
for (let schema of config.structure) {
|
for (let schema of schemas) {
|
||||||
let schemaDir = `${exportDir}/${schema}`;
|
let schemaDir = `${exportDir}/${schema}`;
|
||||||
|
|
||||||
if (!fs.existsSync(schemaDir))
|
if (!fs.existsSync(schemaDir))
|
||||||
|
|
|
@ -5,7 +5,8 @@ CONFIG_FILE=$1
|
||||||
INI_FILE=$2
|
INI_FILE=$2
|
||||||
DUMP_FILE="dump/structure.sql"
|
DUMP_FILE="dump/structure.sql"
|
||||||
|
|
||||||
SCHEMAS=( $(jq -r ".structure[]" "$CONFIG_FILE") )
|
echo "SELECT 1;" | mysql --defaults-file="$INI_FILE" >> /dev/null
|
||||||
|
SCHEMAS=( $(jq -r ".schemas[]" "$CONFIG_FILE") )
|
||||||
|
|
||||||
mysqldump \
|
mysqldump \
|
||||||
--defaults-file="$INI_FILE" \
|
--defaults-file="$INI_FILE" \
|
||||||
|
|
144
index.js
144
index.js
|
@ -2,15 +2,15 @@
|
||||||
require('colors');
|
require('colors');
|
||||||
const getopts = require('getopts');
|
const getopts = require('getopts');
|
||||||
const package = require('./package.json');
|
const package = require('./package.json');
|
||||||
const dockerRun = require('./docker-run');
|
|
||||||
const fs = require('fs-extra');
|
const fs = require('fs-extra');
|
||||||
const path = require('path');
|
|
||||||
const ini = require('ini');
|
const ini = require('ini');
|
||||||
|
const path = require('path');
|
||||||
|
const dockerRun = require('./docker-run');
|
||||||
|
|
||||||
console.log('MyVC (MySQL Version Control)'.green, `v${package.version}`.magenta);
|
console.log('MyVC (MySQL Version Control)'.green, `v${package.version}`.magenta);
|
||||||
|
|
||||||
const argv = process.argv.slice(2);
|
const argv = process.argv.slice(2);
|
||||||
const opts = getopts(argv, {
|
const cliOpts = getopts(argv, {
|
||||||
alias: {
|
alias: {
|
||||||
env: 'e',
|
env: 'e',
|
||||||
workdir: 'w',
|
workdir: 'w',
|
||||||
|
@ -23,23 +23,14 @@ const opts = getopts(argv, {
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
if (opts.version)
|
if (cliOpts.version)
|
||||||
process.exit(0);
|
process.exit(0);
|
||||||
|
|
||||||
function usage() {
|
const action = cliOpts._[0];
|
||||||
console.log('Usage:'.gray, 'myvc [-w|--workdir] [-e|--env] [-h|--help] action'.magenta);
|
if (!action) {
|
||||||
|
console.log('Usage:'.gray, '[npx] myvc [-w|--workdir] [-e|--env] [-h|--help] action'.blue);
|
||||||
process.exit(0);
|
process.exit(0);
|
||||||
}
|
}
|
||||||
function error(message) {
|
|
||||||
console.error('Error:'.gray, message.red);
|
|
||||||
process.exit(1);
|
|
||||||
}
|
|
||||||
function parameter(parameter, value) {
|
|
||||||
console.log(parameter.gray, value.blue);
|
|
||||||
}
|
|
||||||
|
|
||||||
const action = opts._[0];
|
|
||||||
if (!action) usage();
|
|
||||||
|
|
||||||
const actionArgs = {
|
const actionArgs = {
|
||||||
apply: {
|
apply: {
|
||||||
|
@ -55,20 +46,35 @@ const actionArgs = {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
const actionOpts = getopts(argv, actionArgs[action]);
|
const actionOpts = getopts(argv, actionArgs[action]);
|
||||||
Object.assign(opts, actionOpts);
|
Object.assign(cliOpts, actionOpts);
|
||||||
|
|
||||||
|
const opts = {};
|
||||||
|
for (let opt in cliOpts) {
|
||||||
|
if (opt.length > 1 || opt == '_')
|
||||||
|
opts[opt] = cliOpts[opt];
|
||||||
|
}
|
||||||
|
|
||||||
|
function parameter(parameter, value) {
|
||||||
|
console.log(parameter.gray, value.blue);
|
||||||
|
}
|
||||||
|
|
||||||
parameter('Environment:', opts.env);
|
parameter('Environment:', opts.env);
|
||||||
parameter('Workdir:', opts.workdir);
|
parameter('Workdir:', opts.workdir);
|
||||||
parameter('Action:', action);
|
parameter('Action:', action);
|
||||||
|
|
||||||
|
class MyVC {
|
||||||
|
async init(opts) {
|
||||||
// Configuration file
|
// Configuration file
|
||||||
|
|
||||||
const configFile = 'myvc.config.json';
|
const configFile = 'myvc.config.json';
|
||||||
const configPath = path.join(opts.workdir, configFile);
|
const configPath = path.join(opts.workdir, configFile);
|
||||||
if (!fs.existsSync(configPath))
|
if (!await fs.pathExists(configPath))
|
||||||
error(`Config file not found: ${configFile}`);
|
throw new Error(`Config file not found: ${configFile}`);
|
||||||
const config = require(configPath);
|
const config = require(configPath);
|
||||||
|
|
||||||
|
Object.assign(opts, config);
|
||||||
|
opts.configFile = configFile;
|
||||||
|
|
||||||
// Database configuration
|
// Database configuration
|
||||||
|
|
||||||
let iniFile = 'db.ini';
|
let iniFile = 'db.ini';
|
||||||
|
@ -79,10 +85,10 @@ if (opts.env) {
|
||||||
}
|
}
|
||||||
const iniPath = path.join(iniDir, iniFile);
|
const iniPath = path.join(iniDir, iniFile);
|
||||||
|
|
||||||
if (!fs.existsSync(iniPath))
|
if (!await fs.pathExists(iniPath))
|
||||||
error(`Database config file not found: ${iniFile}`);
|
throw new Error(`Database config file not found: ${iniFile}`);
|
||||||
|
|
||||||
const iniConfig = ini.parse(fs.readFileSync(iniPath, 'utf8')).client;
|
const iniConfig = ini.parse(await fs.readFile(iniPath, 'utf8')).client;
|
||||||
const dbConfig = {
|
const dbConfig = {
|
||||||
host: !opts.env ? 'localhost' : iniConfig.host,
|
host: !opts.env ? 'localhost' : iniConfig.host,
|
||||||
port: iniConfig.port,
|
port: iniConfig.port,
|
||||||
|
@ -97,38 +103,82 @@ const dbConfig = {
|
||||||
|
|
||||||
if (iniConfig.ssl_ca) {
|
if (iniConfig.ssl_ca) {
|
||||||
dbConfig.ssl = {
|
dbConfig.ssl = {
|
||||||
ca: fs.readFileSync(`${opts.workdir}/${iniConfig.ssl_ca}`),
|
ca: await fs.readFile(`${opts.workdir}/${iniConfig.ssl_ca}`),
|
||||||
rejectUnauthorized: iniConfig.ssl_verify_server_cert != undefined
|
rejectUnauthorized: iniConfig.ssl_verify_server_cert != undefined
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Actions
|
Object.assign(opts, {
|
||||||
|
iniFile,
|
||||||
|
dbConfig
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
switch (action) {
|
async structure (opts) {
|
||||||
case 'structure':
|
await dockerRun('export-structure.sh',
|
||||||
dockerRun('export-structure.sh', opts.workdir, configFile, iniFile);
|
opts.workdir,
|
||||||
break;
|
opts.configFile,
|
||||||
case 'fixtures':
|
opts.iniFile
|
||||||
dockerRun('export-fixtures.sh', opts.workdir, configFile, iniFile);
|
);
|
||||||
break;
|
}
|
||||||
case 'routines':
|
|
||||||
require('./export-routines')(opts, config, dbConfig);
|
async fixtures(opts) {
|
||||||
break;
|
await dockerRun('export-fixtures.sh',
|
||||||
case 'apply':
|
opts.workdir,
|
||||||
dockerRun('apply-changes.sh', opts.workdir, ...argv);
|
opts.configFile,
|
||||||
break;
|
opts.iniFile
|
||||||
case 'run': {
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async routines(opts) {
|
||||||
|
const exportRoutines = require('./export-routines');
|
||||||
|
await exportRoutines(
|
||||||
|
opts.workdir,
|
||||||
|
opts.schemas,
|
||||||
|
opts.dbConfig
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async apply(opts) {
|
||||||
|
let args = [];
|
||||||
|
if (opts.force) args.push('-f');
|
||||||
|
if (opts.user) args.push('-u');
|
||||||
|
if (opts.env) args = args.concat(['-e', opts.env]);
|
||||||
|
|
||||||
|
await dockerRun('apply-changes.sh',
|
||||||
|
opts.workdir,
|
||||||
|
...args
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
async run(opts) {
|
||||||
const Docker = require('./docker');
|
const Docker = require('./docker');
|
||||||
const container = new Docker(config.code, opts.workdir);
|
const container = new Docker(opts.code, opts.workdir);
|
||||||
container.run();
|
await container.run();
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
case 'start': {
|
|
||||||
|
async start(opts) {
|
||||||
const Docker = require('./docker');
|
const Docker = require('./docker');
|
||||||
const container = new Docker(config.code, opts.workdir);
|
const container = new Docker(opts.code, opts.workdir);
|
||||||
container.start();
|
await container.start();
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
default:
|
|
||||||
usage();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
(async function() {
|
||||||
|
try {
|
||||||
|
const myvc = new MyVC();
|
||||||
|
|
||||||
|
if (myvc[action]) {
|
||||||
|
await myvc.init(opts);
|
||||||
|
await myvc[action](opts);
|
||||||
|
} else
|
||||||
|
throw new Error (`Unknown action '${action}'`);
|
||||||
|
} catch (err) {
|
||||||
|
if (err.name == 'Error')
|
||||||
|
console.error('Error:'.gray, err.message.red);
|
||||||
|
else
|
||||||
|
throw err;
|
||||||
|
}
|
||||||
|
})();
|
||||||
|
|
||||||
|
module.exports = MyVC;
|
||||||
|
|
|
@ -1,17 +1,17 @@
|
||||||
{
|
{
|
||||||
"code": "my-app",
|
"code": "my-app",
|
||||||
"structure": [
|
"schemas": [
|
||||||
"schema1",
|
"util",
|
||||||
"schema2"
|
"my_app"
|
||||||
],
|
],
|
||||||
"fixtures": {
|
"fixtures": {
|
||||||
"schema1": [
|
"util": [
|
||||||
"table1.1",
|
"version",
|
||||||
"table2.1"
|
"versionUser"
|
||||||
],
|
],
|
||||||
"schema2": [
|
"my_app": [
|
||||||
"table2.1",
|
"table1",
|
||||||
"table2.2"
|
"table2"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"name": "myvc",
|
"name": "myvc",
|
||||||
"version": "1.0.6",
|
"version": "1.0.7",
|
||||||
"author": "Verdnatura Levante SL",
|
"author": "Verdnatura Levante SL",
|
||||||
"description": "MySQL Version Control",
|
"description": "MySQL Version Control",
|
||||||
"license": "GPL-3.0",
|
"license": "GPL-3.0",
|
||||||
|
@ -28,7 +28,11 @@
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"mysql",
|
"mysql",
|
||||||
"mariadb",
|
"mariadb",
|
||||||
|
"git",
|
||||||
|
"vcs",
|
||||||
|
"database",
|
||||||
"version",
|
"version",
|
||||||
"control"
|
"control",
|
||||||
|
"sql"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue