Skip to content

Commit

Permalink
feat: load external .env file from execution directory
Browse files Browse the repository at this point in the history
  • Loading branch information
faridevnz committed Oct 28, 2024
1 parent 4efc8bf commit a418835
Show file tree
Hide file tree
Showing 21 changed files with 555 additions and 431 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,5 @@ node_modules

# cosmodrome
.cosmodrome.json

test
12 changes: 12 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
},
"dependencies": {
"commander": "^12.1.0",
"dotenv": "^16.4.5",
"inquirer": "^12.0.0",
"mysql2": "^3.11.3",
"pg": "^8.13.1",
Expand Down
216 changes: 133 additions & 83 deletions src/cli.ts
Original file line number Diff line number Diff line change
@@ -1,46 +1,57 @@
#! /usr/bin/env node
import { program } from 'commander';
import * as process from 'process';
import { init } from './cmd/init/init';
import { generate } from './cmd/generate/generate';
import { validate } from './cmd/validate/validate';
import { format } from './cmd/format/format';
import { db } from './cmd/db/db';
import { studio } from './cmd/studio/studio';
import { migrate } from './cmd/migrate/migrate';
import { program } from "commander";
import * as process from "process";
import { init } from "./cmd/init/init";
import { generate } from "./cmd/generate/generate";
import { validate } from "./cmd/validate/validate";
import { format } from "./cmd/format/format";
import { db } from "./cmd/db/db";
import { studio } from "./cmd/studio/studio";
import { migrate } from "./cmd/migrate/migrate";
import { loadExternalEnv } from "./utils/functions";

// TODO: add custom options processing

// program definition
program
.name('cosmoprism')
.alias('cprism')
.description('Cosmoprism 🔺🧊')
.version(process.env.npm_package_version ?? '-');
.name("cosmoprism")
.alias("cprism")
.description("Cosmoprism 🔺🧊")
.version(process.env.npm_package_version ?? "-")
.hook("preAction", loadExternalEnv);

// ---------------
// command: INIT
// ---------------
program.command('init').action(async () => await init());
program.command("init").action(async () => await init());

// ---------------
// command: GENERATE
// ---------------
program.command('generate')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
program
.command("generate")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.action(async (...args) => {
const { tenant, central } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await generate(!central && !tenant ? { mode: 'all' } : !!central ? { mode: 'central' } : { mode: 'tenant', tenant });
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await generate(
!central && !tenant
? { mode: "all" }
: central
? { mode: "central" }
: { mode: "tenant", tenant }
);
});

// ---------------
// command: VALIDATE
// ---------------
program.command('validate')
.option('--schema [file]', 'Schema to validate.')
program
.command("validate")
.option("--schema [file]", "Schema to validate.")
.action(async (...args) => {
const { schema } = args[0];

Expand All @@ -50,9 +61,13 @@ program.command('validate')
// ---------------
// command: FORMAT
// ---------------
program.command('format')
.option('--schema [file]', 'Schema to validate.')
.option('--check', ' Fails if any files are unformatted. This can be used in CI to detect if the schema is formatted correctly.')
program
.command("format")
.option("--schema [file]", "Schema to validate.")
.option(
"--check",
" Fails if any files are unformatted. This can be used in CI to detect if the schema is formatted correctly."
)
.action(async (...args) => {
const { schema, check } = args[0];

Expand All @@ -63,95 +78,130 @@ program.command('format')
// command: DB
// subcommands: seed
// ---------------
const dbCommand = program.command('db');
const dbCommand = program.command("db");
// dbCommand.command('pull') // TODO: implement
// dbCommand.command('push') // TODO: implement
// dbCommand.command('execute') // TODO: implement
dbCommand.command('seed')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
dbCommand
.command("seed")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.action(async (...args) => {
const { tenant, central } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await db.seed(!central && !tenant ? { mode: 'all' } : !!central ? { mode: 'central' } : { mode: 'tenant', tenant })
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await db.seed(
!central && !tenant
? { mode: "all" }
: central
? { mode: "central" }
: { mode: "tenant", tenant }
);
});

// ---------------
// command: MIGRATE
// subcommands: dev, reset, deploy
// ---------------
const migrateCommand = program.command('migrate');
const migrateCommand = program.command("migrate");
// dbCommand.command('resolve') // TODO: implement
// dbCommand.command('status') // TODO: implement
// dbCommand.command('diff') // TODO: implement
// dev
migrateCommand.command('dev')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
.option('-n, --name <name>', 'The name of the migration. If no name is provided, the CLI will prompt you.')
.option('--create-only', 'Creates a new migration based on the changes in the schema but does not apply that migration. Run migrate dev to apply migration.')
.option('--skip-seed', 'Skip triggering seed.')
.option('--skip-generate', 'Skip triggering generators (for example, Prisma Client)')
migrateCommand
.command("dev")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.option(
"-n, --name <name>",
"The name of the migration. If no name is provided, the CLI will prompt you."
)
.option(
"--create-only",
"Creates a new migration based on the changes in the schema but does not apply that migration. Run migrate dev to apply migration."
)
.option("--skip-seed", "Skip triggering seed.")
.option(
"--skip-generate",
"Skip triggering generators (for example, Prisma Client)"
)
.action(async (...args) => {
const { tenant, central, name, createOnly, skipSeed, skipGenerate } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await migrate.dev(!central && !tenant
? { mode: 'all', name, createOnly, skipGenerate, skipSeed }
: !!central
? { mode: 'central', name, createOnly, skipGenerate, skipSeed }
: { mode: 'tenant', tenant, name, createOnly, skipGenerate, skipSeed}
)
const { tenant, central, name, createOnly, skipSeed, skipGenerate } =
args[0];
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await migrate.dev(
!central && !tenant
? { mode: "all", name, createOnly, skipGenerate, skipSeed }
: central
? { mode: "central", name, createOnly, skipGenerate, skipSeed }
: { mode: "tenant", tenant, name, createOnly, skipGenerate, skipSeed }
);
});
// reset
migrateCommand.command('reset')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
.option('-f, --force', 'Skip the confirmation prompt.')
.option('--skip-seed', 'Skip triggering seed.')
.option('--skip-generate', 'Skip triggering generators (for example, Prisma Client)')
migrateCommand
.command("reset")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.option("-f, --force", "Skip the confirmation prompt.")
.option("--skip-seed", "Skip triggering seed.")
.option(
"--skip-generate",
"Skip triggering generators (for example, Prisma Client)"
)
.action(async (...args) => {
const { tenant, central, force, skipSeed, skipGenerate } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await migrate.reset(!central && !tenant
? { mode: 'all', force, skipGenerate, skipSeed }
: !!central
? { mode: 'central', force, skipGenerate, skipSeed }
: { mode: 'tenant', tenant, force, skipGenerate, skipSeed }
)
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await migrate.reset(
!central && !tenant
? { mode: "all", force, skipGenerate, skipSeed }
: central
? { mode: "central", force, skipGenerate, skipSeed }
: { mode: "tenant", tenant, force, skipGenerate, skipSeed }
);
});
// deploy
migrateCommand.command('deploy')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
migrateCommand
.command("deploy")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.action(async (...args) => {
const { tenant, central } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await migrate.deploy(!central && !tenant
? { mode: 'all' }
: !!central
? { mode: 'central' }
: { mode: 'tenant', tenant }
)
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await migrate.deploy(
!central && !tenant
? { mode: "all" }
: central
? { mode: "central" }
: { mode: "tenant", tenant }
);
});


// ---------------
// command: STUDIO
// ---------------
program.command('studio')
.option('-t, --tenant [tenant-id]', 'Apply generate command only for tenant.')
.option('-c, --central', 'Apply generate command only for central.')
.option('-b, --browser [browser]', 'The browser to auto-open Studio in.')
.option('-p, --port [port]', 'The port number to start Studio on.', '5555')
program
.command("studio")
.option("-t, --tenant [tenant-id]", "Apply generate command only for tenant.")
.option("-c, --central", "Apply generate command only for central.")
.option("-b, --browser [browser]", "The browser to auto-open Studio in.")
.option("-p, --port [port]", "The port number to start Studio on.", "5555")
.action(async (...args) => {
const { tenant, central, browser, port } = args[0];
if (!!tenant && !! central) throw new Error('ERR: Only one of tenant and central can by passed !!');

await studio(!!central ? { mode: 'central', browser, port } : { mode: 'tenant', tenant, browser, port });
if (!!tenant && !!central)
throw new Error("ERR: Only one of tenant and central can by passed !!");

await studio(
central
? { mode: "central", browser, port }
: { mode: "tenant", tenant, browser, port }
);
});

// parse program
Expand Down
4 changes: 2 additions & 2 deletions src/cmd/db/db.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
import * as seedCmd from './seed/seed';
import * as seedCmd from "./seed/seed";

export const db = { seed: seedCmd.seed }
export const db = { seed: seedCmd.seed };
Loading

0 comments on commit a418835

Please sign in to comment.