merchant

Merchant backend to process payments, run by merchants
Log | Files | Refs | Submodules | README | LICENSE

merchant-0036.sql.in (5209B)


      1 --
      2 -- This file is part of TALER
      3 -- Copyright (C) 2026 Taler Systems SA
      4 --
      5 -- TALER is free software; you can redistribute it and/or modify it under the
      6 -- terms of the GNU General Public License as published by the Free Software
      7 -- Foundation; either version 3, or (at your option) any later version.
      8 --
      9 -- TALER is distributed in the hope that it will be useful, but WITHOUT ANY
     10 -- WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
     11 -- A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
     12 --
     13 -- You should have received a copy of the GNU General Public License along with
     14 -- TALER; see the file COPYING.  If not, see <http://www.gnu.org/licenses/>
     15 
     16 -- @file merchant-0036.sql.in
     17 -- @brief Move per-instance tables into per-instance schemas
     18 --   merchant_instance_<merchant_serial>.  Each existing row of
     19 --   merchant_instances is converted by calling
     20 --   merchant.create_instance_schema(serial), copying the rows of every
     21 --   per-instance table into the new schema (dropping the merchant_serial
     22 --   column), and finally dropping the now-empty merchant.<table>.
     23 -- @author Christian Grothoff
     24 
     25 BEGIN;
     26 
     27 SELECT _v.register_patch('merchant-0036', NULL, NULL);
     28 
     29 SET search_path TO merchant;
     30 
     31 -- ---------------------------------------------------------------------
     32 -- Step 0: Fold merchant_keys.merchant_priv into merchant_instances as a
     33 -- nullable column.  Setting merchant_priv to NULL replaces deleting the
     34 -- key row.  The merchant_keys table itself is dropped in step 4.
     35 -- ---------------------------------------------------------------------
     36 ALTER TABLE merchant.merchant_instances
     37   ADD COLUMN merchant_priv BYTEA
     38     CHECK (merchant_priv IS NULL OR LENGTH(merchant_priv) = 32);
     39 COMMENT ON COLUMN merchant.merchant_instances.merchant_priv
     40   IS 'private key of the instance, NULL once the key has been "deleted"';
     41 UPDATE merchant.merchant_instances mi
     42    SET merchant_priv = mk.merchant_priv
     43   FROM merchant.merchant_keys mk
     44  WHERE mk.merchant_serial = mi.merchant_serial;
     45 
     46 CREATE TABLE merchant.instance_fixups
     47  (instance_fixup_serial_id INT8 GENERATED BY DEFAULT AS IDENTITY
     48   ,migration_name TEXT NOT NULL
     49   ,version INT8 NOT NULL);
     50 COMMENT ON TABLE instance_fixups
     51   IS 'Fixups to setup the per-instance tables';
     52 COMMENT ON COLUMN instance_fixups.migration_name
     53   IS 'Name of the stored procedure to run to fix up the schema of the instance';
     54 COMMENT ON COLUMN instance_fixups.version
     55   IS 'Version of the DB in which the given fix up should happen';
     56 
     57 CREATE INDEX instance_fixups_by_version
     58   ON instance_fixups (version);
     59 COMMENT ON INDEX instance_fixups_by_version
     60   IS 'Used by create_instance_schema (and in the future on import)';
     61 
     62 -- ---------------------------------------------------------------------
     63 -- Step 1: Install the schema constructor and actual fix-ups.
     64 -- procedures.sql will re-install the same definition (DROP IF EXISTS),
     65 -- so installing it here is harmless and lets the migration call it.
     66 -- ---------------------------------------------------------------------
     67 #include "../create_tables.sql"
     68 #include "../pg_create_instance_schema.sql"
     69 #include "../pg_fixup_instance_schema.sql"
     70 #include "merchant-0036-init.sql.fragment"
     71 
     72 -- ---------------------------------------------------------------------
     73 -- Step 2: Build a per-instance schema for every existing instance.
     74 -- ---------------------------------------------------------------------
     75 DO $MIG$
     76 DECLARE
     77   rec RECORD;
     78 BEGIN
     79   FOR rec IN
     80     SELECT merchant_serial
     81       FROM merchant.merchant_instances
     82   LOOP
     83     PERFORM merchant.create_instance_schema(rec.merchant_serial);
     84   END LOOP;
     85 END $MIG$;
     86 
     87 -- ---------------------------------------------------------------------
     88 -- Step 3: Migrate row data per instance.
     89 --   Tables are copied in FK-dependency order.  Every copy drops the
     90 --   merchant_serial column.  After each table is copied, its IDENTITY
     91 --   sequence (if any) is advanced past MAX(serial).
     92 --   Indirect-FK tables (merchant_kyc, merchant_deposits, ...) are copied
     93 --   by JOINing back to the table that owns the merchant_serial.
     94 -- ---------------------------------------------------------------------
     95 -- Suppress USER triggers during the bulk copy: per-instance triggers
     96 -- (e.g. merchant_kyc_insert_trigger) would otherwise fire on every
     97 -- inserted row and CALL into per-instance procedures that may rely on
     98 -- runtime invariants we do not have during migration.  This setting is
     99 -- transaction-local and does not affect normal callers.
    100 SET session_replication_role = replica;
    101 
    102 DO $MIG$
    103 DECLARE
    104   rec RECORD;
    105   s   TEXT;
    106 BEGIN
    107   FOR rec IN
    108     SELECT merchant_serial
    109       FROM merchant.merchant_instances
    110   LOOP
    111     s := 'merchant_instance_' || rec.merchant_serial::TEXT;
    112 #include "merchant-0036-copy.sql.fragment"
    113 #include "merchant-0036-setval.sql.fragment"
    114   END LOOP;
    115 END $MIG$;
    116 
    117 SET session_replication_role = origin;
    118 
    119 -- ---------------------------------------------------------------------
    120 -- Step 4: Drop old per-instance tables from the merchant schema, in
    121 -- reverse FK-dependency order so CASCADE is not needed.
    122 -- ---------------------------------------------------------------------
    123 #include "merchant-0036-drop.sql.fragment"
    124 
    125 COMMIT;