Packages

A library to track writes to Ecto models.

Current section

Files

Jump to
journal lib mix journal.init.ex
Raw

lib/mix/journal.init.ex

defmodule Mix.Tasks.Journal.Init do
use Mix.Task
import Mix.Generator
@moduledoc """
Generate a migration to add the journal table, indexes and stored procedure to your schema.
## Usage
```sh
$ mix journal.init
```
"""
def run(args) do
change = EEx.eval_string(migration_template([]))
["create_journal#{args}", "--change=#{change}"]
|> Mix.Tasks.Ecto.Gen.Migration.run()
end
embed_template(:migration, """
create table(:journal_journal) do
add(:table_name, :text)
add(:operation, :text)
add(:new_val, :map)
add(:old_val, :map)
add(:inserted_at, :utc_datetime_usec, default: fragment(\"clock_timestamp()\"))
end
create index(:journal_journal, :inserted_at)
create index(:journal_journal, :table_name)
create index(:journal_journal, :operation)
execute(
\"
CREATE FUNCTION change_trigger ()
RETURNS TRIGGER
AS $$
BEGIN
IF TG_OP = 'INSERT' THEN
INSERT INTO journal_journal (table_name, operation, new_val)
VALUES (TG_RELNAME, TG_OP, row_to_json(NEW));
RETURN NEW;
ELSIF TG_OP = 'UPDATE' THEN
INSERT INTO journal_journal (table_name, operation, new_val, old_val)
VALUES (TG_RELNAME, TG_OP, row_to_json(NEW), row_to_json(OLD));
RETURN NEW;
ELSIF TG_OP = 'DELETE' THEN
INSERT INTO journal_journal (table_name, operation, old_val)
VALUES (TG_RELNAME, TG_OP, row_to_json(OLD));
RETURN OLD;
END IF;
END;
$$
LANGUAGE 'plpgsql'
SECURITY DEFINER;
\",
\"DROP FUNCTION IF EXISTS change_trigger ();\"
)
""")
end