npm package: @fwl/migration
Description: Migration part of Fewlines Web Libraries
Author: Fewlines
Latest version: 0.2.4

= FWL Migration
:toc: preamble

**Disclaimer**: this package is made for our internal usage and is only open source for convenience so we might not consider Pull Requests or Issues. Feel free to fork though.

This is part of the Fewlines Web Libraries packages.

It provides a migration tool using SQL files.

== Installation

[source, shell]
----
yarn add @fwl/migration
----

== Usage

`migration` is a database migration library written in TypeScript, which can be used as a **CLI** or imported as a npm **package**.

It will look into the migrations folder and execute each SQL queries, in the correct order. If one of the transaction fails, `migration` will keep track of the last successful query through a `migration_schemas` table, so you can safely rerun the migration process.

=== As a CLI

==== Config object

To run `migration` as a CLI, you can create a `config.json` with the following data structure:

[source, typescript]
----
{
  "database": {
    "database": string;
    "password": string;
    "username": string;
    "host": string;
    "port": number;
    "ssl"?: boolean | {
      rejectUnauthorized: boolean,
      ca?: string;
      key?: string;
      cert?: string;
    }
  },
  "migration": {
    "dirPath": string;
    "tableName"?: string
  }
}
----

If you don't, the default config object will be used. The default config values can be overridden with various flags, listed in the following section.

You can then simply run one of those command, depending on your needs:

==== `migration migrate`

Run the database migration process. The following options can be passed to this command:

|===
| Flag name | Description

| configPath
| Override the path to the configuration file (default: "./config.json").

| databaseURL
| Override the database configuration, should be a valid PostgreSQL URL (setting this will override the configuration file).

| sslCaPath
| Can be the relative or the absolute path to the file. Add the SSL CA to the config object, and set `rejectUnauthorized` to false.

| sslKeyPath
| Can be the relative or the absolute path to the file. Add the SSL Key to the config object, and set `rejectUnauthorized` to false.

| sslCertPath
| Can be the relative or the absolute path to the file. Add the SSL Cert to the config object, and set `rejectUnauthorized` to false.

| migrationsPath
| Override the path to the migrations SQL files (setting this will override the configuration file).

| migrationsTable
| Override the table name in which ran migrations are registered (setting this will override the configuration file).
|===

==== `migration dryRun`

Run the migration process and rolls it back right away. The following options can be passed to this command:

|===
| Flag name | Description

| configPath
| Override the path to the configuration file (default: "./config.json").

| databaseURL
| Override the database configuration, should be a valid PostgreSQL URL (setting this will override the configuration file).

| sslCaPath
| Can be the relative or the absolute path to the file. Add the SSL CA to the config object, and set `rejectUnauthorized` to false.

| sslKeyPath
| Can be the relative or the absolute path to the file. Add the SSL Key to the config object, and set `rejectUnauthorized` to false.

| sslCertPath
| Can be the relative or the absolute path to the file. Add the SSL Cert to the config object, and set `rejectUnauthorized` to false.

| migrationsPath
| Override the path to the migrations SQL files (setting this will override the configuration file).

| migrationsTable
| Override the table name in which ran migrations are registered, (setting this will override the configuration file).
|===

==== migration create name_of_the_file`

Create a timestamped migration file in the path set up in `config.json`. The following options can be passed to this command:

|===
| Flag name | Description

| configPath
| Override the path to the configuration file (default: "./config.json").

| migrationsPath
| Override the path to the migrations SQL files (setting this will override the configuration file).
|===

=== As a Package

If you need more customization and control over the migration process, you can implement your own logic by importing the package, which give you access to two functions.

==== `runMigrations`

You can give a config of `runMigrationsConfig` type as argument, or use the default settings by using the provided `defaultConfig` for the migrations folder and the database config:

[source, typescript]
----
import * as migration from "@fwl/migration";
import { defaultConfig as databaseDefaultConfig } from "@fwl/database";

migration.runMigrations({
  database: databaseDefaultConfig,
  migration: migration.defaultConfig,
});
----

==== `createMigrationFile`

The `createMigrationFile` takes the name of the file as an argument:

[source, typescript]
----
import * as migration from "@fwl/migration";

migration.createMigrationFile("name_of_the_file");
----

You can also use it through a custom npm script, and use the corresponding `process.argv` value as arguments.

[source, typescript]
----
import * as migration from "@fwl/migration";
import path from "path";

function createMigrationFile(): void {
  const [, , ...args] = process.argv;
  const dirPath = path.join(process.cwd(), "./relative/path");

  if (args.length > 0) {
    if (args.length === 1) {
      migration.createMigrationFile(args[0], dirPath);
    } else {
      throw new Error("Provide only one file name at a time.");
    }
  } else {
    throw new Error("Provide the name_of_the_file.");
  }
}

createMigrationFile();
----