Line data Source code
1 : /*
2 : This file is part of TALER
3 : Copyright (C) 2022, 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 : /**
17 : * @file src/backenddb/iterate_accounts.c
18 : * @brief Implementation of the iterate_accounts function for Postgres
19 : * @author Christian Grothoff
20 : */
21 : #include "platform.h"
22 : #include <taler/taler_pq_lib.h>
23 : #include "merchant-database/iterate_accounts.h"
24 : #include "helper.h"
25 :
26 :
27 : /**
28 : * Context for iterate_accounts().
29 : */
30 : struct SelectAccountsContext
31 : {
32 : /**
33 : * Function to call with the results.
34 : */
35 : TALER_MERCHANTDB_AccountCallback cb;
36 :
37 : /**
38 : * Closure for @e cb.
39 : */
40 : void *cb_cls;
41 :
42 : /**
43 : * Database context.
44 : */
45 : struct TALER_MERCHANTDB_PostgresContext *pg;
46 :
47 : /**
48 : * Set to the return value on errors.
49 : */
50 : enum GNUNET_DB_QueryStatus qs;
51 :
52 : };
53 :
54 :
55 : /**
56 : * Function to be called with the results of a SELECT statement
57 : * that has returned @a num_results results about accounts.
58 : *
59 : * @param cls of type `struct SelectAccountsContext *`
60 : * @param result the postgres result
61 : * @param num_results the number of results in @a result
62 : */
63 : static void
64 72 : select_account_cb (void *cls,
65 : PGresult *result,
66 : unsigned int num_results)
67 : {
68 72 : struct SelectAccountsContext *lic = cls;
69 :
70 133 : for (unsigned int i = 0; i < num_results; i++)
71 : {
72 : struct TALER_FullPayto payto;
73 : char *instance_id;
74 61 : char *facade_url = NULL;
75 61 : char *extra_wire_subject_metadata = NULL;
76 61 : json_t *credential = NULL;
77 : struct TALER_MERCHANTDB_AccountDetails acc;
78 : struct TALER_MerchantPrivateKeyP merchant_priv;
79 : bool no_priv;
80 61 : struct GNUNET_PQ_ResultSpec rs[] = {
81 61 : GNUNET_PQ_result_spec_auto_from_type ("out_h_wire",
82 : &acc.h_wire),
83 61 : GNUNET_PQ_result_spec_auto_from_type ("out_salt",
84 : &acc.salt),
85 61 : GNUNET_PQ_result_spec_string ("out_payto_uri",
86 : &payto.full_payto),
87 61 : GNUNET_PQ_result_spec_string ("out_merchant_id",
88 : &instance_id),
89 61 : GNUNET_PQ_result_spec_allow_null (
90 : GNUNET_PQ_result_spec_string ("out_credit_facade_url",
91 : &facade_url),
92 : NULL),
93 61 : GNUNET_PQ_result_spec_allow_null (
94 : GNUNET_PQ_result_spec_string ("out_extra_wire_subject_metadata",
95 : &extra_wire_subject_metadata),
96 : NULL),
97 61 : GNUNET_PQ_result_spec_allow_null (
98 : TALER_PQ_result_spec_json ("out_credit_facade_credentials",
99 : &credential),
100 : NULL),
101 61 : GNUNET_PQ_result_spec_bool ("out_active",
102 : &acc.active),
103 61 : GNUNET_PQ_result_spec_allow_null (
104 : GNUNET_PQ_result_spec_auto_from_type ("out_merchant_priv",
105 : &merchant_priv),
106 : &no_priv),
107 : GNUNET_PQ_result_spec_end
108 : };
109 :
110 61 : if (GNUNET_OK !=
111 61 : GNUNET_PQ_extract_result (result,
112 : rs,
113 : i))
114 : {
115 0 : GNUNET_break (0);
116 0 : lic->qs = GNUNET_DB_STATUS_HARD_ERROR;
117 0 : return;
118 : }
119 61 : acc.instance_id = instance_id;
120 61 : acc.payto_uri = payto;
121 61 : acc.credit_facade_url = facade_url;
122 61 : acc.credit_facade_credentials = credential;
123 61 : acc.extra_wire_subject_metadata = extra_wire_subject_metadata;
124 61 : if (NULL != lic->cb)
125 61 : lic->cb (lic->cb_cls,
126 : no_priv ? NULL : &merchant_priv,
127 : &acc);
128 61 : GNUNET_PQ_cleanup_result (rs);
129 : }
130 : }
131 :
132 :
133 : enum GNUNET_DB_QueryStatus
134 72 : TALER_MERCHANTDB_iterate_accounts (
135 : struct TALER_MERCHANTDB_PostgresContext *pg,
136 : TALER_MERCHANTDB_AccountCallback cb,
137 : void *cb_cls)
138 : {
139 72 : struct SelectAccountsContext lic = {
140 : .cb = cb,
141 : .cb_cls = cb_cls,
142 : .pg = pg
143 : };
144 72 : struct GNUNET_PQ_QueryParam params[] = {
145 : GNUNET_PQ_query_param_end
146 : };
147 : enum GNUNET_DB_QueryStatus qs;
148 :
149 72 : PREPARE (pg,
150 : "iterate_accounts",
151 : "SELECT"
152 : " out_merchant_id"
153 : " ,out_merchant_priv"
154 : " ,out_h_wire"
155 : " ,out_salt"
156 : " ,out_payto_uri"
157 : " ,out_credit_facade_url"
158 : " ,out_credit_facade_credentials::TEXT"
159 : " ,out_extra_wire_subject_metadata"
160 : " ,out_active"
161 : " FROM merchant.select_accounts()");
162 72 : qs = GNUNET_PQ_eval_prepared_multi_select (pg->conn,
163 : "iterate_accounts",
164 : params,
165 : &select_account_cb,
166 : &lic);
167 72 : if (0 > lic.qs)
168 0 : return lic.qs;
169 72 : return qs;
170 : }
|