gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[taler-donau] branch master updated: [lib] add charity post


From: gnunet
Subject: [taler-donau] branch master updated: [lib] add charity post
Date: Tue, 05 Mar 2024 00:30:54 +0100

This is an automated email from the git hooks/post-receive script.

lukas-matyja pushed a commit to branch master
in repository donau.

The following commit(s) were added to refs/heads/master by this push:
     new 96acfb7  [lib] add charity post
96acfb7 is described below

commit 96acfb7bb41e3ee3c660e3228ab713fc3ddb79d8
Author: Matyja Lukas Adam <lukas.matyja@students.bfh.ch>
AuthorDate: Tue Mar 5 00:31:33 2024 +0100

    [lib] add charity post
---
 src/include/donau_service.h        |  28 +++-
 src/lib/Makefile.am                |   1 +
 src/lib/donau_api_charity_delete.c | 258 ++++++++++++++++++++++++++++++++++++
 src/lib/donau_api_charity_post.c   | 264 +++++++++++++++++++++++++++++++++++++
 4 files changed, 545 insertions(+), 6 deletions(-)

diff --git a/src/include/donau_service.h b/src/include/donau_service.h
index 7f7fd54..c3cef8b 100644
--- a/src/include/donau_service.h
+++ b/src/include/donau_service.h
@@ -870,7 +870,7 @@ typedef void
  *
  * @param ctx curl context
  * @param url donau base URL
