gnunet-svn
[Top][All Lists]
Advanced

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

[taler-merchant] branch master updated: template bangs


From: gnunet
Subject: [taler-merchant] branch master updated: template bangs
Date: Fri, 21 Aug 2020 12:48:11 +0200

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

dold pushed a commit to branch master
in repository merchant.

The following commit(s) were added to refs/heads/master by this push:
     new 87a93ed  template bangs
87a93ed is described below

commit 87a93ed1607cdc5a5e3ec8e0e37d6c288d4cf5cc
Author: Florian Dold <florian.dold@gmail.com>
AuthorDate: Fri Aug 21 16:18:06 2020 +0530

    template bangs
---
 src/mustach/mustach-jansson.c      | 167 ++++++++++++++++++++++++++++++-------
 src/mustach/test_mustach_jansson.c |  38 +++++++++
 2 files changed, 176 insertions(+), 29 deletions(-)

diff --git a/src/mustach/mustach-jansson.c b/src/mustach/mustach-jansson.c
index afb8f82..2aed582 100644
--- a/src/mustach/mustach-jansson.c
+++ b/src/mustach/mustach-jansson.c
@@ -53,6 +53,15 @@ struct Context
   bool is_objiter;
 };
 
+enum Bang
+{
+  BANG_NONE,
+  BANG_I18N,
+  BANG_STRINGIFY,
+  BANG_AMOUNT_CURRENCY,
+  BANG_AMOUNT_DECIMAL,
+};
+
 struct JanssonClosure
 {
   json_t *root;
@@ -68,16 +77,25 @@ struct JanssonClosure
    * The last object we found should be iterated over.
    */
   bool found_iter;
+
+  /**
+   * Last bang we found.
+   */
+  enum Bang found_bang;
+  
+  /**
+   * Language for i18n lookups.
+   */
+  const char *lang;
 };
 
+
 static json_t *
-find (struct JanssonClosure *e, const char *name)
+walk (json_t *obj, const char *path)
 {
-  json_t *obj = e->stack[e->depth].obj;
-  char *nd = GNUNET_strdup (name);
-  char *p = nd;
   char *saveptr = NULL;
-
+  char *sp = GNUNET_strdup (path);
+  char *p = sp;
   while (true)
   {
     char *tok = strtok_r (p, ".", &saveptr);
@@ -88,8 +106,51 @@ find (struct JanssonClosure *e, const char *name)
       break;
     p = NULL;
   }
+  GNUNET_free (sp);
+  return obj;
+}
+
+
+static json_t *
+find (struct JanssonClosure *e, const char *name)
+{
+  json_t *obj = NULL;
+  char *path = GNUNET_strdup (name);
+  char *bang;
+
+  bang = strchr (path, '!');
+
+  e->found_bang = BANG_NONE;
+
+  if (NULL != bang)
+  {
+    *bang = 0;
+    bang++;
+
+    if (0 == strcmp (bang, "i18n"))
+      e->found_bang = BANG_I18N;
+    else if (0 == strcmp(bang, "stringify"))
+      e->found_bang = BANG_STRINGIFY;
+    else if (0 == strcmp(bang, "amount_decimal"))
+      e->found_bang = BANG_AMOUNT_CURRENCY;
+    else if (0 == strcmp(bang, "amount_currency"))
+      e->found_bang = BANG_AMOUNT_DECIMAL;
+  }
+
+  if (BANG_I18N == e->found_bang && NULL != e->lang)
+  {
+    char *aug_path;
+    GNUNET_asprintf (&aug_path, "%s_i18n.%s", path, e->lang);
+    obj = walk (e->stack[e->depth].obj, aug_path);
+    GNUNET_free (aug_path);
+  }
+
+  if (NULL == obj)
+  {
+    obj = walk (e->stack[e->depth].obj, path);
+  }
 
-  GNUNET_free (nd);
+  GNUNET_free (path);
 
   return obj;
 }
@@ -104,6 +165,7 @@ start(void *closure)
   e->stack[0].obj = e->root;
   e->stack[0].index = 0;
   e->stack[0].count = 1;
+  e->lang = json_string_value (json_object_get (e->root, "$language"));
   return MUSTACH_OK;
 }
 
@@ -139,21 +201,6 @@ emituw (void *closure, const char *buffer, size_t size, 
int escape, FILE *file)
 }
 
 
-static const char *
-item (struct JanssonClosure *e, const char *name)
-{
-  json_t *obj;
-
-  if ( (0 == strcmp (name, "*") ) &&
-       (e->stack[e->depth].is_objiter ) )
-    return json_object_iter_key (e->stack[e->depth].iter);
-  obj = find (e, name);
-  if (NULL != obj)
-    return json_string_value (obj);
-  return NULL;
-}
-
-
 static int
 enter(void *closure, const char *name)
 {
@@ -230,7 +277,8 @@ next (void *closure)
   return 1;
 }
 
-static int leave (void *closure)
+static int
+leave (void *closure)
 {
   struct JanssonClosure *e = closure;
   if (e->depth <= 0)
@@ -239,16 +287,77 @@ static int leave (void *closure)
   return 0;
 }
 
