merchant

Merchant backend to process payments, run by merchants
Log | Files | Refs | Submodules | README | LICENSE

merchant_api_delete-private-fountains-FOUNTAIN_ID.c (5889B)


      1 /*
      2   This file is part of TALER
      3   Copyright (C) 2026 Taler Systems SA
      4 
      5   TALER is free software; you can redistribute it and/or modify
      6   it under the terms of the GNU Lesser General Public License as
      7   published by the Free Software Foundation; either version 2.1,
      8   or (at your option) any later version.
      9 
     10   TALER is distributed in the hope that it will be useful,
     11   but WITHOUT ANY WARRANTY; without even the implied warranty of
     12   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     13   GNU Lesser General Public License for more details.
     14 
     15   You should have received a copy of the GNU Lesser General
     16   Public License along with TALER; see the file COPYING.LGPL.
     17   If not, see <http://www.gnu.org/licenses/>
     18 */
     19 /**
     20  * @file src/lib/merchant_api_delete-private-fountains-FOUNTAIN_ID.c
     21  * @brief Implementation of the DELETE /private/fountains/$FOUNTAIN_ID request
     22  * @author Bohdan Potuzhnyi
     23  */
     24 #include "platform.h"
     25 #include <curl/curl.h>
     26 #include <jansson.h>
     27 #include <microhttpd.h> /* just for HTTP status codes */
     28 #include <gnunet/gnunet_util_lib.h>
     29 #include <gnunet/gnunet_curl_lib.h>
     30 #include <taler/merchant/delete-private-fountains-FOUNTAIN_ID.h>
     31 #include "merchant_api_curl_defaults.h"
     32 #include "merchant_api_common.h"
     33 #include <taler/taler_json_lib.h>
     34 #include <taler/taler_curl_lib.h>
     35 
     36 
     37 /**
     38  * Handle for a DELETE /private/fountains/$FOUNTAIN_ID operation.
     39  */
     40 struct TALER_MERCHANT_DeletePrivateFountainHandle
     41 {
     42   /**
     43    * Base URL of the merchant backend.
     44    */
     45   char *base_url;
     46 
     47   /**
     48    * The full URL for this request.
     49    */
     50   char *url;
     51 
     52   /**
     53    * Fountain identifier.
     54    */
     55   char *fountain_id;
     56 
     57   /**
     58    * Handle for the request.
     59    */
     60   struct GNUNET_CURL_Job *job;
     61 
     62   /**
     63    * Function to call with the result.
     64    */
     65   TALER_MERCHANT_DeletePrivateFountainCallback cb;
     66 
     67   /**
     68    * Closure for @a cb.
     69    */
     70   TALER_MERCHANT_DELETE_PRIVATE_FOUNTAIN_RESULT_CLOSURE *cb_cls;
     71 
     72   /**
     73    * Reference to the execution context.
     74    */
     75   struct GNUNET_CURL_Context *ctx;
     76 };
     77 
     78 
     79 /**
     80  * Function called when we're done processing the
     81  * HTTP DELETE /private/fountains/$FOUNTAIN_ID request.
     82  *
     83  * @param cls the `struct TALER_MERCHANT_DeletePrivateFountainHandle`
     84  * @param response_code HTTP response code, 0 on error
     85  * @param response response body, NULL if not in JSON
     86  */
     87 static void
     88 handle_delete_fountain_finished (void *cls,
     89                                  long response_code,
     90                                  const void *response)
     91 {
     92   struct TALER_MERCHANT_DeletePrivateFountainHandle *dpfh = cls;
     93   const json_t *json = response;
     94   struct TALER_MERCHANT_DeletePrivateFountainResponse dfr = {
     95     .hr.http_status = (unsigned int) response_code,
     96     .hr.reply = json
     97   };
     98 
     99   dpfh->job = NULL;
    100   GNUNET_log (GNUNET_ERROR_TYPE_INFO,
    101               "DELETE /private/fountains/$ID completed with response code %u\n",
    102               (unsigned int) response_code);
    103   switch (response_code)
    104   {
    105   case 0:
    106     dfr.hr.ec = TALER_EC_GENERIC_INVALID_RESPONSE;
    107     break;
    108   case MHD_HTTP_NO_CONTENT:
    109     break;
    110   case MHD_HTTP_UNAUTHORIZED:
    111   case MHD_HTTP_FORBIDDEN:
    112   case MHD_HTTP_NOT_FOUND:
    113   case MHD_HTTP_INTERNAL_SERVER_ERROR:
    114     dfr.hr.ec = TALER_JSON_get_error_code (json);
    115     dfr.hr.hint = TALER_JSON_get_error_hint (json);
    116     break;
    117   default:
    118     TALER_MERCHANT_parse_error_details_ (json,
    119                                          response_code,
    120                                          &dfr.hr);
    121     GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
    122                 "Unexpected response code %u/%d\n",
    123                 (unsigned int) response_code,
    124                 (int) dfr.hr.ec);
    125     GNUNET_break_op (0);
    126     break;
    127   }
    128   dpfh->cb (dpfh->cb_cls,
    129             &dfr);
    130   TALER_MERCHANT_delete_private_fountain_cancel (dpfh);
    131 }
    132 
    133 
    134 struct TALER_MERCHANT_DeletePrivateFountainHandle *
    135 TALER_MERCHANT_delete_private_fountain_create (
    136   struct GNUNET_CURL_Context *ctx,
    137   const char *url,
    138   const char *fountain_id)
    139 {
    140   struct TALER_MERCHANT_DeletePrivateFountainHandle *dpfh;
    141 
    142   dpfh = GNUNET_new (struct TALER_MERCHANT_DeletePrivateFountainHandle);
    143   dpfh->ctx = ctx;
    144   dpfh->base_url = GNUNET_strdup (url);
    145   dpfh->fountain_id = GNUNET_strdup (fountain_id);
    146   return dpfh;
    147 }
    148 
    149 
    150 enum TALER_ErrorCode
    151 TALER_MERCHANT_delete_private_fountain_start (
    152   struct TALER_MERCHANT_DeletePrivateFountainHandle *dpfh,
    153   TALER_MERCHANT_DeletePrivateFountainCallback cb,
    154   TALER_MERCHANT_DELETE_PRIVATE_FOUNTAIN_RESULT_CLOSURE *cb_cls)
    155 {
    156   CURL *eh;
    157 
    158   dpfh->cb = cb;
    159   dpfh->cb_cls = cb_cls;
    160   {
    161     char *path;
    162 
    163     GNUNET_asprintf (&path,
    164                      "private/fountains/%s",
    165                      dpfh->fountain_id);
    166     dpfh->url = TALER_url_join (dpfh->base_url,
    167                                 path,
    168                                 NULL);
    169     GNUNET_free (path);
    170   }
    171   if (NULL == dpfh->url)
    172     return TALER_EC_GENERIC_CONFIGURATION_INVALID;
    173   eh = TALER_MERCHANT_curl_easy_get_ (dpfh->url);
    174   if (NULL == eh)
    175   {
    176     GNUNET_break (0);
    177     return TALER_EC_GENERIC_INTERNAL_INVARIANT_FAILURE;
    178   }
    179   GNUNET_assert (CURLE_OK ==
    180                  curl_easy_setopt (eh,
    181                                    CURLOPT_CUSTOMREQUEST,
    182                                    MHD_HTTP_METHOD_DELETE));
    183   dpfh->job = GNUNET_CURL_job_add (dpfh->ctx,
    184                                    eh,
    185                                    &handle_delete_fountain_finished,
    186                                    dpfh);
    187   if (NULL == dpfh->job)
    188     return TALER_EC_GENERIC_INTERNAL_INVARIANT_FAILURE;
    189   return TALER_EC_NONE;
    190 }
    191 
    192 
    193 void
    194 TALER_MERCHANT_delete_private_fountain_cancel (
    195   struct TALER_MERCHANT_DeletePrivateFountainHandle *dpfh)
    196 {
    197   if (NULL != dpfh->job)
    198   {
    199     GNUNET_CURL_job_cancel (dpfh->job);
    200     dpfh->job = NULL;
    201   }
    202   GNUNET_free (dpfh->fountain_id);
    203   GNUNET_free (dpfh->url);
    204   GNUNET_free (dpfh->base_url);
    205   GNUNET_free (dpfh);
    206 }
    207 
    208 
    209 /* end of merchant_api_delete-private-fountains-FOUNTAIN_ID.c */