- * @param bearer for authentication
+ * @param bearer for authorization
  * @param cb the callback to call when a reply for this request is available
  * @param cb_cls closure for the above callback
  * @return a handle for this request; NULL if the inputs are invalid (i.e.
@@ -997,7 +997,7 @@ typedef void
  *
  * @param ctx curl context
  * @param url donau base URL
- * @param bearer for authentication
+ * @param bearer for authorization
  * @param id of the requested charity
  * @param cb the callback to call when a reply for this request is available
  * @param cb_cls closure for the above callback
@@ -1037,16 +1037,32 @@ struct DONAU_CharityRequest
    */
   char *name;
 
+  /**
+   * URL
+   */
+  char *charity_url;
+
+  /**
+   * max donation amount per year
+   */
+  struct TALER_Amount max_per_year;
+
   /**
    * max donation amount per year
    */
-  struct TALER_Amount amount;
+  struct TALER_Amount receipts_to_date;
 
   /**
    * public key of the charity
    */
   struct DONAU_DonauPublicKeyP charity_pub;
 
+
+  /**
+   * current year
+   */
+  uint64_t current_year;
+
 };
 /**
  * @brief A /charities Post Handle
@@ -1115,7 +1131,7 @@ typedef void
  * @param ctx curl context
  * @param url donau base URL
  * @param charity_req contains the name, public key and the max donation amount
- * @param bearer for authentication
+ * @param bearer for authorization
  * @param cb the callback to call when a reply for this request is available
  * @param cb_cls closure for the above callback
  * @return a handle for this request; NULL if the inputs are invalid (i.e.
@@ -1125,7 +1141,7 @@ struct DONAU_CharityPostHandle *
 DONAU_charity_post (
   struct GNUNET_CURL_Context *ctx,
   const char *url,
-  const struct DONAU_CharityRequest *charity_req,
+  struct DONAU_CharityRequest *charity_req,
   const struct DONAU_BearerToken bearer,
   DONAU_PostCharityResponseCallback cb,
   void *cb_cls);
@@ -1259,7 +1275,7 @@ typedef void
  * @param ctx curl context
  * @param url donau base URL
  * @param id of the charity
- * @param bearer for authentication
+ * @param bearer for authorization
  * @param cb the callback to call when a reply for this request is available
  * @param cb_cls closure for the above callback
  * @return a handle for this request; NULL if the inputs are invalid (i.e.
diff --git a/src/lib/Makefile.am b/src/lib/Makefile.am
index 07b8f09..7c7c1fc 100644
--- a/src/lib/Makefile.am
+++ b/src/lib/Makefile.am
@@ -22,6 +22,7 @@ libdonau_la_LDFLAGS = \
 libdonau_la_SOURCES = \
   donau_api_handle.c \
   donau_api_charity_get.c \
+  donau_api_charity_post.c \
   donau_api_charities_get.c \
   donau_api_curl_defaults.c donau_api_curl_defaults.h 
  
diff --git a/src/lib/donau_api_charity_delete.c 
b/src/lib/donau_api_charity_delete.c
new file mode 100644
index 0000000..006c8e5
--- /dev/null
+++ b/src/lib/donau_api_charity_delete.c
@@ -0,0 +1,258 @@
+/*
+  This file is part of TALER
+  Copyright (C) 2024 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
+  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 lib/donau_api_charity_get.c
+ * @brief Implementation of the "handle" component of the donau's HTTP API
+ * @author Lukas Matyja
+ */
+#include <gnunet/gnunet_curl_lib.h>
+#include <taler/taler_json_lib.h>
+#include "donau_service.h"
+#include "donau_api_curl_defaults.h"
+#include "donau_json_lib.h"
+
+
+/**
+ * Handle for a GET /charities/$CHARITY_ID request.
+ */
+struct DONAU_CharityGetHandle
+{
+  /**
+   * The url for the /charities/$CHARITY_ID request.
+   */
+  char *url;
+
+  /**
+   * Entry for this request with the `struct GNUNET_CURL_Context`.
+   */
+  struct GNUNET_CURL_Job *job;
+
+  /**
+   * Function to call with the result.
+   */
+  DONAU_GetCharityResponseCallback cb;
+
+  /**
+   * Charity id we are querying.
+   */
+  unsigned long long charity_id;
+
+  /**
+   * Closure to pass to @e cb.
+   */
+  void *cb_cls;
+
+};
+
+/**
+ * Decode the JSON in @a resp_obj from the /charities/$ID response
+ * and store the data in the @a charity_data.
+ *
+ * @param[in] resp_obj JSON object to parse
+ * @param[out] charity_data where to store the results we decoded
+ * @return #GNUNET_OK on success, #GNUNET_SYSERR on error
+ * (malformed JSON)
+ */
+static enum GNUNET_GenericReturnValue
+handle_charity_get_ok (const json_t *resp_obj,
+                       struct DONAU_CharityGetHandle *cgh,
+                                          struct DONAU_GetCharityResponse 
*gcresp)
+{
+  struct DONAU_Charity *charity = &gcresp->details.ok.charity;
+  const char *name;
+  if (JSON_OBJECT != json_typeof (resp_obj))
+  {
+    GNUNET_break_op (0);
+    return GNUNET_SYSERR;
+  }
+
+  struct GNUNET_JSON_Specification spec[] = {
+    GNUNET_JSON_spec_fixed_auto ("charity_pub",
+                                 &charity->charity_pub),
+       GNUNET_JSON_spec_string ("name", &name),
+    TALER_JSON_spec_amount_any ("max_per_year",
+                                &charity->max_per_year),
+    TALER_JSON_spec_amount_any ("receipts_to_date",
+                                &charity->
+                                receipts_to_date),
+    GNUNET_JSON_spec_uint64 ("current_year",
+                             &charity->current_year),
+    GNUNET_JSON_spec_end ()
+  };
+  if (GNUNET_OK !=
+      GNUNET_JSON_parse (resp_obj,
+                         spec,
+                         NULL,
+                         NULL))
+  {
+    GNUNET_break_op (0);
+    return GNUNET_SYSERR;
+  }
+  charity->name = GNUNET_strdup (name);
+
+  cgh->cb (cgh->cb_cls,
+           gcresp);
+  cgh->cb = NULL;
+  return GNUNET_OK;
+}
+
+
+/**
+ * Callback used when downloading the reply to a /charity request
+ * is complete.
+ *
+ * @param cls the `struct KeysRequest`
+ * @param response_code HTTP response code, 0 on error
+ * @param resp_obj parsed JSON result, NULL on error
+ */
+static void
+handle_charity_get_finished (void *cls,
+                             long response_code,
+                             const void *resp_obj)
+{
+  // struct DONAU_Charity *cd = NULL;
+
+  struct DONAU_CharityGetHandle *cgh = cls;
+  const json_t *j = resp_obj;
+  struct DONAU_GetCharityResponse gcresp = {
+    .hr.reply = j,
+    .hr.http_status = (unsigned int) response_code
+  };
+
+  cgh->job = NULL;
+  switch (response_code)
+  {
+  case 0:
+    gcresp.hr.ec = TALER_EC_GENERIC_INVALID_RESPONSE;
+    break;
+  case MHD_HTTP_OK:
+    if (GNUNET_OK !=
+        handle_charity_get_ok (j,
+                               cgh,
+                                                          &gcresp))
+    {
+      gcresp.hr.http_status = 0;
+      gcresp.hr.ec = TALER_EC_GENERIC_REPLY_MALFORMED;
+    }
+    break;
+  case MHD_HTTP_BAD_REQUEST:
+    /* This should never happen, either us or the donau is buggy
+       (or API version conflict); just pass JSON reply to the application */
+    gcresp.hr.ec = TALER_JSON_get_error_code (j);
+    gcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  case MHD_HTTP_NOT_FOUND:
+    /* Nothing really to verify, this should never
+       happen, we should pass the JSON reply to the application */
+    gcresp.hr.ec = TALER_JSON_get_error_code (j);
+    gcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  case MHD_HTTP_INTERNAL_SERVER_ERROR:
+    /* Server had an internal issue; we should retry, but this API
+       leaves this to the application */
+    gcresp.hr.ec = TALER_JSON_get_error_code (j);
+    gcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  default:
+    /* unexpected response code */
+    GNUNET_break_op (0);
+    gcresp.hr.ec = TALER_JSON_get_error_code (j);
+    gcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+                "Unexpected response code %u/%d for GET %s\n",
+                (unsigned int) response_code,
+                (int) gcresp.hr.ec,
+                cgh->url);
+    break;
+  }
+  if (NULL != cgh->cb)
+  {
+    cgh->cb (cgh->cb_cls,
+             &gcresp);
+    cgh->cb = NULL;
+  }
+  DONAU_charity_get_cancel (cgh);
+}
+
+
+struct DONAU_CharityGetHandle *
+DONAU_charity_get (
+  struct GNUNET_CURL_Context *ctx,
+  const char *url,
+  const uint64_t id,
+  const struct DONAU_BearerToken bearer, // TODO: check authorization
+  DONAU_GetCharityResponseCallback cb,
+  void *cb_cls)
+{
+  struct DONAU_CharityGetHandle *cgh;
+  CURL *eh;
+
+  TALER_LOG_DEBUG ("Connecting to the donau (%s)\n",
+                   url);
+  cgh = GNUNET_new (struct DONAU_CharityGetHandle);
+  cgh->url = GNUNET_strdup (url);
+  cgh->cb = cb;
+  cgh->charity_id = id;
+  cgh->cb_cls = cb_cls;
+  char arg_str[sizeof (id) * 2 + 32];
+  GNUNET_snprintf (arg_str,
+                                  sizeof (arg_str),
+                                  "charities/%llu",
+                                  (unsigned long long)
+                                  id);
+  cgh->url = TALER_url_join (url,
+                             arg_str,
+                             NULL);
+  if (NULL == cgh->url)
+  {
+    GNUNET_free (cgh);
+    return NULL;
+  }
+  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+              "Requesting a charity with URL `%s'.\n",
+              cgh->url);
+  eh = DONAU_curl_easy_get_ (cgh->url);
+  if (NULL == eh)
+  {
+    GNUNET_break (0);
+    GNUNET_free (cgh->url);
+    GNUNET_free (cgh);
+    return NULL;
+  }
+  cgh->job = GNUNET_CURL_job_add_with_ct_json (ctx,
+                                  eh,
+                                  &handle_charity_get_finished,
+                                  cgh);
+  return cgh;
+}
+
+
+void
+DONAU_charity_get_cancel (
+  struct DONAU_CharityGetHandle *cgh)
+{
+  if (NULL != cgh->job)
+  {
+    GNUNET_CURL_job_cancel (cgh->job);
+    cgh->job = NULL;
+  }
+  GNUNET_free (cgh->url);
+  GNUNET_free (cgh);
+}
diff --git a/src/lib/donau_api_charity_post.c b/src/lib/donau_api_charity_post.c
new file mode 100644
index 0000000..31effc0
--- /dev/null
+++ b/src/lib/donau_api_charity_post.c
@@ -0,0 +1,264 @@
+/*
+  This file is part of TALER
+  Copyright (C) 2024 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
+  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 lib/donau_api_charity_post.c
+ * @brief Implementation of the "handle" component of the donau's HTTP API
+ * @author Lukas Matyja
+ */
+#include <gnunet/gnunet_curl_lib.h>
+#include <taler/taler_json_lib.h>
+#include <taler/taler_curl_lib.h>
+#include "donau_service.h"
+#include "donau_api_curl_defaults.h"
+#include "donau_json_lib.h"
+
+
+/**
+ * Handle for a POST /charities/ request.
+ */
+struct DONAU_CharityPostHandle
+{
+  /**
+   * The url for the /charities/ request.
+   */
+  char *url;
+
+  /**
+   * Minor context that holds body and headers.
+   */
+  struct TALER_CURL_PostContext post_ctx;
+
+  /**
+   * Entry for this request with the `struct GNUNET_CURL_Context`.
+   */
+  struct GNUNET_CURL_Job *job;
+
+  /**
+   * Function to call with the result.
+   */
+  DONAU_PostCharityResponseCallback cb;
+
+  /**
+   * Closure to pass to @e cb.
+   */
+  void *cb_cls;
+
+  /**
+   * Reference to the execution context.
+   */
+  struct GNUNET_CURL_Context *ctx;
+
+};
+
+/**
+ * Decode the JSON in @a resp_obj from the /charities/$ID response
+ * and store the data in the @a charity_data.
+ *
+ * @param[in] resp_obj JSON object to parse
+ * @param[out] charity_data where to store the results we decoded
+ * @return #GNUNET_OK on success, #GNUNET_SYSERR on error
+ * (malformed JSON)
+ */
+//static enum GNUNET_GenericReturnValue
+//handle_charity_get_ok (const json_t *resp_obj,
+//                       struct DONAU_CharityGetHandle *cgh,
+//                                        struct DONAU_GetCharityResponse 
*gcresp)
+//{
+//  struct DONAU_Charity *charity = &gcresp->details.ok.charity;
+//  const char *name;
+//  if (JSON_OBJECT != json_typeof (resp_obj))
+//  {
+//    GNUNET_break_op (0);
+//    return GNUNET_SYSERR;
+//  }
+//
+//  struct GNUNET_JSON_Specification spec[] = {
+//    GNUNET_JSON_spec_fixed_auto ("charity_pub",
+//                                 &charity->charity_pub),
+//     GNUNET_JSON_spec_string ("name", &name),
+//    TALER_JSON_spec_amount_any ("max_per_year",
+//                                &charity->max_per_year),
+//    TALER_JSON_spec_amount_any ("receipts_to_date",
+//                                &charity->
+//                                receipts_to_date),
+//    GNUNET_JSON_spec_uint64 ("current_year",
+//                             &charity->current_year),
+//    GNUNET_JSON_spec_end ()
+//  };
+//  if (GNUNET_OK !=
+//      GNUNET_JSON_parse (resp_obj,
+//                         spec,
+//                         NULL,
+//                         NULL))
+//  {
+//    GNUNET_break_op (0);
+//    return GNUNET_SYSERR;
+//  }
+//  charity->name = GNUNET_strdup (name);
+//
+//  cgh->cb (cgh->cb_cls,
+//           gcresp);
+//  cgh->cb = NULL;
+//  return GNUNET_OK;
+//}
+
+
+/**
+ * Function called when we're done processing the
+ * HTTP POST /charities request.
+ *
+ * @param cls the `struct KeysRequest`
+ * @param response_code HTTP response code, 0 on error
+ * @param resp_obj parsed JSON result, NULL on error
+ */
+static void
+handle_charity_post_finished (void *cls,
+                             long response_code,
+                             const void *resp_obj)
+{
+  struct DONAU_CharityPostHandle *cph = cls;
+  const json_t *j = resp_obj;
+  struct DONAU_PostCharityResponse pcresp = {
+    .hr.reply = j,
+    .hr.http_status = (unsigned int) response_code
+  };
+
+  cph->job = NULL;
+  switch (response_code)
+  {
+  case MHD_HTTP_NO_CONTENT:
+    break;
+  case MHD_HTTP_FORBIDDEN:
+    pcresp.hr.ec = TALER_JSON_get_error_code (j);
+    pcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  case MHD_HTTP_NOT_FOUND:
+    pcresp.hr.ec = TALER_JSON_get_error_code (j);
+    pcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  case MHD_HTTP_CONTENT_TOO_LARGE:
+    pcresp.hr.ec = TALER_JSON_get_error_code (j);
+    pcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    break;
+  default:
+    /* unexpected response code */
+    GNUNET_break_op (0);
+    pcresp.hr.ec = TALER_JSON_get_error_code (j);
+    pcresp.hr.hint = TALER_JSON_get_error_hint (j);
+    GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+                "Unexpected response code %u/%d for POST %s\n",
+                (unsigned int) response_code,
+                (int) pcresp.hr.ec,
+                cph->url);
+    break;
+  }
+  if (NULL != cph->cb)
+  {
+    cph->cb (cph->cb_cls,
+             &pcresp);
+    cph->cb = NULL;
+  }
+  DONAU_charity_post_cancel (cph);
+}
+
+
+struct DONAU_CharityPostHandle *
+DONAU_charity_post (
+  struct GNUNET_CURL_Context *ctx,
+  const char *url,
+  struct DONAU_CharityRequest *charity_req,
+  const struct DONAU_BearerToken bearer,
+  DONAU_PostCharityResponseCallback cb,
+  void *cb_cls)
+{
+  struct DONAU_CharityPostHandle *cph;
+  CURL *eh;
+  json_t *body;
+
+  TALER_LOG_DEBUG ("Connecting to the donau (%s)\n",
+                   url);
+  cph = GNUNET_new (struct DONAU_CharityPostHandle);
+  cph->url = GNUNET_strdup (url);
+  cph->cb = cb;
+  cph->cb_cls = cb_cls;
+  cph->ctx = ctx;
+  cph->url = TALER_url_join (url,
+                                                        "charities",
+                             NULL);
+  if (NULL == cph->url)
+  {
+       GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+                               "Could not construct request URL.\n");
+    GNUNET_free (cph);
+    return NULL;
+  }
+  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+              "POST a charity with URL `%s'.\n",
+              cph->url);
+  body = GNUNET_JSON_PACK (
+             GNUNET_JSON_pack_data_auto ("charity_pub",
+                                         &charity_req->charity_pub),
+             GNUNET_JSON_pack_string ("url",
+                                                                
charity_req->charity_url),
+             GNUNET_JSON_pack_string ("name",
+                                                          charity_req->name),
+             TALER_JSON_pack_amount ("max_per_year",
+                                     &charity_req->max_per_year),
+             TALER_JSON_pack_amount ("receipts_to_date",
+                                     &charity_req->receipts_to_date), // 
really needed?
+             GNUNET_JSON_pack_uint64 ("current_year",
+                                                         
charity_req->current_year));
+  eh = DONAU_curl_easy_get_ (cph->url);
+  if ( (NULL == eh) ||
+       (GNUNET_OK !=
+        TALER_curl_easy_post (&cph->post_ctx,
+                              eh,
+                              body)) )
+  {
+    GNUNET_break (0);
+    if (NULL != eh)
+      curl_easy_cleanup (eh);
+    json_decref (body);
+    GNUNET_free (cph->url);
+    return NULL;
+  }
+  json_decref (body);
+  cph->job = GNUNET_CURL_job_add2 (ctx,
+                                  eh,
+                                                                 
cph->post_ctx.headers,
+                                  &handle_charity_post_finished,
+                                  cph);
+  return cph;
+}
+
+
+void
+DONAU_charity_post_cancel (
+  struct DONAU_CharityPostHandle *cph)
+{
+  if (NULL != cph->job)
+  {
+    GNUNET_CURL_job_cancel (cph->job);
+    cph->job = NULL;
+  }
+  TALER_curl_easy_post_finished (&cph->post_ctx);
+  GNUNET_free (cph->url);
+  GNUNET_free (cph);
+}

-- 
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]