-static int get (void *closure, const char *name, struct mustach_sbuf *sbuf)
+static void
+freecb (void *v)
+{
+  free (v);
+}
+
+static int
+get (void *closure, const char *name, struct mustach_sbuf *sbuf)
 {
   struct JanssonClosure *e = closure;
-  const char *s;
+  json_t *obj;
 
-  s = item (e, name);
-  if (s)
-    sbuf->value = s;
-  else
-    sbuf->value = "";
+  if ( (0 == strcmp (name, "*") ) &&
+       (e->stack[e->depth].is_objiter ) )
+  {
+    sbuf->value = json_object_iter_key (e->stack[e->depth].iter);
+    return MUSTACH_OK;
+  }
+  obj = find (e, name);
+  if (NULL != obj)
+  {
+    switch (e->found_bang)
+    {
+      case BANG_I18N:
+      case BANG_NONE:
+        {
+          const char *s = json_string_value (obj);
+          if (NULL != s)
+          {
+            sbuf->value = s;
+            return MUSTACH_OK;
+          }
+        }
+        break;
+      case BANG_STRINGIFY:
+        sbuf->value = json_dumps (obj, JSON_INDENT (2));
+        sbuf->freecb = freecb;
+        return MUSTACH_OK;
+      case BANG_AMOUNT_DECIMAL:
+        {
+          char *s;
+          char *c;
+          if (!json_is_string (obj))
+            break;
+          s = strdup (json_string_value (obj));
+          c = strchr (s, ':');
+          if (NULL != c)
+            *c = 0;
+          sbuf->value = s;
+          sbuf->freecb = freecb;
+          return MUSTACH_OK;
+        }
+        break;
+      case BANG_AMOUNT_CURRENCY:
+        {
+          const char *s;
+          if (!json_is_string (obj))
+            break;
+          s = json_string_value (obj);
+          s = strchr (s, ':');
+          if (NULL == s)
+            break;
+          sbuf->value = s + 1;
+          return MUSTACH_OK;
+        }
+        break;
+      default:
+        break;
+    }
+  }
+  sbuf->value = "";
   return MUSTACH_OK;
 }
 
diff --git a/src/mustach/test_mustach_jansson.c 
b/src/mustach/test_mustach_jansson.c
index 8f1e37b..a211d87 100644
--- a/src/mustach/test_mustach_jansson.c
+++ b/src/mustach/test_mustach_jansson.c
@@ -43,6 +43,7 @@ main (int argc,
   json_t *root = json_object ();
   json_t *arr = json_array ();
   json_t *obj = json_object();
+  json_t *contract;
   /* test 1 */
   char *t1 = "hello world";
   char *x1 = "hello world";
@@ -58,22 +59,59 @@ main (int argc,
   /* test 5 */
   char *t5 = "hello {{# v3 }}{{ y }}/{{ x }}{{ z }}{{/ v3 }}";
   char *x5 = "hello quux/baz";
+  /* test 6 */
+  char *t6 = "hello {{ v2!stringify }}";
+  char *x6 = "hello [\n  \"foo\",\n  \"bar\"\n]";
+  /* test 7 */
+  char *t7 = "amount: {{ amt!amount_decimal }} {{ amt!amount_currency }}";
+  char *x7 = "amount: 123.00 EUR";
+
+  /* contract test 8 (contract) */
+  char *tc = "summary: {{ summary!i18n }}";
+  char *xc_en = "summary: ENGLISH";
+  char *xc_de = "summary: DEUTSCH";
+  char *xc_fr = "summary: FRANCAISE";
 
   json_object_set_new (root, "v1", json_string ("world"));
   json_array_append_new (arr, json_string ("foo"));
   json_array_append_new (arr, json_string ("bar"));
   json_object_set_new (root, "v2", arr);
   json_object_set_new (root, "v3", obj);
+  json_object_set_new (root, "amt", json_string("EUR:123.00"));
   json_object_set_new (obj, "x", json_string ("baz"));
   json_object_set_new (obj, "y", json_string ("quux"));
 
+  contract = json_pack("{ s:s, s:{s:s, s:s}}",
+                       "summary",
+                       "ENGLISH",
+                       "summary_i18n",
+                       "de",
+                       "DEUTSCH",
+                       "fr",
+                       "FRANCAISE");
+  GNUNET_assert (NULL != contract);
+
   assert_template (t1, root, x1);
   assert_template (t2, root, x2);
   assert_template (t3, root, x3);
   assert_template (t4, root, x4);
   assert_template (t5, root, x5);
+  assert_template (t6, root, x6);
+  assert_template (t7, root, x7);
+
+  assert_template (tc, contract, xc_en);
+
+  json_object_set_new (contract, "$language", json_string ("de"));
+  assert_template (tc, contract, xc_de);
+
+  json_object_set_new (contract, "$language", json_string ("fr"));
+  assert_template (tc, contract, xc_fr);
+
+  json_object_set_new (contract, "$language", json_string ("it"));
+  assert_template (tc, contract, xc_en);
 
   json_decref (root);
+  json_decref (contract);
 
   return 0;
 }

-- 
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]