commit 4be8fe916b1596ec13339d5f91034b878ef9ace4
parent 3d69f730a23b956614d16aa9ed857c37354033b3
Author: Christian Grothoff <grothoff@gnunet.org>
Date: Tue, 5 Sep 2023 23:07:53 +0200
auth token skeleton logic
Diffstat:
9 files changed, 332 insertions(+), 150 deletions(-)
diff --git a/src/backend/Makefile.am b/src/backend/Makefile.am
@@ -35,11 +35,14 @@ taler_merchant_httpd_SOURCES = \
taler-merchant-httpd_private-get-rewards.h \
taler-merchant-httpd_private-get-rewards-ID.c \
taler-merchant-httpd_private-get-rewards-ID.h \
- taler-merchant-httpd_mhd.c taler-merchant-httpd_mhd.h \
+ taler-merchant-httpd_mhd.c \
+ taler-merchant-httpd_mhd.h \
taler-merchant-httpd_private-delete-account-ID.c \
taler-merchant-httpd_private-delete-account-ID.h \
taler-merchant-httpd_private-delete-instances-ID.c \
taler-merchant-httpd_private-delete-instances-ID.h \
+ taler-merchant-httpd_private-delete-instances-ID-token.c \
+ taler-merchant-httpd_private-delete-instances-ID-token.h \
taler-merchant-httpd_private-delete-products-ID.c \
taler-merchant-httpd_private-delete-products-ID.h \
taler-merchant-httpd_private-delete-orders-ID.c \
@@ -110,8 +113,8 @@ taler_merchant_httpd_SOURCES = \
taler-merchant-httpd_private-post-instances.h \
taler-merchant-httpd_private-post-instances-ID-auth.c \
taler-merchant-httpd_private-post-instances-ID-auth.h \
- taler-merchant-httpd_private-post-instances-ID-login.c \
- taler-merchant-httpd_private-post-instances-ID-login.h \
+ taler-merchant-httpd_private-post-instances-ID-token.c \
+ taler-merchant-httpd_private-post-instances-ID-token.h \
taler-merchant-httpd_private-post-orders-ID-refund.c \
taler-merchant-httpd_private-post-orders-ID-refund.h \
taler-merchant-httpd_private-post-orders.c \
diff --git a/src/backend/taler-merchant-httpd.c b/src/backend/taler-merchant-httpd.c
@@ -35,6 +35,7 @@
#include "taler-merchant-httpd_mhd.h"
#include "taler-merchant-httpd_private-delete-account-ID.h"
#include "taler-merchant-httpd_private-delete-instances-ID.h"
+#include "taler-merchant-httpd_private-delete-instances-ID-token.h"
#include "taler-merchant-httpd_private-delete-products-ID.h"
#include "taler-merchant-httpd_private-delete-orders-ID.h"
#include "taler-merchant-httpd_private-delete-otp-devices-ID.h"
@@ -72,7 +73,7 @@
#include "taler-merchant-httpd_private-post-account.h"
#include "taler-merchant-httpd_private-post-instances.h"
#include "taler-merchant-httpd_private-post-instances-ID-auth.h"
-#include "taler-merchant-httpd_private-post-instances-ID-login.h"
+#include "taler-merchant-httpd_private-post-instances-ID-token.h"
#include "taler-merchant-httpd_private-post-otp-devices.h"
#include "taler-merchant-httpd_private-post-orders.h"
#include "taler-merchant-httpd_private-post-orders-ID-refund.h"
@@ -182,6 +183,16 @@ static const struct GNUNET_CONFIGURATION_Handle *cfg;
char *TMH_default_auth;
+enum TMH_AuthScope
+TMH_check_token (const char *token,
+ const char *instance_id)
+{
+ if (NULL == token)
+ return TMH_AS_NONE;
+ GNUNET_break (0); // FIXME: not implemented
+ return TMH_AS_NONE;
+}
+
enum GNUNET_GenericReturnValue
TMH_check_auth (const char *token,
struct TALER_MerchantAuthenticationSaltP *salt,
@@ -754,6 +765,7 @@ url_handler (void *cls,
/* POST /token: */
{
.url_prefix = "/instances/",
+ .auth_scope = TMH_AS_RENEWABLE,
.url_suffix = "token",
.method = MHD_HTTP_METHOD_POST,
.have_id_segment = true,
@@ -761,6 +773,17 @@ url_handler (void *cls,
/* Body should be tiny. */
.max_upload = 1024
},
+#if FUTURE_FIXME
+ /* DELETE /token: */
+ {
+ .url_prefix = "/instances/",
+ .auth_scope = TMH_AS_READ_ONLY,
+ .url_suffix = "token",
+ .method = MHD_HTTP_METHOD_DELETE,
+ .have_id_segment = true,
+ .handler = &TMH_private_delete_instances_ID_auth,
+ },
+#endif
/* POST /kyc: */
{
.url_prefix = "/instances/",
@@ -1753,14 +1776,16 @@ url_handler (void *cls,
if (public_handlers != handlers)
{
const char *auth;
+ const char *tok;
bool auth_ok;
bool auth_malformed = false;
/* PATCHing an instance can alternatively be checked against
the default instance */
- auth = MHD_lookup_connection_value (connection,
- MHD_HEADER_KIND,
- MHD_HTTP_HEADER_AUTHORIZATION);
+ tok = MHD_lookup_connection_value (connection,
+ MHD_HEADER_KIND,
+ MHD_HTTP_HEADER_AUTHORIZATION);
+ auth = tok;
if (NULL != auth)
{
/* We _only_ complain about malformed auth headers if
@@ -1794,9 +1819,23 @@ url_handler (void *cls,
(! auth_malformed) &&
(0 == strcmp (auth,
TMH_default_auth)) );
- if (! auth_ok)
- {
- if (auth_malformed)
+ hc->auth_scope = auth_ok
+ ? TMH_AS_ALL
+ : TMH_check_token (tok,
+ hc->instance->settings.id);
+ /* We grant access if:
+ - scope is 'all'
+ - rh has an explicit non-NONE scope that matches
+ - scope is 'read only' and we have a GET request */
+ if (! ( (TMH_AS_ALL == hc->auth_scope) ||
+ ( (TMH_AS_NONE != hc->rh->auth_scope) &&
+ (hc->rh->auth_scope == (hc->rh->auth_scope & hc->auth_scope)) ) ||
+ ( (TMH_AS_READ_ONLY == hc->auth_scope) &&
+ (0 == strcmp (MHD_HTTP_METHOD_GET,
+ method)) ) ) )
+ {
+ if ( auth_malformed &&
+ (TMH_AS_NONE == hc->auth_scope) )
return TALER_MHD_reply_with_error (connection,
MHD_HTTP_UNAUTHORIZED,
TALER_EC_GENERIC_PARAMETER_MALFORMED,
diff --git a/src/backend/taler-merchant-httpd.h b/src/backend/taler-merchant-httpd.h
@@ -408,6 +408,33 @@ struct TMH_HandlerContext;
/**
+ * Possible authorization scopes. This is a bit mask.
+ */
+enum TMH_AuthScope {
+ /**
+ * Nothing is authorized.
+ */
+ TMH_AS_NONE = 0,
+
+ /**
+ * Read-only access is OK. Any GET request is
+ * automatically OK.
+ */
+ TMH_AS_READ_ONLY = 1,
+
+ /**
+ * /login access to renew the token is OK.
+ */
+ TMH_AS_RENEWABLE = 1 << 30,
+
+ /**
+ * Full access is granted to everything.
+ */
+ TMH_AS_ALL = INT32_MAX
+};
+
+
+/**
* @brief Struct describing an URL and the handler for it.
*
* The overall URL is always @e url_prefix, optionally followed by the
@@ -428,6 +455,13 @@ struct TMH_RequestHandler
const char *url_prefix;
/**
+ * Required authentication scope for this request. NONE implies that
+ * #TMH_AS_ALL is required unless this is a #MHD_HTTP_GET method, in which
+ * case #TMH_AS_READ_ONLY is sufficient.
+ */
+ enum TMH_AuthScope auth_scope;
+
+ /**
* Does this request include an identifier segment
* (product_id, reserve_pub, order_id, reward_id, template_id, webhook_id) in the
* second segment?
@@ -584,6 +618,12 @@ struct TMH_HandlerContext
uint64_t total_upload;
/**
+ * Actual authentication scope of this request.
+ * Only set for ``/private/`` requests.
+ */
+ enum TMH_AuthScope auth_scope;
+
+ /**
* Set to true if this is an #MHD_HTTP_METHOD_POST or #MHD_HTTP_METHOD_PATCH request.
* (In principle #MHD_HTTP_METHOD_PUT may also belong, but we do not have PUTs
* in the API today, so we do not test for PUT.)
diff --git a/src/backend/taler-merchant-httpd_private-delete-instances-ID-token.c b/src/backend/taler-merchant-httpd_private-delete-instances-ID-token.c
@@ -0,0 +1,54 @@
+/*
+ This file is part of GNU Taler
+ (C) 2023 Taler Systems SA
+
+ GNU Taler is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Affero General Public License as
+ published by the Free Software Foundation; either version 3,
+ or (at your option) any later version.
+
+ GNU Taler is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY 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-merchant-httpd_private-post-instances-ID-token.c
+ * @brief implementing DELETE /instances/$ID/token request handling
+ * @author Christian Grothoff
+ */
+#include "platform.h"
+#include "taler-merchant-httpd_private-delete-instances-ID-token.h"
+#include "taler-merchant-httpd_helper.h"
+#include <taler/taler_json_lib.h>
+
+
+MHD_RESULT
+TMH_private_delete_instances_ID_token (const struct TMH_RequestHandler *rh,
+ struct MHD_Connection *connection,
+ struct TMH_HandlerContext *hc)
+{
+ struct TMH_MerchantInstance *mi = hc->instance;
+ const char *tok;
+
+ tok = MHD_lookup_connection_value (connection,
+ MHD_HEADER_KIND,
+ MHD_HTTP_HEADER_AUTHORIZATION);
+ GNUNET_break (0); // FIXME: not implemented
+ (void) tok;
+ (void) mi;
+
+ return TALER_MHD_reply_static (connection,
+ MHD_HTTP_NO_CONTENT,
+ NULL,
+ NULL,
+ 0);
+}
+
+
+/* end of taler-merchant-httpd_private-delete-instances-ID-login.c */
diff --git a/src/backend/taler-merchant-httpd_private-delete-instances-ID-token.h b/src/backend/taler-merchant-httpd_private-delete-instances-ID-token.h
@@ -0,0 +1,45 @@
+/*
+ This file is part of GNU Taler
+ (C) 2023 Taler Systems SA
+
+ GNU Taler is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Affero General Public License as
+ published by the Free Software Foundation; either version 3,
+ or (at your option) any later version.
+
+ GNU Taler is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY 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-merchant-httpd_private-delete-instances-ID-token.h
+ * @brief implements DELETE /instances/$ID/token request handling
+ * @author Christian Grothoff
+ */
+#ifndef TALER_MERCHANT_HTTPD_PRIVATE_DELETE_INSTANCES_ID_TOKEN_H
+#define TALER_MERCHANT_HTTPD_PRIVATE_DELETE_INSTANCES_ID_TOKEN_H
+#include "taler-merchant-httpd.h"
+
+
+/**
+ * Delete login token for an instance.
+ *
+ * @param rh context of the handler
+ * @param connection the MHD connection to handle
+ * @param[in,out] hc context with further information about the request
+ * @return MHD result code
+ */
+MHD_RESULT
+TMH_private_delete_instances_ID_token (
+ const struct TMH_RequestHandler *rh,
+ struct MHD_Connection *connection,
+ struct TMH_HandlerContext *hc);
+
+
+#endif
diff --git a/src/backend/taler-merchant-httpd_private-post-instances-ID-login.c b/src/backend/taler-merchant-httpd_private-post-instances-ID-login.c
@@ -1,96 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2023 Taler Systems SA
-
- GNU Taler is free software; you can redistribute it and/or modify
- it under the terms of the GNU Affero General Public License as
- published by the Free Software Foundation; either version 3,
- or (at your option) any later version.
-
- GNU Taler is distributed in the hope that it will be useful, but
- WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY 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-merchant-httpd_private-post-instances-ID-login.c
- * @brief implementing POST /instances/$ID/login request handling
- * @author Christian Grothoff
- */
-#include "platform.h"
-#include "taler-merchant-httpd_private-post-instances-ID-login.h"
-#include "taler-merchant-httpd_helper.h"
-#include <taler/taler_json_lib.h>
-
-
-/**
- * Maximum duration for the validity of a login token.
- */
-#define MAX_DURATION GNUNET_TIME_UNIT_DAYS
-
-
-MHD_RESULT
-TMH_private_post_instances_ID_login (const struct TMH_RequestHandler *rh,
- struct MHD_Connection *connection,
- struct TMH_HandlerContext *hc)
-{
- struct TMH_MerchantInstance *mi = hc->instance;
- json_t *jlogin = hc->request_body;
- const char *scope;
- bool refreshable = false;
- struct GNUNET_TIME_Relative duration
- = MAX_DURATION;
- struct GNUNET_TIME_Timestamp expiration_time;
- struct GNUNET_JSON_Specification spec[] = {
- GNUNET_JSON_spec_string ("scope",
- &scope),
- GNUNET_JSON_spec_mark_optional (
- GNUNET_JSON_spec_relative_time ("duration",
- &duration),
- NULL),
- GNUNET_JSON_spec_mark_optional (
- GNUNET_JSON_spec_bool ("refreshable",
- &refreshable),
- NULL),
- GNUNET_JSON_spec_end ()
- };
- char *token;
- MHD_RESULT ret;
-
- {
- enum GNUNET_GenericReturnValue res;
-
- res = TALER_MHD_parse_json_data (connection,
- jlogin,
- spec);
- if (GNUNET_OK != res)
- return (GNUNET_NO == res) ? MHD_YES : MHD_NO;
- }
- duration = GNUNET_TIME_relative_min (duration,
- MAX_DURATION);
- expiration_time = GNUNET_TIME_relative_to_timestamp (duration);
- token = GNUNET_strdup ("FIXME-foo");
- (void) mi;
-
- ret = TALER_MHD_REPLY_JSON_PACK (
- connection,
- MHD_HTTP_OK,
- GNUNET_JSON_pack_string ("token",
- token),
- GNUNET_JSON_pack_string ("scope",
- scope),
- GNUNET_JSON_pack_bool ("refreshable",
- refreshable),
- GNUNET_JSON_pack_timestamp ("expiration",
- expiration_time));
- GNUNET_free (token);
- return ret;
-}
-
-
-/* end of taler-merchant-httpd_private-post-instances-ID-login.c */
diff --git a/src/backend/taler-merchant-httpd_private-post-instances-ID-login.h b/src/backend/taler-merchant-httpd_private-post-instances-ID-login.h
@@ -1,44 +0,0 @@
-/*
- This file is part of GNU Taler
- (C) 2023 Taler Systems SA
-
- GNU Taler is free software; you can redistribute it and/or modify
- it under the terms of the GNU Affero General Public License as
- published by the Free Software Foundation; either version 3,
- or (at your option) any later version.
-
- GNU Taler is distributed in the hope that it will be useful, but
- WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY 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-merchant-httpd_private-post-instances-ID-login.h
- * @brief implements POST /instances/$ID/login request handling
- * @author Christian Grothoff
- */
-#ifndef TALER_MERCHANT_HTTPD_PRIVATE_POST_INSTANCES_ID_LOGIN_H
-#define TALER_MERCHANT_HTTPD_PRIVATE_POST_INSTANCES_ID_LOGIN_H
-#include "taler-merchant-httpd.h"
-
-
-/**
- * Obtain a login token for an instance.
- *
- * @param rh context of the handler
- * @param connection the MHD connection to handle
- * @param[in,out] hc context with further information about the request
- * @return MHD result code
- */
-MHD_RESULT
-TMH_private_post_instances_ID_login (const struct TMH_RequestHandler *rh,
- struct MHD_Connection *connection,
- struct TMH_HandlerContext *hc);
-
-
-#endif
diff --git a/src/backend/taler-merchant-httpd_private-post-instances-ID-token.c b/src/backend/taler-merchant-httpd_private-post-instances-ID-token.c
@@ -0,0 +1,96 @@
+/*
+ This file is part of GNU Taler
+ (C) 2023 Taler Systems SA
+
+ GNU Taler is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Affero General Public License as
+ published by the Free Software Foundation; either version 3,
+ or (at your option) any later version.
+
+ GNU Taler is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY 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-merchant-httpd_private-post-instances-ID-token.c
+ * @brief implementing POST /instances/$ID/token request handling
+ * @author Christian Grothoff
+ */
+#include "platform.h"
+#include "taler-merchant-httpd_private-post-instances-ID-token.h"
+#include "taler-merchant-httpd_helper.h"
+#include <taler/taler_json_lib.h>
+
+
+/**
+ * Maximum duration for the validity of a token token.
+ */
+#define MAX_DURATION GNUNET_TIME_UNIT_DAYS
+
+
+MHD_RESULT
+TMH_private_post_instances_ID_token (const struct TMH_RequestHandler *rh,
+ struct MHD_Connection *connection,
+ struct TMH_HandlerContext *hc)
+{
+ struct TMH_MerchantInstance *mi = hc->instance;
+ json_t *jtoken = hc->request_body;
+ const char *scope;
+ bool refreshable = false;
+ struct GNUNET_TIME_Relative duration
+ = MAX_DURATION;
+ struct GNUNET_TIME_Timestamp expiration_time;
+ struct GNUNET_JSON_Specification spec[] = {
+ GNUNET_JSON_spec_string ("scope",
+ &scope),
+ GNUNET_JSON_spec_mark_optional (
+ GNUNET_JSON_spec_relative_time ("duration",
+ &duration),
+ NULL),
+ GNUNET_JSON_spec_mark_optional (
+ GNUNET_JSON_spec_bool ("refreshable",
+ &refreshable),
+ NULL),
+ GNUNET_JSON_spec_end ()
+ };
+ char *token;
+ MHD_RESULT ret;
+
+ {
+ enum GNUNET_GenericReturnValue res;
+
+ res = TALER_MHD_parse_json_data (connection,
+ jtoken,
+ spec);
+ if (GNUNET_OK != res)
+ return (GNUNET_NO == res) ? MHD_YES : MHD_NO;
+ }
+ duration = GNUNET_TIME_relative_min (duration,
+ MAX_DURATION);
+ expiration_time = GNUNET_TIME_relative_to_timestamp (duration);
+ token = GNUNET_strdup ("FIXME-foo");
+ (void) mi;
+
+ ret = TALER_MHD_REPLY_JSON_PACK (
+ connection,
+ MHD_HTTP_OK,
+ GNUNET_JSON_pack_string ("token",
+ token),
+ GNUNET_JSON_pack_string ("scope",
+ scope),
+ GNUNET_JSON_pack_bool ("refreshable",
+ refreshable),
+ GNUNET_JSON_pack_timestamp ("expiration",
+ expiration_time));
+ GNUNET_free (token);
+ return ret;
+}
+
+
+/* end of taler-merchant-httpd_private-post-instances-ID-token.c */
diff --git a/src/backend/taler-merchant-httpd_private-post-instances-ID-token.h b/src/backend/taler-merchant-httpd_private-post-instances-ID-token.h
@@ -0,0 +1,45 @@
+/*
+ This file is part of GNU Taler
+ (C) 2023 Taler Systems SA
+
+ GNU Taler is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Affero General Public License as
+ published by the Free Software Foundation; either version 3,
+ or (at your option) any later version.
+
+ GNU Taler is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY 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-merchant-httpd_private-post-instances-ID-token.h
+ * @brief implements POST /instances/$ID/token request handling
+ * @author Christian Grothoff
+ */
+#ifndef TALER_MERCHANT_HTTPD_PRIVATE_POST_INSTANCES_ID_TOKEN_H
+#define TALER_MERCHANT_HTTPD_PRIVATE_POST_INSTANCES_ID_TOKEN_H
+
+#include "taler-merchant-httpd.h"
+
+
+/**
+ * Obtain a login token for an instance.
+ *
+ * @param rh context of the handler
+ * @param connection the MHD connection to handle
+ * @param[in,out] hc context with further information about the request
+ * @return MHD result code
+ */
+MHD_RESULT
+TMH_private_post_instances_ID_token (const struct TMH_RequestHandler *rh,
+ struct MHD_Connection *connection,
+ struct TMH_HandlerContext *hc);
+
+
+#endif