summaryrefslogtreecommitdiff
path: root/src/backend/taler-merchant-httpd_private-post-instances.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/backend/taler-merchant-httpd_private-post-instances.c')
-rw-r--r--src/backend/taler-merchant-httpd_private-post-instances.c311
1 files changed, 93 insertions, 218 deletions
diff --git a/src/backend/taler-merchant-httpd_private-post-instances.c b/src/backend/taler-merchant-httpd_private-post-instances.c
index 58a93b27..a4cf884d 100644
--- a/src/backend/taler-merchant-httpd_private-post-instances.c
+++ b/src/backend/taler-merchant-httpd_private-post-instances.c
@@ -1,6 +1,6 @@
/*
This file is part of TALER
- (C) 2020, 2021 Taler Systems SA
+ (C) 2020-2023 Taler Systems SA
TALER is free software; you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as
@@ -25,6 +25,8 @@
#include "platform.h"
#include "taler-merchant-httpd_private-post-instances.h"
#include "taler-merchant-httpd_helper.h"
+#include "taler_merchant_bank_lib.h"
+#include <taler/taler_dbevents.h>
#include <taler/taler_json_lib.h>
#include <regex.h>
@@ -35,104 +37,6 @@
/**
- * Check if the array of @a payto_uris contains exactly the same
- * URIs as those already in @a mi (possibly in a different order).
- *
- * @param mi a merchant instance with accounts
- * @param payto_uris a JSON array with accounts (presumably)
- * @return true if they are 'equal', false if not or of payto_uris is not an array
- */
-static bool
-accounts_equal (const struct TMH_MerchantInstance *mi,
- json_t *payto_uris)
-{
- if (! json_is_array (payto_uris))
- return false;
- {
- unsigned int len = json_array_size (payto_uris);
- bool matches[GNUNET_NZL (len)];
- struct TMH_WireMethod *wm;
-
- memset (matches,
- 0,
- sizeof (matches));
- for (wm = mi->wm_head;
- NULL != wm;
- wm = wm->next)
- {
- const char *uri = wm->payto_uri;
-
- GNUNET_assert (NULL != uri);
- for (unsigned int i = 0; i<len; i++)
- {
- const char *str = json_string_value (json_array_get (payto_uris,
- i));
-
- GNUNET_assert (NULL != str);
- if (0 == strcasecmp (uri,
- str))
- {
- if (matches[i])
- {
- GNUNET_break (0);
- return false; /* duplicate entry!? */
- }
- matches[i] = true;
- break;
- }
- }
- }
- for (unsigned int i = 0; i<len; i++)
- if (! matches[i])
- return false;
- }
- return true;
-}
-
-
-/**
- * Free memory used by @a wm
- *
- * @param wm wire method to free
- */
-static void
-free_wm (struct TMH_WireMethod *wm)
-{
- GNUNET_free (wm->payto_uri);
- GNUNET_free (wm->wire_method);
- GNUNET_free (wm);
-}
-
-
-/**
- * Free memory used by @a mi.
- *
- * @param mi instance to free
- */
-static void
-free_mi (struct TMH_MerchantInstance *mi)
-{
- struct TMH_WireMethod *wm;
-
- while (NULL != (wm = mi->wm_head))
- {
- GNUNET_CONTAINER_DLL_remove (mi->wm_head,
- mi->wm_tail,
- wm);
- free_wm (wm);
- }
- GNUNET_free (mi->settings.id);
- GNUNET_free (mi->settings.name);
- GNUNET_free (mi->settings.website);
- GNUNET_free (mi->settings.email);
- GNUNET_free (mi->settings.logo);
- json_decref (mi->settings.address);
- json_decref (mi->settings.jurisdiction);
- GNUNET_free (mi);
-}
-
-
-/**
* Generate an instance, given its configuration.
*
* @param rh context of the handler
@@ -145,46 +49,42 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
struct MHD_Connection *connection,
struct TMH_HandlerContext *hc)
{
- struct TALER_MERCHANTDB_InstanceSettings is;
+ struct TALER_MERCHANTDB_InstanceSettings is = { 0 };
struct TALER_MERCHANTDB_InstanceAuthSettings ias;
- json_t *payto_uris;
const char *auth_token = NULL;
+ const char *uts = "business";
struct TMH_WireMethod *wm_head = NULL;
struct TMH_WireMethod *wm_tail = NULL;
- json_t *jauth;
+ const json_t *jauth;
struct GNUNET_JSON_Specification spec[] = {
- GNUNET_JSON_spec_json ("payto_uris",
- &payto_uris),
GNUNET_JSON_spec_string ("id",
(const char **) &is.id),
GNUNET_JSON_spec_string ("name",
(const char **) &is.name),
- GNUNET_JSON_spec_mark_optional(
+ GNUNET_JSON_spec_mark_optional (
+ GNUNET_JSON_spec_string ("user_type",
+ &uts),
+ NULL),
+ GNUNET_JSON_spec_mark_optional (
GNUNET_JSON_spec_string ("email",
(const char **) &is.email),
NULL),
- GNUNET_JSON_spec_mark_optional(
+ GNUNET_JSON_spec_mark_optional (
GNUNET_JSON_spec_string ("website",
(const char **) &is.website),
NULL),
- GNUNET_JSON_spec_mark_optional(
+ GNUNET_JSON_spec_mark_optional (
GNUNET_JSON_spec_string ("logo",
(const char **) &is.logo),
NULL),
- GNUNET_JSON_spec_json ("auth",
- &jauth),
+ GNUNET_JSON_spec_object_const ("auth",
+ &jauth),
GNUNET_JSON_spec_json ("address",
&is.address),
GNUNET_JSON_spec_json ("jurisdiction",
&is.jurisdiction),
- TALER_JSON_spec_amount ("default_max_wire_fee",
- TMH_currency,
- &is.default_max_wire_fee),
- GNUNET_JSON_spec_uint32 ("default_wire_fee_amortization",
- &is.default_wire_fee_amortization),
- TALER_JSON_spec_amount ("default_max_deposit_fee",
- TMH_currency,
- &is.default_max_deposit_fee),
+ GNUNET_JSON_spec_bool ("use_stefan",
+ &is.use_stefan),
GNUNET_JSON_spec_relative_time ("default_wire_transfer_delay",
&is.default_wire_transfer_delay),
GNUNET_JSON_spec_relative_time ("default_pay_delay",
@@ -203,6 +103,19 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
? MHD_YES
: MHD_NO;
}
+ if (NULL == uts)
+ uts = "business";
+ if (GNUNET_OK !=
+ TALER_KYCLOGIC_kyc_user_type_from_string (uts,
+ &is.ut))
+ {
+ GNUNET_break_op (0);
+ GNUNET_JSON_parse_free (spec);
+ return TALER_MHD_reply_with_error (connection,
+ MHD_HTTP_BAD_REQUEST,
+ TALER_EC_GENERIC_PARAMETER_MALFORMED,
+ "user_type");
+ }
{
enum GNUNET_GenericReturnValue ret;
@@ -211,16 +124,12 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
jauth,
&auth_token);
if (GNUNET_OK != ret)
+ {
+ GNUNET_JSON_parse_free (spec);
return (GNUNET_NO == ret) ? MHD_YES : MHD_NO;
+ }
}
- /* check payto_uris for well-formedness */
- if (! TMH_payto_uri_array_valid (payto_uris))
- return TALER_MHD_reply_with_error (connection,
- MHD_HTTP_BAD_REQUEST,
- TALER_EC_GENERIC_PAYTO_URI_MALFORMED,
- NULL);
-
/* check 'id' well-formed */
{
static bool once;
@@ -229,6 +138,7 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
if (! once)
{
+ once = true;
GNUNET_assert (0 ==
regcomp (&reg,
"^[A-Za-z0-9][A-Za-z0-9_.@-]+$",
@@ -240,10 +150,13 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
0, NULL, 0))
id_wellformed = false;
if (! id_wellformed)
+ {
+ GNUNET_JSON_parse_free (spec);
return TALER_MHD_reply_with_error (connection,
MHD_HTTP_BAD_REQUEST,
TALER_EC_GENERIC_PARAMETER_MALFORMED,
"id");
+ }
}
if (! TMH_location_object_valid (is.address))
@@ -297,18 +210,18 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
is.id)) &&
(0 == strcmp (mi->settings.name,
is.name)) &&
- ((mi->settings.email == is.email) ||
- (NULL != is.email && NULL != mi->settings.email &&
- 0 == strcmp (mi->settings.email,
- is.email))) &&
- ((mi->settings.website == is.website) ||
- (NULL != is.website && NULL != mi->settings.website &&
- 0 == strcmp (mi->settings.website,
- is.website))) &&
- ((mi->settings.logo == is.logo) ||
- (NULL != is.logo && NULL != mi->settings.logo &&
- 0 == strcmp (mi->settings.logo,
- is.logo))) &&
+ ((mi->settings.email == is.email) ||
+ (NULL != is.email && NULL != mi->settings.email &&
+ 0 == strcmp (mi->settings.email,
+ is.email))) &&
+ ((mi->settings.website == is.website) ||
+ (NULL != is.website && NULL != mi->settings.website &&
+ 0 == strcmp (mi->settings.website,
+ is.website))) &&
+ ((mi->settings.logo == is.logo) ||
+ (NULL != is.logo && NULL != mi->settings.logo &&
+ 0 == strcmp (mi->settings.logo,
+ is.logo))) &&
( ( (NULL != auth_token) &&
(GNUNET_OK ==
TMH_check_auth (auth_token,
@@ -321,26 +234,13 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
is.address)) &&
(1 == json_equal (mi->settings.jurisdiction,
is.jurisdiction)) &&
- (GNUNET_OK == TALER_amount_cmp_currency (
- &mi->settings.default_max_deposit_fee,
- &is.default_max_deposit_fee)) &&
- (0 == TALER_amount_cmp (&mi->settings.default_max_deposit_fee,
- &is.default_max_deposit_fee)) &&
- (GNUNET_OK == TALER_amount_cmp_currency (
- &mi->settings.default_max_wire_fee,
- &is.default_max_wire_fee)) &&
- (0 == TALER_amount_cmp (&mi->settings.default_max_wire_fee,
- &is.default_max_wire_fee)) &&
- (mi->settings.default_wire_fee_amortization ==
- is.default_wire_fee_amortization) &&
+ (mi->settings.use_stefan == is.use_stefan) &&
(GNUNET_TIME_relative_cmp (mi->settings.default_wire_transfer_delay,
==,
is.default_wire_transfer_delay)) &&
(GNUNET_TIME_relative_cmp (mi->settings.default_pay_delay,
==,
- is.default_pay_delay)) &&
- (accounts_equal (mi,
- payto_uris)) )
+ is.default_pay_delay)) )
{
GNUNET_JSON_parse_free (spec);
return TALER_MHD_reply_static (connection,
@@ -349,31 +249,11 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
NULL,
0);
}
- else
- {
- GNUNET_JSON_parse_free (spec);
- return TALER_MHD_reply_with_error (connection,
- MHD_HTTP_CONFLICT,
- TALER_EC_MERCHANT_PRIVATE_POST_INSTANCES_ALREADY_EXISTS,
- is.id);
- }
- }
- }
-
- /* convert provided payto URIs into internal data structure with salts */
- {
- unsigned int len = json_array_size (payto_uris);
-
- for (unsigned int i = 0; i<len; i++)
- {
- json_t *payto_uri = json_array_get (payto_uris,
- i);
- struct TMH_WireMethod *wm;
-
- wm = TMH_setup_wire_account (json_string_value (payto_uri));
- GNUNET_CONTAINER_DLL_insert (wm_head,
- wm_tail,
- wm);
+ GNUNET_JSON_parse_free (spec);
+ return TALER_MHD_reply_with_error (connection,
+ MHD_HTTP_CONFLICT,
+ TALER_EC_MERCHANT_PRIVATE_POST_INSTANCES_ALREADY_EXISTS,
+ is.id);
}
}
@@ -425,8 +305,8 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
TMH_db->start (TMH_db->cls,
"post /instances"))
{
- GNUNET_JSON_parse_free (spec);
- free_mi (mi);
+ mi->rc = 1;
+ TMH_instance_decref (mi);
return TALER_MHD_reply_with_error (connection,
MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_START_FAILED,
@@ -437,45 +317,41 @@ TMH_private_post_instances (const struct TMH_RequestHandler *rh,
&mi->merchant_priv,
&mi->settings,
&mi->auth);
- if (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != qs)
- {
- MHD_RESULT ret;
-
- TMH_db->rollback (TMH_db->cls);
- if (GNUNET_DB_STATUS_SOFT_ERROR == qs)
- goto retry;
- ret = TALER_MHD_reply_with_error (connection,
- MHD_HTTP_CONFLICT,
- TALER_EC_MERCHANT_PRIVATE_POST_INSTANCES_ALREADY_EXISTS,
- is.id);
- GNUNET_JSON_parse_free (spec);
- free_mi (mi);
- return ret;
- }
- for (struct TMH_WireMethod *wm = wm_head;
- NULL != wm;
- wm = wm->next)
- {
- struct TALER_MERCHANTDB_AccountDetails ad = {
- .payto_uri = wm->payto_uri,
- .salt = wm->wire_salt,
- .h_wire = wm->h_wire,
- .active = wm->active
- };
-
- qs = TMH_db->insert_account (TMH_db->cls,
- mi->settings.id,
- &ad);
- if (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != qs)
- break;
- }
- if (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != qs)
+ switch (qs)
{
- GNUNET_break (GNUNET_DB_STATUS_SOFT_ERROR == qs);
- TMH_db->rollback (TMH_db->cls);
- if (GNUNET_DB_STATUS_HARD_ERROR == qs)
- break;
+ case GNUNET_DB_STATUS_HARD_ERROR:
+ {
+ MHD_RESULT ret;
+
+ TMH_db->rollback (TMH_db->cls);
+ GNUNET_break (0);
+ ret = TALER_MHD_reply_with_error (connection,
+ MHD_HTTP_INTERNAL_SERVER_ERROR,
+ TALER_EC_GENERIC_DB_STORE_FAILED,
+ is.id);
+ mi->rc = 1;
+ TMH_instance_decref (mi);
+ return ret;
+ }
+ case GNUNET_DB_STATUS_SOFT_ERROR:
goto retry;
+ case GNUNET_DB_STATUS_SUCCESS_NO_RESULTS:
+ {
+ MHD_RESULT ret;
+
+ TMH_db->rollback (TMH_db->cls);
+ GNUNET_break (0);
+ ret = TALER_MHD_reply_with_error (connection,
+ MHD_HTTP_CONFLICT,
+ TALER_EC_MERCHANT_PRIVATE_POST_INSTANCES_ALREADY_EXISTS,
+ is.id);
+ mi->rc = 1;
+ TMH_instance_decref (mi);
+ return ret;
+ }
+ case GNUNET_DB_STATUS_SUCCESS_ONE_RESULT:
+ /* handled below */
+ break;
}
qs = TMH_db->commit (TMH_db->cls);
if (GNUNET_DB_STATUS_SUCCESS_NO_RESULTS == qs)
@@ -486,8 +362,8 @@ retry:
} /* for .. MAX_RETRIES */
if (GNUNET_DB_STATUS_SUCCESS_ONE_RESULT != qs)
{
- GNUNET_JSON_parse_free (spec);
- free_mi (mi);
+ mi->rc = 1;
+ TMH_instance_decref (mi);
return TALER_MHD_reply_with_error (connection,
MHD_HTTP_INTERNAL_SERVER_ERROR,
TALER_EC_GENERIC_DB_COMMIT_FAILED,
@@ -498,7 +374,6 @@ retry:
TMH_add_instance (mi));
TMH_reload_instances (mi->settings.id);
}
- GNUNET_JSON_parse_free (spec);
if (0 == strcmp (is.id,
"default"))
{