anastasis-gtk

Demonstrator GUI for Anastasis
Log | Files | Refs | README | LICENSE

anastasis-gtk_handle-add-provider.c (8074B)


      1 /*
      2      This file is part of anastasis-gtk.
      3      Copyright (C) 2022 Anastasis SARL
      4 
      5      Anastasis is free software; you can redistribute it and/or modify
      6      it under the terms of the GNU General Public License as published
      7      by the Free Software Foundation; either version 3, or (at your
      8      option) any later version.
      9 
     10      Anastasis is distributed in the hope that it will be useful, but
     11      WITHOUT ANY WARRANTY; without even the implied warranty of
     12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     13      General Public License for more details.
     14 
     15      You should have received a copy of the GNU General Public License
     16      along with Anastasis; see the file COPYING.  If not, write to the
     17      Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
     18      Boston, MA 02110-1301, USA.
     19 */
     20 
     21 /**
     22  * @file src/anastasis/anastasis-gtk_handle-add-provider.c
     23  * @brief Dialog to add a provider during recovery
     24  * @author Christian Grothoff
     25  */
     26 #include <gnunet/gnunet_util_lib.h>
     27 #include "anastasis_gtk_util.h"
     28 #include "anastasis-gtk_action.h"
     29 #include "anastasis-gtk_helper.h"
     30 #include <jansson.h>
     31 #include <microhttpd.h>
     32 
     33 /**
     34  * State data for the provider, NULL if none is available.
     35  */
     36 static json_t *pstate;
     37 
     38 /**
     39  * Current /config operation, or NULL if none.
     40  */
     41 static struct ANASTASIS_ConfigOperation *co;
     42 
     43 
     44 /**
     45  * Function called with the result of a /config request.
     46  * Note that an HTTP status of #MHD_HTTP_OK is no guarantee
     47  * that @a acfg is non-NULL. @a acfg is non-NULL only if
     48  * the server provided an acceptable response.
     49  *
     50  * @param cls closure with our `GtkBuilder *`
     51  * @param acfg configuration obtained, NULL if we could not parse it
     52  */
     53 static void
     54 config_cb (void *cls,
     55            const struct ANASTASIS_Config *acfg)
     56 {
     57   GtkBuilder *builder = GTK_BUILDER (cls);
     58   GtkWidget *button;
     59   json_t *methods_list;
     60   GtkLabel *l;
     61 
     62   co = NULL;
     63   l = GTK_LABEL (gtk_builder_get_object (builder,
     64                                          "error_label"));
     65   if (MHD_HTTP_OK != acfg->http_status)
     66   {
     67     char *msg;
     68 
     69     if (0 == acfg->http_status)
     70       GNUNET_asprintf (&msg,
     71                        "Provider URL invalid (no response)");
     72     else
     73       GNUNET_asprintf (&msg,
     74                        "Provider URL invalid (HTTP status %u)",
     75                        acfg->http_status);
     76     gtk_widget_set_visible (GTK_WIDGET (l),
     77                             TRUE);
     78     gtk_label_set_text (l,
     79                         msg);
     80     free (msg);
     81     return;
     82   }
     83   methods_list = json_array ();
     84   GNUNET_assert (NULL != methods_list);
     85   for (unsigned int i = 0; i<acfg->details.ok.methods_length; i++)
     86   {
     87     const struct ANASTASIS_AuthorizationMethodConfig *method
     88       = &acfg->details.ok.methods[i];
     89     json_t *mj = GNUNET_JSON_PACK (
     90       GNUNET_JSON_pack_string ("type",
     91                                method->type),
     92       TALER_JSON_pack_amount ("usage_fee",
     93                               &method->usage_fee));
     94 
     95     GNUNET_assert (0 ==
     96                    json_array_append_new (methods_list,
     97                                           mj));
     98   }
     99   pstate = GNUNET_JSON_PACK (
    100     GNUNET_JSON_pack_array_steal ("methods",
    101                                   methods_list),
    102     TALER_JSON_pack_amount ("annual_fee",
    103                             &acfg->details.ok.annual_fee),
    104     TALER_JSON_pack_amount ("truth_upload_fee",
    105                             &acfg->details.ok.truth_upload_fee),
    106     TALER_JSON_pack_amount ("liability_limit",
    107                             &acfg->details.ok.liability_limit),
    108     GNUNET_JSON_pack_string ("business_name",
    109                              acfg->details.ok.business_name),
    110     GNUNET_JSON_pack_string ("status",
    111                              "enabled"),
    112     GNUNET_JSON_pack_uint64 ("http_status",
    113                              MHD_HTTP_OK),
    114     GNUNET_JSON_pack_uint64 ("storage_limit_in_megabytes",
    115                              acfg->details.ok.storage_limit_in_megabytes),
    116     GNUNET_JSON_pack_data_auto ("provider_salt",
    117                                 &acfg->details.ok.provider_salt),
    118     GNUNET_JSON_pack_uint64 ("http_status",
    119                              acfg->http_status));
    120   button = GTK_WIDGET (gtk_builder_get_object (builder,
    121                                                "add_button"));
    122   gtk_widget_set_sensitive (button,
    123                             true);
    124   gtk_widget_set_visible (GTK_WIDGET (l),
    125                           FALSE);
    126 }
    127 
    128 
    129 /**
    130  * Function called when the user edits the URL in the "add_provider"
    131  * dialog. Updates the visibility of the 'apply/add' button.
    132  *
    133  * @param entry the entry that changed
    134  * @param user_data our `GtkBuilder *`
    135  */
    136 void
    137 add_provider_url_entry_changed_cb (GtkEntry *entry,
    138                                    gpointer user_data)
    139 {
    140   GtkBuilder *builder = GTK_BUILDER (user_data);
    141   GtkWidget *button;
    142   const char *url;
    143 
    144   json_decref (pstate);
    145   pstate = NULL;
    146   if (NULL != co)
    147   {
    148     ANASTASIS_config_cancel (co);
    149     co = NULL;
    150   }
    151   button = GTK_WIDGET (gtk_builder_get_object (builder,
    152                                                "add_button"));
    153   gtk_widget_set_sensitive (button,
    154                             false);
    155   url = gtk_editable_get_text (GTK_EDITABLE (entry));
    156   if ( (0 == strncasecmp (url,
    157                           "http://",
    158                           strlen ("http://"))) ||
    159        (0 == strncasecmp (url,
    160                           "https://",
    161                           strlen ("https://"))) )
    162   {
    163     co = ANASTASIS_get_config (AG_ctx,
    164                                url,
    165                                &config_cb,
    166                                builder);
    167     GNUNET_break (NULL != co);
    168   }
    169 }
    170 
    171 
    172 /**
    173  * Function called from the edit-provider dialog upon completion.
    174  *
    175  * @param dialog the pseudonym selection dialog
    176  * @param response_id response code from the dialog
    177  * @param user_data the builder of the dialog
    178  */
    179 void
    180 add_provider_dialog_response_cb (GtkDialog *dialog,
    181                                  gint response_id,
    182                                  gpointer user_data)
    183 {
    184   GtkBuilder *builder = GTK_BUILDER (user_data);
    185   GtkEntry *entry;
    186   const char *url;
    187   json_t *ap;
    188 
    189   if (NULL != co)
    190   {
    191     ANASTASIS_config_cancel (co);
    192     co = NULL;
    193   }
    194   if (GTK_RESPONSE_APPLY != response_id)
    195   {
    196     gtk_window_destroy (GTK_WINDOW (dialog));
    197     g_object_unref (G_OBJECT (builder));
    198     json_decref (pstate);
    199     pstate = NULL;
    200     return;
    201   }
    202   if (NULL == pstate)
    203   {
    204     GNUNET_break (0);
    205     return;
    206   }
    207   ap = json_object_get (AG_redux_state,
    208                         "authentication_providers");
    209   if (NULL == ap)
    210   {
    211     GNUNET_break (0);
    212     return;
    213   }
    214   entry = GTK_ENTRY (gtk_builder_get_object (builder,
    215                                              "url_entry"));
    216   url = gtk_editable_get_text (GTK_EDITABLE (entry));
    217   ANASTASIS_policy_discovery_more (AG_pd,
    218                                    url,
    219                                    pstate);
    220   GNUNET_break (0 ==
    221                 json_object_set_new (ap,
    222                                      url,
    223                                      pstate));
    224   pstate = NULL;
    225   gtk_window_destroy (GTK_WINDOW (dialog));
    226   g_object_unref (G_OBJECT (builder));
    227 }
    228 
    229 
    230 /**
    231  * Callback invoked if the the "Add"-provider button is clicked.
    232  *
    233  * @param object
    234  * @param user_data unused
    235  */
    236 void
    237 anastasis_gtk_add_provider_button_clicked_cb (GtkButton *object,
    238                                               gpointer user_data)
    239 {
    240   GtkWidget *ad;
    241   GtkBuilder *builder;
    242   GtkRoot *toplevel;
    243 
    244   if (NULL == AG_pd)
    245   {
    246     GNUNET_break (0);
    247     return;
    248   }
    249   builder = ANASTASIS_GTK_get_new_builder (
    250     ANASTASIS_GTK_project_data (),
    251     "anastasis_gtk_add_provider.ui",
    252     NULL);
    253   if (NULL == builder)
    254   {
    255     GNUNET_break (0);
    256     return;
    257   }
    258   ad = GTK_WIDGET (gtk_builder_get_object (builder,
    259                                            "add_provider_dialog"));
    260   toplevel = gtk_widget_get_root (GTK_WIDGET (object));
    261   gtk_window_set_transient_for (GTK_WINDOW (ad),
    262                                 GTK_WINDOW (toplevel));
    263   gtk_window_present (GTK_WINDOW (ad));
    264 }