merchant

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

merchant-0045.sql (2973B)


      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-0045.sql
     17 -- @brief repair settlement flags left stale by the reconciliation SQL bug
     18 
     19 BEGIN;
     20 
     21 SELECT _v.register_patch('merchant-0045', NULL, NULL);
     22 
     23 SET search_path TO merchant;
     24 
     25 CREATE PROCEDURE merchant.merchant_0045_init(s TEXT)
     26   LANGUAGE plpgsql
     27   AS $OUTER$
     28 BEGIN
     29 
     30   EXECUTE format('SET LOCAL search_path TO %I', s);
     31 
     32   -- From July 2025 until April 2026, the reconciliation query missed
     33   -- parentheses around its retry/WTID test.  An unrelated deposit without a
     34   -- WTID could therefore keep completed deposit confirmations wire-pending.
     35   -- Reconstruct the flag from the per-deposit settlement evidence.  Be
     36   -- conservative about NULL retry state and require at least one deposit.
     37   UPDATE merchant_deposit_confirmations mdc
     38      SET wire_pending=FALSE
     39    WHERE mdc.wire_pending
     40      AND EXISTS
     41          (SELECT 1
     42             FROM merchant_deposits md
     43            WHERE md.deposit_confirmation_serial=
     44                  mdc.deposit_confirmation_serial)
     45      AND NOT EXISTS
     46          (SELECT 1
     47             FROM merchant_deposits md
     48            WHERE md.deposit_confirmation_serial=
     49                  mdc.deposit_confirmation_serial
     50              AND (COALESCE(md.settlement_retry_needed, TRUE)
     51                   OR (md.settlement_wtid IS NULL)
     52                   OR (COALESCE(md.settlement_last_ec, 0) <> 0)));
     53 
     54   -- A paid contract is wired once all of its deposit confirmations are done.
     55   -- Require a confirmation so externally marked payments are not changed.
     56   -- This migration deliberately does not generate historical notifications
     57   -- or order-settled webhooks.
     58   UPDATE merchant_contract_terms mct
     59      SET wired=TRUE
     60    WHERE mct.paid
     61      AND NOT mct.wired
     62      AND EXISTS
     63          (SELECT 1
     64             FROM merchant_deposit_confirmations mdc
     65            WHERE mdc.order_serial=mct.order_serial)
     66      AND NOT EXISTS
     67          (SELECT 1
     68             FROM merchant_deposit_confirmations mdc
     69            WHERE mdc.order_serial=mct.order_serial
     70              AND mdc.wire_pending);
     71 
     72   SET LOCAL search_path TO merchant;
     73 
     74 END
     75 $OUTER$;
     76 
     77 INSERT INTO merchant.instance_fixups
     78   (migration_name
     79   ,version)
     80   VALUES
     81   ('merchant_0045_init'
     82   ,45);
     83 -- Apply new fix-up to existing instances
     84 CALL merchant.fixup_instance_schema (45::INT8);
     85 
     86 COMMIT;