sql построить дерево, повесив его на лист - PullRequest
0 голосов
/ 21 апреля 2020

У меня есть 2 таблицы (даны только соответствующие столбцы) как

таблица j

id int
account int
amount numeric;

таблица e

id int
account int
amount numeric
code_id foreign key to j.id

образец данных

таблица j

  id   account_id   amount     
 ---- ------------ -------- -- 
   1            5      500     
   2            6     -700     
   3                           
   4            6      200     
   5                           

таблица e

  id   account_id   amount   code_id  
 ---- ------------ -------- --------- 
   1           10     -200         1  
   2            6     -100         1  
   3            8      150         1  
   4            7     -350         1  
   5           12      200         2  
   6           13      500         2  
   5            6      200         3  
   6            4     -100         3  
   7            6     -125         3  
   8            5       25         3  
   9            6     -200         4  
  10            6      300         5  
  11           12     -300         5  

Я хочу для каждого account_id в таблице j или таблице e следующее. Я даю результат для счета 6

Редактировать: нужно взять 6 и повесить его вверх ногами, перечислив все транзакции против него следующим образом.

  ledger_head_id   account_id   amount   bal   t_id  
 ---------------- ------------ -------- ----- ------ 
               6           10     -200            1  
               6            8      150            1  
               6            7     -350            1  
               6            5      500   100      1  
               6           12      200            2  
               6           13      500   700      2  
               6            4     -100            3  
               6            5       25    75      3  
               6            6     -200   200      4  
               6           12     -300   300      5  

То, что я сделал, это

WITH tb1 AS (
    SELECT *
    FROM (
        SELECT code_id AS j_id, account_id, amount, 'E' AS entry_type, e.id AS entry_id
        FROM t, e
        WHERE code_id = t.id
        UNION ALL
        SELECT id, account_id, amount, NULL, NULL
        FROM t
    ) foo
    WHERE account_id NOTNULL
)
    SELECT
        DISTINCT ON (l2.account_id, j_id)
        j_id,
        l2.account_id AS ledger_head_id,
        jsonb_agg(
            jsonb_build_object(
                'account_id', l1.account_id,
                'amt', l1.amount,
            )
        ) OVER ( PARTITION BY l2.account_id, l1.j_id ORDER BY l2.account_id, l1.j_id ) AS details,
        l2.amount
    FROM tb1 l1
    LEFT JOIN tb1 l2 USING (j_id)
    WHERE
          ((l1.entry_type = 'E' AND l1.entry_id IS DISTINCT FROM l2.entry_id) OR ((l1.entry_type != 'E' OR l1.entry_type ISNULL ) AND l1.account_id != l2.account_id))
    ORDER BY ledger_head_id, j_id

Я чувствую, это не оптимальный способ сделать это. Просто для информации, мне не нужно объединять целые таблицы ... Я мог бы сделать это для учетной записи, требуемой как (ledger_head_id), если это может быть более эффективным, тогда я должен использовать функции в Postgres.

В основном ищем лучший способ сделать это.

Использование: Postgres 12

Спасибо

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...