aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChristian Blättler <blatc2@bfh.ch>2023-11-21 08:07:27 +0100
committerChristian Blättler <blatc2@bfh.ch>2023-11-21 08:07:27 +0100
commit14dae4fd53aaadbf7792eda5aa3158b562ccff3a (patch)
tree2364551192d4ccacdb2833c569bcc3b6284cb44a /src
parentda3bc6a9326b8e0c0c4d6d7af0ec3dc990592f28 (diff)
parentcdc93b68f0b586282653acc9d3aaaa9f2ac4fa2e (diff)
downloadexchange-14dae4fd53aaadbf7792eda5aa3158b562ccff3a.tar.xz
Merge branch 'master' into feature/tokens
Diffstat (limited to 'src')
-rw-r--r--src/auditor/generate-auditor-basedb.conf24
-rw-r--r--src/exchange/Makefile.am3
-rw-r--r--src/exchange/taler-exchange-httpd.c74
-rw-r--r--src/exchange/taler-exchange-httpd_aml-decisions-get.c22
-rw-r--r--src/exchange/taler-exchange-httpd_spa.c362
-rw-r--r--src/exchange/taler-exchange-httpd_spa.h49
-rw-r--r--src/exchangedb/exchange_do_insert_aml_decision.sql16
-rw-r--r--src/exchangedb/pg_trigger_aml_process.c8
-rw-r--r--src/include/taler_crypto_lib.h96
-rw-r--r--src/include/taler_util.h6
-rw-r--r--src/json/json_helper.c2
-rw-r--r--src/kyclogic/plugin_kyclogic_kycaid.c6
-rw-r--r--src/lib/exchange_api_stefan.c28
-rw-r--r--src/templating/templating_api.c5
-rwxr-xr-xsrc/testing/taler-unified-setup.sh18
-rw-r--r--src/util/config.c7
-rw-r--r--src/util/currencies.conf9
-rw-r--r--src/util/paths.conf6
18 files changed, 609 insertions, 132 deletions
diff --git a/src/auditor/generate-auditor-basedb.conf b/src/auditor/generate-auditor-basedb.conf
index f718886dc..8aae9a924 100644
--- a/src/auditor/generate-auditor-basedb.conf
+++ b/src/auditor/generate-auditor-basedb.conf
@@ -28,12 +28,26 @@ WIRE_GATEWAY_AUTH_METHOD = basic
USERNAME = exchange
PASSWORD = x
+[exchange-account-2]
+PAYTO_URI = "payto://x-taler-bank/localhost/2?receiver-name=2"
+ENABLE_DEBIT = YES
+ENABLE_CREDIT = YES
+
+[exchange-accountcredentials-2]
+WIRE_GATEWAY_AUTH_METHOD = basic
+USERNAME = Exchange
+PASSWORD = x
+WIRE_GATEWAY_URL = "http://localhost:8082/accounts/2/taler-wire-gateway/"
+
+[admin-accountcredentials-2]
+WIRE_GATEWAY_AUTH_METHOD = basic
+# For now, fakebank still checks against the Exchange account...
+USERNAME = Exchange
+PASSWORD = x
+WIRE_GATEWAY_URL = "http://localhost:8082/accounts/2/taler-wire-gateway/"
+
+
[merchant]
-WIREFORMAT = default
-DEFAULT_MAX_DEPOSIT_FEE = TESTKUDOS:0.1
-KEYFILE = ${TALER_DATA_HOME}/merchant/merchant.priv
-DEFAULT_MAX_WIRE_FEE = TESTKUDOS:0.10
-WIRE_TRANSFER_DELAY = 1 minute
FORCE_AUDIT = YES
[merchantdb-postgres]
diff --git a/src/exchange/Makefile.am b/src/exchange/Makefile.am
index 12ea34e13..7d0e5a334 100644
--- a/src/exchange/Makefile.am
+++ b/src/exchange/Makefile.am
@@ -181,8 +181,9 @@ taler_exchange_httpd_SOURCES = \
taler-exchange-httpd_reserves_open.c taler-exchange-httpd_reserves_open.h \
taler-exchange-httpd_reserves_purse.c taler-exchange-httpd_reserves_purse.h \
taler-exchange-httpd_responses.c taler-exchange-httpd_responses.h \
+ taler-exchange-httpd_spa.c taler-exchange-httpd_spa.h \
taler-exchange-httpd_terms.c taler-exchange-httpd_terms.h \
- taler-exchange-httpd_transfers_get.c taler-exchange-httpd_transfers_get.h
+ taler-exchange-httpd_transfers_get.c taler-exchange-httpd_transfers_get.h
taler_exchange_httpd_LDADD = \
$(LIBGCRYPT_LIBS) \
diff --git a/src/exchange/taler-exchange-httpd.c b/src/exchange/taler-exchange-httpd.c
index 7c7777561..1cde58164 100644
--- a/src/exchange/taler-exchange-httpd.c
+++ b/src/exchange/taler-exchange-httpd.c
@@ -68,6 +68,7 @@
#include "taler-exchange-httpd_reserves_history.h"
#include "taler-exchange-httpd_reserves_open.h"
#include "taler-exchange-httpd_reserves_purse.h"
+#include "taler-exchange-httpd_spa.h"
#include "taler-exchange-httpd_terms.h"
#include "taler-exchange-httpd_transfers_get.h"
#include "taler_exchangedb_lib.h"
@@ -1508,6 +1509,56 @@ handle_post_auditors (struct TEH_RequestContext *rc,
/**
+ * Generates the response for "/", redirecting the
+ * client to the "/webui/" from where we serve the SPA.
+ *
+ * @param rc request context
+ * @param args remaining arguments (should be empty)
+ * @return MHD result code
+ */
+static MHD_RESULT
+spa_redirect (struct TEH_RequestContext *rc,
+ const char *const args[])
+{
+ const char *text = "Redirecting to /webui/";
+ struct MHD_Response *response;
+
+ response = MHD_create_response_from_buffer (strlen (text),
+ (void *) text,
+ MHD_RESPMEM_PERSISTENT);
+ if (NULL == response)
+ {
+ GNUNET_break (0);
+ return MHD_NO;
+ }
+ TALER_MHD_add_global_headers (response);
+ GNUNET_break (MHD_YES ==
+ MHD_add_response_header (response,
+ MHD_HTTP_HEADER_CONTENT_TYPE,
+ "text/plain"));
+ if (MHD_NO ==
+ MHD_add_response_header (response,
+ MHD_HTTP_HEADER_LOCATION,
+ "/webui/"))
+ {
+ GNUNET_break (0);
+ MHD_destroy_response (response);
+ return MHD_NO;
+ }
+
+ {
+ MHD_RESULT ret;
+
+ ret = MHD_queue_response (rc->connection,
+ MHD_HTTP_FOUND,
+ response);
+ MHD_destroy_response (response);
+ return ret;
+ }
+}
+
+
+/**
* Handle incoming HTTP request.
*
* @param cls closure for MHD daemon (unused)
@@ -1540,15 +1591,11 @@ handle_mhd_request (void *cls,
.data = "User-agent: *\nDisallow: /\n",
.response_code = MHD_HTTP_OK
},
- /* Landing page, tell humans to go away. */
+ /* Landing page, redirect to SPA */
{
.url = "",
.method = MHD_HTTP_METHOD_GET,
- .handler.get = TEH_handler_static_response,
- .mime_type = "text/plain",
- .data =
- "Hello, I'm the Taler exchange. This HTTP server is not for humans.\n",
- .response_code = MHD_HTTP_OK
+ .handler.get = &spa_redirect
},
/* AGPL licensing page, redirect to source. As per the AGPL-license, every
deployment is required to offer the user a download of the source of
@@ -1778,7 +1825,13 @@ handle_mhd_request (void *cls,
.handler.post = &handle_post_aml,
.nargs = 2
},
-
+ {
+ .url = "webui",
+ .method = MHD_HTTP_METHOD_GET,
+ .handler.get = &TEH_handler_spa,
+ .nargs = 1,
+ .nargs_is_upper_bound = true
+ },
/* mark end of list */
{
@@ -2543,6 +2596,13 @@ run (void *cls,
return;
}
if (GNUNET_OK !=
+ TEH_spa_init ())
+ {
+ global_ret = EXIT_NOTCONFIGURED;
+ GNUNET_SCHEDULER_shutdown ();
+ return;
+ }
+ if (GNUNET_OK !=
TALER_TEMPLATING_init ("exchange"))
{
global_ret = EXIT_FAILURE;
diff --git a/src/exchange/taler-exchange-httpd_aml-decisions-get.c b/src/exchange/taler-exchange-httpd_aml-decisions-get.c
index 0183ac3b8..763817cf6 100644
--- a/src/exchange/taler-exchange-httpd_aml-decisions-get.c
+++ b/src/exchange/taler-exchange-httpd_aml-decisions-get.c
@@ -81,7 +81,7 @@ TEH_handler_aml_decisions_get (
{
enum TALER_AmlDecisionState decision;
int delta = -20;
- unsigned long long start = INT64_MAX;
+ unsigned long long start;
const char *state_str = args[0];
if (NULL == state_str)
@@ -123,40 +123,44 @@ TEH_handler_aml_decisions_get (
p = MHD_lookup_connection_value (rc->connection,
MHD_GET_ARGUMENT_KIND,
- "start");
+ "delta");
if (NULL != p)
{
char dummy;
if (1 != sscanf (p,
- "%llu%c",
- &start,
+ "%d%c",
+ &delta,
&dummy))
{
GNUNET_break_op (0);
return TALER_MHD_reply_with_error (rc->connection,
MHD_HTTP_BAD_REQUEST,
TALER_EC_GENERIC_PARAMETER_MALFORMED,
- "start");
+ "delta");
}
}
+ if (delta > 0)
+ start = 0;
+ else
+ start = INT64_MAX;
p = MHD_lookup_connection_value (rc->connection,
MHD_GET_ARGUMENT_KIND,
- "delta");
+ "start");
if (NULL != p)
{
char dummy;
if (1 != sscanf (p,
- "%d%c",
- &delta,
+ "%llu%c",
+ &start,
&dummy))
{
GNUNET_break_op (0);
return TALER_MHD_reply_with_error (rc->connection,
MHD_HTTP_BAD_REQUEST,
TALER_EC_GENERIC_PARAMETER_MALFORMED,
- "delta");
+ "start");
}
}
}
diff --git a/src/exchange/taler-exchange-httpd_spa.c b/src/exchange/taler-exchange-httpd_spa.c
new file mode 100644
index 000000000..60bed3d28
--- /dev/null
+++ b/src/exchange/taler-exchange-httpd_spa.c
@@ -0,0 +1,362 @@
+/*
+ This file is part of TALER
+ Copyright (C) 2020, 2023 Taler Systems SA
+
+ TALER is free software; you can redistribute it and/or modify it under the
+ terms of the GNU General Public License as published by the Free Software
+ Foundation; either version 3, or (at your option) any later version.
+
+ TALER is distributed in the hope that it will be useful, but WITHOUT ANY
+ WARRANTY; without even the implied warranty of EXCHANGEABILITY or FITNESS FOR
+ A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License along with
+ TALER; see the file COPYING. If not, see <http://www.gnu.org/licenses/>
+*/
+/**
+ * @file taler-exchange-httpd_spa.c
+ * @brief logic to load the single page app (/)
+ * @author Christian Grothoff
+ */
+#include "platform.h"
+#include <gnunet/gnunet_util_lib.h>
+#include "taler_util.h"
+#include "taler_mhd_lib.h"
+#include <gnunet/gnunet_mhd_compat.h>
+#include "taler-exchange-httpd.h"
+
+
+/**
+ * Resource from the WebUi.
+ */
+struct WebuiFile
+{
+ /**
+ * Kept in a DLL.
+ */
+ struct WebuiFile *next;
+
+ /**
+ * Kept in a DLL.
+ */
+ struct WebuiFile *prev;
+
+ /**
+ * Path this resource matches.
+ */
+ char *path;
+
+ /**
+ * SPA resource, compressed.
+ */
+ struct MHD_Response *zspa;
+
+ /**
+ * SPA resource, vanilla.
+ */
+ struct MHD_Response *spa;
+
+};
+
+
+/**
+ * Resources of the WebuUI, kept in a DLL.
+ */
+static struct WebuiFile *webui_head;
+
+/**
+ * Resources of the WebuUI, kept in a DLL.
+ */
+static struct WebuiFile *webui_tail;
+
+
+MHD_RESULT
+TEH_handler_spa (struct TEH_RequestContext *rc,
+ const char *const args[])
+{
+ struct WebuiFile *w = NULL;
+ const char *infix = args[0];
+
+ if ( (NULL == infix) ||
+ (0 == strcmp (infix,
+ "")) )
+ infix = "index.html";
+ for (struct WebuiFile *pos = webui_head;
+ NULL != pos;
+ pos = pos->next)
+ if (0 == strcmp (infix,
+ pos->path))
+ {
+ w = pos;
+ break;
+ }
+ if (NULL == w)
+ return TALER_MHD_reply_with_error (rc->connection,
+ MHD_HTTP_NOT_FOUND,
+ TALER_EC_GENERIC_ENDPOINT_UNKNOWN,
+ rc->url);
+ if ( (MHD_YES ==
+ TALER_MHD_can_compress (rc->connection)) &&
+ (NULL != w->zspa) )
+ return MHD_queue_response (rc->connection,
+ MHD_HTTP_OK,
+ w->zspa);
+ return MHD_queue_response (rc->connection,
+ MHD_HTTP_OK,
+ w->spa);
+}
+
+
+/**
+ * Function called on each file to load for the WebUI.
+ *
+ * @param cls NULL
+ * @param dn name of the file to load
+ */
+static enum GNUNET_GenericReturnValue
+build_webui (void *cls,
+ const char *dn)
+{
+ static struct
+ {
+ const char *ext;
+ const char *mime;
+ } mime_map[] = {
+ {
+ .ext = "css",
+ .mime = "text/css"
+ },
+ {
+ .ext = "html",
+ .mime = "text/html"
+ },
+ {
+ .ext = "js",
+ .mime = "text/javascript"
+ },
+ {
+ .ext = "jpg",
+ .mime = "image/jpeg"
+ },
+ {
+ .ext = "jpeg",
+ .mime = "image/jpeg"
+ },
+ {
+ .ext = "png",
+ .mime = "image/png"
+ },
+ {
+ .ext = "svg",
+ .mime = "image/svg+xml"
+ },
+ {
+ .ext = NULL,
+ .mime = NULL
+ },
+ };
+ int fd;
+ struct stat sb;
+ struct MHD_Response *zspa = NULL;
+ struct MHD_Response *spa;
+ const char *ext;
+ const char *mime;
+
+ (void) cls;
+ /* finally open template */
+ fd = open (dn,
+ O_RDONLY);
+ if (-1 == fd)
+ {
+ GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR,
+ "open",
+ dn);
+ return GNUNET_SYSERR;
+ }
+ if (0 !=
+ fstat (fd,
+ &sb))
+ {
+ GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR,
+ "open",
+ dn);
+ GNUNET_break (0 == close (fd));
+ return GNUNET_SYSERR;
+ }
+
+ mime = NULL;
+ ext = strrchr (dn, '.');
+ if (NULL == ext)
+ {
+ GNUNET_break (0 == close (fd));
+ return GNUNET_OK;
+ }
+ ext++;
+ for (unsigned int i = 0; NULL != mime_map[i].ext; i++)
+ if (0 == strcasecmp (ext,
+ mime_map[i].ext))
+ {
+ mime = mime_map[i].mime;
+ break;
+ }
+
+ {
+ void *in;
+ ssize_t r;
+ size_t csize;
+
+ in = GNUNET_malloc_large (sb.st_size);
+ if (NULL == in)
+ {
+ GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR,
+ "malloc");
+ GNUNET_break (0 == close (fd));
+ return GNUNET_SYSERR;
+ }
+ r = read (fd,
+ in,
+ sb.st_size);
+ if ( (-1 == r) ||
+ (sb.st_size != (size_t) r) )
+ {
+ GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR,
+ "read",
+ dn);
+ GNUNET_free (in);
+ GNUNET_break (0 == close (fd));
+ return GNUNET_SYSERR;
+ }
+ csize = (size_t) r;
+ if (MHD_YES ==
+ TALER_MHD_body_compress (&in,
+ &csize))
+ {
+ zspa = MHD_create_response_from_buffer (csize,
+ in,
+ MHD_RESPMEM_MUST_FREE);
+ if (NULL != zspa)
+ {
+ if (MHD_NO ==
+ MHD_add_response_header (zspa,
+ MHD_HTTP_HEADER_CONTENT_ENCODING,
+ "deflate"))
+ {
+ GNUNET_break (0);
+ MHD_destroy_response (zspa);
+ zspa = NULL;
+ }
+ if (NULL != mime)
+ GNUNET_break (MHD_YES ==
+ MHD_add_response_header (zspa,
+ MHD_HTTP_HEADER_CONTENT_TYPE,
+ mime));
+ }
+ }
+ else
+ {
+ GNUNET_free (in);
+ }
+ }
+
+ spa = MHD_create_response_from_fd (sb.st_size,
+ fd);
+ if (NULL == spa)
+ {
+ GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR,
+ "open",
+ dn);
+ GNUNET_break (0 == close (fd));
+ if (NULL != zspa)
+ {
+ MHD_destroy_response (zspa);
+ zspa = NULL;
+ }
+ return GNUNET_SYSERR;
+ }
+ if (NULL != mime)
+ GNUNET_break (MHD_YES ==
+ MHD_add_response_header (spa,
+ MHD_HTTP_HEADER_CONTENT_TYPE,
+ mime));
+
+ {
+ struct WebuiFile *w;
+ const char *fn;
+
+ fn = strrchr (dn, '/');
+ GNUNET_assert (NULL != fn);
+ w = GNUNET_new (struct WebuiFile);
+ w->path = GNUNET_strdup (fn + 1);
+ w->spa = spa;
+ w->zspa = zspa;
+ GNUNET_CONTAINER_DLL_insert (webui_head,
+ webui_tail,
+ w);
+ }
+ return GNUNET_OK;
+}
+
+
+enum GNUNET_GenericReturnValue
+TEH_spa_init ()
+{
+ char *dn;
+
+ {
+ char *path;
+
+ path = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR);
+ if (NULL == path)
+ {
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+ GNUNET_asprintf (&dn,
+ "%sexchange/spa/",
+ path);
+ GNUNET_free (path);
+ }
+
+ if (-1 ==
+ GNUNET_DISK_directory_scan (dn,
+ &build_webui,
+ NULL))
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Failed to load WebUI from `%s'\n",
+ dn);
+ GNUNET_free (dn);
+ return GNUNET_SYSERR;
+ }
+ GNUNET_free (dn);
+ return GNUNET_OK;
+}
+
+
+/**
+ * Nicely shut down.
+ */
+void __attribute__ ((destructor))
+get_spa_fini ()
+{
+ struct WebuiFile *w;
+
+ while (NULL != (w = webui_head))
+ {
+ GNUNET_CONTAINER_DLL_remove (webui_head,
+ webui_tail,
+ w);
+ if (NULL != w->spa)
+ {
+ MHD_destroy_response (w->spa);
+ w->spa = NULL;
+ }
+ if (NULL != w->zspa)
+ {
+ MHD_destroy_response (w->zspa);
+ w->zspa = NULL;
+ }
+ GNUNET_free (w->path);
+ GNUNET_free (w);
+ }
+}
diff --git a/src/exchange/taler-exchange-httpd_spa.h b/src/exchange/taler-exchange-httpd_spa.h
new file mode 100644
index 000000000..4147a853b
--- /dev/null
+++ b/src/exchange/taler-exchange-httpd_spa.h
@@ -0,0 +1,49 @@
+/*
+ This file is part of TALER
+ Copyright (C) 2023 Taler Systems SA
+
+ TALER is free software; you can redistribute it and/or modify it under the
+ terms of the GNU General Public License as published by the Free Software
+ Foundation; either version 3, or (at your option) any later version.
+
+ TALER is distributed in the hope that it will be useful, but WITHOUT ANY
+ WARRANTY; without even the implied warranty of EXCHANGEABILITY or FITNESS FOR
+ A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License along with
+ TALER; see the file COPYING. If not, see <http://www.gnu.org/licenses/>
+*/
+/**
+ * @file taler-exchange-httpd_spa.h
+ * @brief logic to preload and serve static files
+ * @author Christian Grothoff
+ */
+#ifndef TALER_EXCHANGE_HTTPD_SPA_H
+#define TALER_EXCHANGE_HTTPD_SPA_H
+
+#include <microhttpd.h>
+#include "taler-exchange-httpd.h"
+
+
+/**
+ * Return our single-page-app user interface (see contrib/wallet-core/).
+ *
+ * @param rc context of the handler
+ * @param[in,out] args remaining arguments (ignored)
+ * @return #MHD_YES on success (reply queued), #MHD_NO on error (close connection)
+ */
+MHD_RESULT
+TEH_handler_spa (struct TEH_RequestContext *rc,
+ const char *const args[]);
+
+
+/**
+ * Preload and compress SPA files.
+ *
+ * @return #GNUNET_OK on success
+ */
+enum GNUNET_GenericReturnValue
+TEH_spa_init (void);
+
+
+#endif
diff --git a/src/exchangedb/exchange_do_insert_aml_decision.sql b/src/exchangedb/exchange_do_insert_aml_decision.sql
index 1598a4073..c8ed7e928 100644
--- a/src/exchangedb/exchange_do_insert_aml_decision.sql
+++ b/src/exchangedb/exchange_do_insert_aml_decision.sql
@@ -32,7 +32,7 @@ AS $$
BEGIN
-- Check officer is eligible to make decisions.
PERFORM
- FROM exchange.aml_staff
+ FROM aml_staff
WHERE decider_pub=in_decider_pub
AND is_active
AND NOT read_only;
@@ -47,7 +47,7 @@ out_invalid_officer=FALSE;
-- Check no more recent decision exists.
SELECT decision_time
INTO out_last_date
- FROM exchange.aml_history
+ FROM aml_history
WHERE h_payto=in_h_payto
ORDER BY decision_time DESC;
IF FOUND
@@ -57,7 +57,7 @@ THEN
-- Refuse to insert older decision.
RETURN;
END IF;
- UPDATE exchange.aml_status
+ UPDATE aml_status
SET threshold=in_new_threshold
,status=in_new_status
,kyc_requirement=in_requirement_row
@@ -65,7 +65,7 @@ THEN
ASSERT FOUND, 'cannot have AML decision history but no AML status';
ELSE
out_last_date = 0;
- INSERT INTO exchange.aml_status
+ INSERT INTO aml_status
(h_payto
,threshold
,status
@@ -74,11 +74,15 @@ ELSE
(in_h_payto
,in_new_threshold
,in_new_status
- ,in_requirement_row);
+ ,in_requirement_row)
+ ON CONFLICT (h_payto) DO
+ UPDATE SET
+ threshold=in_new_threshold
+ ,status=in_new_status;
END IF;
-INSERT INTO exchange.aml_history
+INSERT INTO aml_history
(h_payto
,new_threshold
,new_status
diff --git a/src/exchangedb/pg_trigger_aml_process.c b/src/exchangedb/pg_trigger_aml_process.c
index 0450eb713..7534fe3df 100644
--- a/src/exchangedb/pg_trigger_aml_process.c
+++ b/src/exchangedb/pg_trigger_aml_process.c
@@ -46,12 +46,12 @@ TEH_PG_trigger_aml_process (
"(h_payto"
",threshold"
",status)"
- "VALUES"
- "($1, $2, 1)" // 1: decision needed
- "ON CONFLICT DO"
+ " VALUES"
+ " ($1, $2, 1)" // 1: decision needed
+ " ON CONFLICT (h_payto) DO"
" UPDATE SET"
" threshold=$2"
- " ,status=status | 1;"); // do not clear 'frozen' status
+ " ,status=aml_status.status | 1;"); // do not clear 'frozen' status
return GNUNET_PQ_eval_prepared_non_select (pg->conn,
"trigger_aml_process",
params);
diff --git a/src/include/taler_crypto_lib.h b/src/include/taler_crypto_lib.h
index d8094434c..65a28d715 100644
--- a/src/include/taler_crypto_lib.h
+++ b/src/include/taler_crypto_lib.h
@@ -50,6 +50,54 @@
#define TALER_CNC_KAPPA_MINUS_ONE_STR "2"
+/**
+ * Possible AML decision states.
+ */
+enum TALER_AmlDecisionState
+{
+
+ /**
+ * All AML requirements are currently satisfied.
+ */
+ TALER_AML_NORMAL = 0,
+
+ /**
+ * An AML investigation is pending.
+ */
+ TALER_AML_PENDING = 1,
+
+ /**
+ * An AML decision has concluded that the funds must be frozen.
+ */
+ TALER_AML_FROZEN = 2
+
+};
+
+
+/**
+ * Possible algorithms for confirmation code generation.
+ */
+enum TALER_MerchantConfirmationAlgorithm
+{
+
+ /**
+ * No purchase confirmation.
+ */
+ TALER_MCA_NONE = 0,
+
+ /**
+ * Purchase confirmation without payment
+ */
+ TALER_MCA_WITHOUT_PRICE = 1,
+
+ /**
+ * Purchase confirmation with payment
+ */
+ TALER_MCA_WITH_PRICE = 2
+
+};
+
+
/* ****************** Coin crypto primitives ************* */
GNUNET_NETWORK_STRUCT_BEGIN
@@ -562,54 +610,6 @@ struct TALER_AmlOfficerSignatureP
/**
- * Possible AML decision states.
- */
-enum TALER_AmlDecisionState
-{
-
- /**
- * All AML requirements are currently satisfied.
- */
- TALER_AML_NORMAL = 0,
-
- /**
- * An AML investigation is pending.
- */
- TALER_AML_PENDING = 1,
-
- /**
- * An AML decision has concluded that the funds must be frozen.
- */
- TALER_AML_FROZEN = 2
-
-};
-
-
-/**
- * Possible algorithms for confirmation code generation.
- */
-enum TALER_MerchantConfirmationAlgorithm
-{
-
- /**
- * No purchase confirmation.
- */
- TALER_MCA_NONE = 0,
-
- /**
- * Purchase confirmation without payment
- */
- TALER_MCA_WITHOUT_PRICE = 1,
-
- /**
- * Purchase confirmation with payment
- */
- TALER_MCA_WITH_PRICE = 2
-
-};
-
-
-/**
* Commitment value for the refresh protocol.
* See #TALER_refresh_get_commitment().
*/
diff --git a/src/include/taler_util.h b/src/include/taler_util.h
index 1ca019b99..19dc84fc0 100644
--- a/src/include/taler_util.h
+++ b/src/include/taler_util.h
@@ -242,12 +242,6 @@ struct TALER_CurrencySpecification
unsigned int num_fractional_trailing_zero_digits;
/**
- * True to put the currency symbol before the number,
- * false to put the currency symbol after the number.
- */
- bool is_currency_name_leading;
-
- /**
* Mapping of powers of 10 to alternative currency names or symbols.
* Keys are the decimal powers, values the currency symbol to use.
* Map MUST contain an entry for "0" to the default currency symbol.
diff --git a/src/json/json_helper.c b/src/json/json_helper.c
index 71291a9e5..fd2a8d272 100644
--- a/src/json/json_helper.c
+++ b/src/json/json_helper.c
@@ -179,8 +179,6 @@ parse_cspec (void *cls,
&fnd),
GNUNET_JSON_spec_uint32 ("num_fractional_trailing_zero_digits",
&ftzd),
- GNUNET_JSON_spec_bool ("is_currency_name_leading",
- &r_cspec->is_currency_name_leading),
GNUNET_JSON_spec_object_const ("alt_unit_names",
&map),
GNUNET_JSON_spec_end ()
diff --git a/src/kyclogic/plugin_kyclogic_kycaid.c b/src/kyclogic/plugin_kyclogic_kycaid.c
index 10f9658fe..d7fddab4b 100644
--- a/src/kyclogic/plugin_kyclogic_kycaid.c
+++ b/src/kyclogic/plugin_kyclogic_kycaid.c
@@ -917,12 +917,6 @@ handle_webhook_finished (void *cls,
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Webhook returned with HTTP status %u\n",
(unsigned int) response_code);
-#if 1
- if (NULL != j)
- json_dumpf (j,
- stderr,
- JSON_INDENT (2));
-#endif
wh->kycaid_response_code = response_code;
wh->json_response = json_incref ((json_t *) j);
switch (response_code)
diff --git a/src/lib/exchange_api_stefan.c b/src/lib/exchange_api_stefan.c
index c3576cd73..226bca82f 100644
--- a/src/lib/exchange_api_stefan.c
+++ b/src/lib/exchange_api_stefan.c
@@ -299,22 +299,30 @@ TALER_EXCHANGE_keys_stefan_round (
struct TALER_Amount *val)
{
const struct TALER_Amount *min;
- uint32_t mod = 1;
+ uint32_t mod;
uint32_t frac;
- uint32_t rst;
+ uint32_t lim;
+ if (0 == val->fraction)
+ {
+ /* rounding of non-fractions not supported */
+ return;
+ }
min = get_unit (keys);
if (NULL == min)
return;
- frac = min->fraction;
- while (0 == frac % 10)
+ if (0 == min->fraction)
+ {
+ frac = TALER_AMOUNT_FRAC_BASE;
+ }
+ else
{
- mod *= 10;
- frac /= 10;
+ frac = min->fraction;
}
- rst = val->fraction % mod;
- if (rst < mod / 2)
- val->fraction -= rst;
+ lim = frac / 2;
+ mod = val->fraction % frac;
+ if (mod < lim)
+ val->fraction -= mod; /* round down */
else
- val->fraction += mod - rst;
+ val->fraction += frac - mod; /* round up */
}
diff --git a/src/templating/templating_api.c b/src/templating/templating_api.c
index efe020761..3bda7de55 100644
--- a/src/templating/templating_api.c
+++ b/src/templating/templating_api.c
@@ -100,7 +100,7 @@ lookup_template (struct MHD_Connection *connection,
if (NULL == best)
{
GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "No templates found in `%s'\n",
+ "No templates found for `%s'\n",
name);
return NULL;
}
@@ -360,7 +360,6 @@ load_template (void *cls,
(void) cls;
if ('.' == filename[0])
return GNUNET_OK;
-
name = strrchr (filename,
'/');
if (NULL == name)
@@ -395,7 +394,7 @@ load_template (void *cls,
&sb))
{
GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR,
- "open",
+ "fstat",
filename);
GNUNET_break (0 == close (fd));
return GNUNET_OK;
diff --git a/src/testing/taler-unified-setup.sh b/src/testing/taler-unified-setup.sh
index 13b715503..479a125fa 100755
--- a/src/testing/taler-unified-setup.sh
+++ b/src/testing/taler-unified-setup.sh
@@ -260,9 +260,13 @@ register_bank_account() {
}
register_fakebank_account() {
- # FIXME: may need to pass 'is_taler_exchange' here
- # in the future to get exchange facade from libeufin!
- BODY='{"username":"'"$1"'","password":"'"$2"'","name":"'"$1"'"}'
+ if [ "$1" = "exchange" ] || [ "$1" = "Exchange" ]
+ then
+ IS_EXCHANGE="true"
+ else
+ IS_EXCHANGE="false"
+ fi
+ BODY='{"username":"'"$1"'","password":"'"$2"'","name":"'"$1"'","is_taler_exchange":'"$IS_EXCHANGE"'}'
wget \
--post-data="$BODY" \
--header='Content-type: application/json' \
@@ -270,6 +274,7 @@ register_fakebank_account() {
--waitretry=1 \
--timeout=30 \
"http://localhost:$BANK_PORT/accounts" \
+ -a wget-register-account.log \
-o /dev/null \
-O /dev/null \
>/dev/null
@@ -705,18 +710,19 @@ then
sleep "$DEFAULT_SLEEP"
wget \
--tries=1 \
- --timeout=1 \
+ --timeout=5 \
"${EXCHANGE_URL}keys" \
+ -a wget-keys-check.log \
-o /dev/null \
-O "$LAST_RESPONSE" \
- >/dev/null || continue
+ >/dev/null || continue
OK="1"
break
done
if [ "1" != "$OK" ]
then
cat "$LAST_RESPONSE"
- exit_fail " Failed to setup keys"
+ exit_fail " Failed to fetch ${EXCHANGE_URL}keys"
fi
rm "$LAST_RESPONSE"
echo " OK"
diff --git a/src/util/config.c b/src/util/config.c
index e22207f77..205670431 100644
--- a/src/util/config.c
+++ b/src/util/config.c
@@ -233,11 +233,6 @@ parse_currencies_cb (void *cls,
cpc->len_cspecs * 2 + 4);
}
cspec = &cpc->cspecs[cpc->num_currencies++];
- cspec->is_currency_name_leading
- = GNUNET_CONFIGURATION_get_value_yesno (cpc->cfg,
- section,
- "NAME_LEADING");
-
if (GNUNET_OK !=
GNUNET_CONFIGURATION_get_value_string (cpc->cfg,
section,
@@ -483,8 +478,6 @@ TALER_CONFIG_currency_specs_to_json (const struct
cspec->num_fractional_normal_digits),
GNUNET_JSON_pack_uint64 ("num_fractional_trailing_zero_digits",
cspec->num_fractional_trailing_zero_digits),
- GNUNET_JSON_pack_bool ("is_currency_name_leading",
- cspec->is_currency_name_leading),
GNUNET_JSON_pack_object_incref ("alt_unit_names",
cspec->map_alt_unit_names));
}
diff --git a/src/util/currencies.conf b/src/util/currencies.conf
index 539804fc2..5f4fcbe60 100644
--- a/src/util/currencies.conf
+++ b/src/util/currencies.conf
@@ -5,7 +5,6 @@ code = "EUR"
fractional_input_digits = 2
fractional_normal_digits = 2
fractional_trailing_zero_digits = 2
-is_currency_name_leading = NO
alt_unit_names = {"0":"€"}
[currency-swiss-francs]
@@ -15,7 +14,6 @@ code = "CHF"
fractional_input_digits = 2
fractional_normal_digits = 2
fractional_trailing_zero_digits = 2
-is_currency_name_leading = YES
alt_unit_names = {"0":"Fr.","-2":"Rp."}
[currency-forint]
@@ -25,7 +23,6 @@ code = "HUF"
fractional_input_digits = 0
fractional_normal_digits = 0
fractional_trailing_zero_digits = 0
-is_currency_name_leading = NO
alt_unit_names = {"0":"Ft"}
[currency-us-dollar]
@@ -35,7 +32,6 @@ code = "USD"
fractional_input_digits = 2
fractional_normal_digits = 2
fractional_trailing_zero_digits = 2
-is_currency_name_leading = YES
alt_unit_names = {"0":"$"}
[currency-kudos]
@@ -45,7 +41,6 @@ code = "KUDOS"
fractional_input_digits = 2
fractional_normal_digits = 2
fractional_trailing_zero_digits = 2
-is_currency_name_leading = NO
alt_unit_names = {"0":"ク"}
[currency-testkudos]
@@ -55,7 +50,6 @@ code = "TESTKUDOS"
fractional_input_digits = 2
fractional_normal_digits = 2
fractional_trailing_zero_digits = 2
-is_currency_name_leading = NO
alt_unit_names = {"0":"テ","3":"kテ","-3":"mテ"}
[currency-japanese-yen]
@@ -65,7 +59,6 @@ code = "JPY"
fractional_input_digits = 2
fractional_normal_digits = 0
fractional_trailing_zero_digits = 2
-is_currency_name_leading = YES
alt_unit_names = {"0":"¥"}
[currency-bitcoin-mainnet]
@@ -75,7 +68,6 @@ code = "BITCOINBTC"
fractional_input_digits = 8
fractional_normal_digits = 3
fractional_trailing_zero_digits = 0
-is_currency_name_leading = NO
alt_unit_names = {"0":"BTC","-3":"mBTC"}
[currency-ethereum]
@@ -85,5 +77,4 @@ code = "EthereumWAI"
fractional_input_digits = 0
fractional_normal_digits = 0
fractional_trailing_zero_digits = 0
-is_currency_name_leading = NO
alt_unit_names = {"0":"WAI","3":"KWAI","6":"MWAI","9":"GWAI","12":"Szabo","15":"Finney","18":"Ether","21":"KEther","24":"MEther"}
diff --git a/src/util/paths.conf b/src/util/paths.conf
index 9e1c53bb7..f34ccb41e 100644
--- a/src/util/paths.conf
+++ b/src/util/paths.conf
@@ -17,13 +17,13 @@ TALER_HOME = ${TALER_TEST_HOME:-${HOME:-${USERPROFILE}}}
# for how these should be used.
# Persistent data storage
-TALER_DATA_HOME = ${TALER_TEST_HOME:-${XDG_DATA_HOME:-${TALER_HOME}}}/.local/share/taler/
+TALER_DATA_HOME = ${XDG_DATA_HOME:-${TALER_HOME}/.local/share}/taler/
# Configuration files
-TALER_CONFIG_HOME = ${TALER_TEST_HOME:-${XDG_CONFIG_HOME:-${TALER_HOME}}}/.config/taler/
+TALER_CONFIG_HOME = ${XDG_CONFIG_HOME:-${TALER_HOME}/.config}/taler/
# Cached data, no big deal if lost
-TALER_CACHE_HOME = ${TALER_TEST_HOME:-${XDG_CACHE_HOME:-${TALER_HOME}}}/.cache/taler/
+TALER_CACHE_HOME = ${XDG_CACHE_HOME:-${TALER_HOME}/.cache}/taler/
# Runtime data (always lost on system boot)
TALER_RUNTIME_DIR = ${TMPDIR:-${TMP:-/tmp}}/taler-system-runtime/