Skip to content

Commit

Permalink
improvement: add money sub & negation operators
Browse files Browse the repository at this point in the history
  • Loading branch information
zachdaniel committed May 12, 2024
1 parent 684b0dc commit c25e0eb
Showing 1 changed file with 95 additions and 1 deletion.
96 changes: 95 additions & 1 deletion lib/ash_money/ash_postgres_extension.ex
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,27 @@ if Code.ensure_loaded?(AshPostgres.CustomExtension) do
@moduledoc """
Installs the `money_with_currency` type and operators/functions for Postgres.
"""
use AshPostgres.CustomExtension, name: :ash_money, latest_version: 2
use AshPostgres.CustomExtension, name: :ash_money, latest_version: 3

def install(2) do
"""
#{Money.DDL.execute_each(add_money_sub())}
#{Money.DDL.execute_each(add_money_neg())}
"""
end

def install(1) do
"""
#{Money.DDL.execute_each(add_money_sub())}
#{Money.DDL.execute_each(add_money_mult())}
#{Money.DDL.execute_each(add_money_neg())}
"""
end

def install(0) do
"""
#{Money.DDL.execute_each(add_money_sub())}
#{Money.DDL.execute_each(add_money_neg())}
#{Money.DDL.execute_each(Money.DDL.create_money_with_currency())}
#{Money.DDL.execute_each(Money.DDL.define_plus_operator())}
#{Money.DDL.execute_each(Money.DDL.define_minmax_functions())}
Expand All @@ -21,6 +32,14 @@ if Code.ensure_loaded?(AshPostgres.CustomExtension) do
"""
end

def uninstall(3) do
"""
#{Money.DDL.execute_each(remove_money_sub())}
#{Money.DDL.execute_each(remove_money_neg())}
#{uninstall(2)}
"""
end

def uninstall(v) when v in [0, 1, 2] do
"""
#{Money.DDL.execute_each(remove_money_mult())}
Expand All @@ -31,6 +50,81 @@ if Code.ensure_loaded?(AshPostgres.CustomExtension) do
"""
end

defp add_money_neg do
"""
CREATE OR REPLACE FUNCTION money_neg(money_1 money_with_currency)
RETURNS money_with_currency
IMMUTABLE
STRICT
LANGUAGE plpgsql
AS $$
DECLARE
currency varchar;
addition numeric;
BEGIN
currency := currency_code(money_1);
addition := amount(money_1) * -1;
return row(currency, addition);
END;
$$;
CREATE OPERATOR - (
rightarg = money_with_currency,
procedure = money_neg
);
"""
end

defp remove_money_neg do
"""
DROP OPERATOR -(none, money_with_currency);
DROP FUNCTION IF EXISTS money_neg(money_1 money_with_currency);
"""
end

defp add_money_sub do
"""
CREATE OR REPLACE FUNCTION money_sub(money_1 money_with_currency, money_2 money_with_currency)
RETURNS money_with_currency
IMMUTABLE
STRICT
LANGUAGE plpgsql
AS $$
DECLARE
currency varchar;
subtraction numeric;
BEGIN
IF currency_code(money_1) = currency_code(money_2) THEN
currency := currency_code(money_1);
subtraction := amount(money_1) - amount(money_2);
return row(currency, subtraction);
ELSE
RAISE EXCEPTION
'Incompatible currency codes for - operator. Expected both currency codes to be %', currency_code(money_1)
USING HINT = 'Please ensure both columns have the same currency code',
ERRCODE = '22033';
END IF;
END;
$$;
CREATE OPERATOR - (
leftarg = money_with_currency,
rightarg = money_with_currency,
procedure = money_sub,
commutator = -
);
"""
end

defp remove_money_sub do
"""
DROP OPERATOR - (money_with_currency, money_with_currency);
DROP FUNCTION IF EXISTS money_sub(money_1 money_with_currency, money_2 money_with_currency);
"""
end

defp add_money_mult do
"""
CREATE OR REPLACE FUNCTION money_mult(multiplicator numeric, money money_with_currency)
Expand Down

0 comments on commit c25e0eb

Please sign in to comment.