diff options
author | Christian Grothoff <christian@grothoff.org> | 2021-09-02 14:10:54 +0200 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2021-09-02 14:10:58 +0200 |
commit | 4b8dc55c4330df6a3d2a552985afdd6a80737405 (patch) | |
tree | 3ca385ba66a0d39165765be0ca6ca13d415744e0 | |
parent | 98d9dfb8c8637b8902e8b7f249834f807fa3e322 (diff) | |
download | merchant-4b8dc55c4330df6a3d2a552985afdd6a80737405.tar.gz merchant-4b8dc55c4330df6a3d2a552985afdd6a80737405.zip |
fix internal APIs and implemnetation to match new UUID specification based on application-defined strings; implement test for order creation with locks (#6932)
-rw-r--r-- | src/backend/taler-merchant-httpd_private-post-orders.c | 25 | ||||
-rw-r--r-- | src/include/taler_merchant_service.h | 4 | ||||
-rw-r--r-- | src/lib/merchant_api_lock_product.c | 6 | ||||
-rw-r--r-- | src/lib/merchant_api_post_orders.c | 6 | ||||
-rwxr-xr-x | src/testing/test_merchant_product_creation.sh | 68 | ||||
-rw-r--r-- | src/testing/testing_api_cmd_lock_product.c | 12 | ||||
-rw-r--r-- | src/testing/testing_api_cmd_post_orders.c | 14 |
7 files changed, 88 insertions, 47 deletions
diff --git a/src/backend/taler-merchant-httpd_private-post-orders.c b/src/backend/taler-merchant-httpd_private-post-orders.c index d6290eff..2706e511 100644 --- a/src/backend/taler-merchant-httpd_private-post-orders.c +++ b/src/backend/taler-merchant-httpd_private-post-orders.c | |||
@@ -1478,21 +1478,10 @@ TMH_private_post_orders (const struct TMH_RequestHandler *rh, | |||
1478 | json_array_size (uuid)); | 1478 | json_array_size (uuid)); |
1479 | for (unsigned int i = 0; i<uuids_len; i++) | 1479 | for (unsigned int i = 0; i<uuids_len; i++) |
1480 | { | 1480 | { |
1481 | const char *error_name; | 1481 | json_t *ui = json_array_get (uuid, |
1482 | unsigned int error_line; | 1482 | i); |
1483 | const char *uuidsi; | ||
1484 | struct GNUNET_JSON_Specification ispec[] = { | ||
1485 | GNUNET_JSON_spec_string ("uuid", | ||
1486 | &uuidsi), | ||
1487 | GNUNET_JSON_spec_end () | ||
1488 | }; | ||
1489 | 1483 | ||
1490 | ret = GNUNET_JSON_parse (json_array_get (uuid, | 1484 | if (! json_is_string (ui)) |
1491 | i), | ||
1492 | ispec, | ||
1493 | &error_name, | ||
1494 | &error_line); | ||
1495 | if (GNUNET_OK != ret) | ||
1496 | { | 1485 | { |
1497 | GNUNET_break_op (0); | 1486 | GNUNET_break_op (0); |
1498 | GNUNET_array_grow (ips, | 1487 | GNUNET_array_grow (ips, |
@@ -1503,16 +1492,14 @@ TMH_private_post_orders (const struct TMH_RequestHandler *rh, | |||
1503 | 0); | 1492 | 0); |
1504 | GNUNET_JSON_parse_free (spec); | 1493 | GNUNET_JSON_parse_free (spec); |
1505 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 1494 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1506 | "UUID parsing failed at #%u: %s:%u\n", | 1495 | "UUID parsing failed at #%u\n", |
1507 | i, | 1496 | i); |
1508 | error_name, | ||
1509 | error_line); | ||
1510 | return TALER_MHD_reply_with_error (connection, | 1497 | return TALER_MHD_reply_with_error (connection, |
1511 | MHD_HTTP_BAD_REQUEST, | 1498 | MHD_HTTP_BAD_REQUEST, |
1512 | TALER_EC_GENERIC_PARAMETER_MALFORMED, | 1499 | TALER_EC_GENERIC_PARAMETER_MALFORMED, |
1513 | "lock_uuids"); | 1500 | "lock_uuids"); |
1514 | } | 1501 | } |
1515 | TMH_uuid_from_string (uuidsi, | 1502 | TMH_uuid_from_string (json_string_value (ui), |
1516 | &uuids[i]); | 1503 | &uuids[i]); |
1517 | } | 1504 | } |
1518 | } | 1505 | } |
diff --git a/src/include/taler_merchant_service.h b/src/include/taler_merchant_service.h index cc44e660..cc3063f6 100644 --- a/src/include/taler_merchant_service.h +++ b/src/include/taler_merchant_service.h | |||
@@ -1213,7 +1213,7 @@ TALER_MERCHANT_product_lock ( | |||
1213 | struct GNUNET_CURL_Context *ctx, | 1213 | struct GNUNET_CURL_Context *ctx, |
1214 | const char *backend_url, | 1214 | const char *backend_url, |
1215 | const char *product_id, | 1215 | const char *product_id, |
1216 | const struct GNUNET_Uuid *uuid, | 1216 | const char *uuid, |
1217 | struct GNUNET_TIME_Relative duration, | 1217 | struct GNUNET_TIME_Relative duration, |
1218 | uint32_t quantity, | 1218 | uint32_t quantity, |
1219 | TALER_MERCHANT_ProductLockCallback cb, | 1219 | TALER_MERCHANT_ProductLockCallback cb, |
@@ -1444,7 +1444,7 @@ TALER_MERCHANT_orders_post2 ( | |||
1444 | unsigned int inventory_products_length, | 1444 | unsigned int inventory_products_length, |
1445 | const struct TALER_MERCHANT_InventoryProduct inventory_products[], | 1445 | const struct TALER_MERCHANT_InventoryProduct inventory_products[], |
1446 | unsigned int uuids_length, | 1446 | unsigned int uuids_length, |
1447 | const struct GNUNET_Uuid uuids[], | 1447 | const char *uuids[], |
1448 | bool create_token, | 1448 | bool create_token, |
1449 | TALER_MERCHANT_PostOrdersCallback cb, | 1449 | TALER_MERCHANT_PostOrdersCallback cb, |
1450 | void *cb_cls); | 1450 | void *cb_cls); |
diff --git a/src/lib/merchant_api_lock_product.c b/src/lib/merchant_api_lock_product.c index a3c345d5..3a3caaeb 100644 --- a/src/lib/merchant_api_lock_product.c +++ b/src/lib/merchant_api_lock_product.c | |||
@@ -159,7 +159,7 @@ TALER_MERCHANT_product_lock ( | |||
159 | struct GNUNET_CURL_Context *ctx, | 159 | struct GNUNET_CURL_Context *ctx, |
160 | const char *backend_url, | 160 | const char *backend_url, |
161 | const char *product_id, | 161 | const char *product_id, |
162 | const struct GNUNET_Uuid *uuid, | 162 | const char *uuid, |
163 | struct GNUNET_TIME_Relative duration, | 163 | struct GNUNET_TIME_Relative duration, |
164 | uint32_t quantity, | 164 | uint32_t quantity, |
165 | TALER_MERCHANT_ProductLockCallback cb, | 165 | TALER_MERCHANT_ProductLockCallback cb, |
@@ -169,8 +169,8 @@ TALER_MERCHANT_product_lock ( | |||
169 | json_t *req_obj; | 169 | json_t *req_obj; |
170 | 170 | ||
171 | req_obj = GNUNET_JSON_PACK ( | 171 | req_obj = GNUNET_JSON_PACK ( |
172 | GNUNET_JSON_pack_data_auto ("lock_uuid", | 172 | GNUNET_JSON_pack_string ("lock_uuid", |
173 | uuid), | 173 | uuid), |
174 | GNUNET_JSON_pack_time_rel ("duration", | 174 | GNUNET_JSON_pack_time_rel ("duration", |
175 | duration), | 175 | duration), |
176 | GNUNET_JSON_pack_uint64 ("quantity", | 176 | GNUNET_JSON_pack_uint64 ("quantity", |
diff --git a/src/lib/merchant_api_post_orders.c b/src/lib/merchant_api_post_orders.c index b7e406f4..2cd16cba 100644 --- a/src/lib/merchant_api_post_orders.c +++ b/src/lib/merchant_api_post_orders.c | |||
@@ -247,7 +247,7 @@ TALER_MERCHANT_orders_post2 ( | |||
247 | unsigned int inventory_products_length, | 247 | unsigned int inventory_products_length, |
248 | const struct TALER_MERCHANT_InventoryProduct inventory_products[], | 248 | const struct TALER_MERCHANT_InventoryProduct inventory_products[], |
249 | unsigned int uuids_length, | 249 | unsigned int uuids_length, |
250 | const struct GNUNET_Uuid uuids[], | 250 | const char *uuids[], |
251 | bool create_token, | 251 | bool create_token, |
252 | TALER_MERCHANT_PostOrdersCallback cb, | 252 | TALER_MERCHANT_PostOrdersCallback cb, |
253 | void *cb_cls) | 253 | void *cb_cls) |
@@ -310,9 +310,7 @@ TALER_MERCHANT_orders_post2 ( | |||
310 | { | 310 | { |
311 | json_t *u; | 311 | json_t *u; |
312 | 312 | ||
313 | u = GNUNET_JSON_PACK ( | 313 | u = json_string (uuids[i]); |
314 | GNUNET_JSON_pack_data_auto ("uuid", | ||
315 | &uuids[i])); | ||
316 | GNUNET_assert (0 == | 314 | GNUNET_assert (0 == |
317 | json_array_append_new (ua, | 315 | json_array_append_new (ua, |
318 | u)); | 316 | u)); |
diff --git a/src/testing/test_merchant_product_creation.sh b/src/testing/test_merchant_product_creation.sh index 938a13d3..78b95d4e 100755 --- a/src/testing/test_merchant_product_creation.sh +++ b/src/testing/test_merchant_product_creation.sh | |||
@@ -85,20 +85,47 @@ then | |||
85 | cat $LAST_RESPONSE | 85 | cat $LAST_RESPONSE |
86 | exit 1 | 86 | exit 1 |
87 | fi | 87 | fi |
88 | |||
89 | echo OK | 88 | echo OK |
90 | 89 | ||
90 | MANAGED_PRODUCT_ID=$(echo $MANAGED_PRODUCT_TEMPLATE | jq -r '.product_id') | ||
91 | |||
92 | echo -n "Locking inventory ..." | ||
93 | |||
94 | STATUS=$(curl "http://localhost:9966/instances/default/private/products/${MANAGED_PRODUCT_ID}/lock" \ | ||
95 | -d '{"lock_uuid":"luck","duration":{"d_ms": 100000},"quantity":10}' \ | ||
96 | -w "%{http_code}" -s -o $LAST_RESPONSE) | ||
97 | |||
98 | if [ "$STATUS" != "410" ] | ||
99 | then | ||
100 | echo 'should respond gone, lock failed. got:' $STATUS `cat $LAST_RESPONSE` | ||
101 | exit 1 | ||
102 | fi | ||
103 | |||
104 | echo -n "." | ||
105 | |||
106 | STATUS=$(curl "http://localhost:9966/instances/default/private/products/${MANAGED_PRODUCT_ID}/lock" \ | ||
107 | -d '{"lock_uuid":"luck","duration":{"d_ms": 100000},"quantity":1}' \ | ||
108 | -w "%{http_code}" -s -o $LAST_RESPONSE) | ||
109 | |||
110 | if [ "$STATUS" != "204" ] | ||
111 | then | ||
112 | echo 'should respond ok, lock created. got:' $STATUS `cat $LAST_RESPONSE` | ||
113 | exit 1 | ||
114 | fi | ||
115 | |||
116 | echo " OK" | ||
117 | |||
118 | |||
91 | echo -n "Creating order to be paid..." | 119 | echo -n "Creating order to be paid..." |
92 | 120 | ||
93 | MANAGED_PRODUCT_ID=$(echo $MANAGED_PRODUCT_TEMPLATE | jq -r '.product_id') | ||
94 | 121 | ||
95 | STATUS=$(curl 'http://localhost:9966/instances/default/private/orders' \ | 122 | STATUS=$(curl 'http://localhost:9966/instances/default/private/orders' \ |
96 | -d '{"order":{"amount":"TESTKUDOS:1","summary":"payme"},"inventory_products":[{"product_id":"'$MANAGED_PRODUCT_ID'","quantity":1}]}' \ | 123 | -d '{"order":{"amount":"TESTKUDOS:1","summary":"payme"},"inventory_products":[{"product_id":"'${MANAGED_PRODUCT_ID}'","quantity":1}]}' \ |
97 | -w "%{http_code}" -s -o $LAST_RESPONSE) | 124 | -w "%{http_code}" -s -o $LAST_RESPONSE) |
98 | 125 | ||
99 | if [ "$STATUS" != "200" ] | 126 | if [ "$STATUS" != "200" ] |
100 | then | 127 | then |
101 | echo 'should response ok, order created. got:' $STATUS `cat $LAST_RESPONSE` | 128 | echo 'should respond ok, order created. got:' $STATUS `cat $LAST_RESPONSE` |
102 | exit 1 | 129 | exit 1 |
103 | fi | 130 | fi |
104 | 131 | ||
@@ -110,13 +137,38 @@ STATUS=$(curl "http://localhost:9966/instances/default/private/orders/${ORDER_ID | |||
110 | 137 | ||
111 | if [ "$STATUS" != "200" ] | 138 | if [ "$STATUS" != "200" ] |
112 | then | 139 | then |
113 | echo 'should response ok, getting order info before claming it. got:' $STATUS `cat $LAST_RESPONSE` | 140 | echo 'should respond ok, getting order info before claming it. got:' $STATUS `cat $LAST_RESPONSE` |
114 | exit 1 | 141 | exit 1 |
115 | fi | 142 | fi |
116 | |||
117 | PAY_URL=`jq -e -r .taler_pay_uri < $LAST_RESPONSE` | 143 | PAY_URL=`jq -e -r .taler_pay_uri < $LAST_RESPONSE` |
118 | 144 | ||
119 | echo OK | 145 | echo -n "." |
146 | |||
147 | STATUS=$(curl 'http://localhost:9966/instances/default/private/orders' \ | ||
148 | -d '{"order":{"amount":"TESTKUDOS:1","summary":"payme"},"inventory_products":[{"product_id":"'${MANAGED_PRODUCT_ID}'","quantity":1}]}' \ | ||
149 | -w "%{http_code}" -s -o $LAST_RESPONSE) | ||
150 | |||
151 | if [ "$STATUS" != "410" ] | ||
152 | then | ||
153 | echo 'should respond out of stock (what remains is locked). got:' $STATUS `cat $LAST_RESPONSE` | ||
154 | exit 1 | ||
155 | fi | ||
156 | |||
157 | echo -n "." | ||
158 | |||
159 | # Using the 'luck' inventory lock, order creation should work. | ||
160 | STATUS=$(curl 'http://localhost:9966/instances/default/private/orders' \ | ||
161 | -d '{"order":{"amount":"TESTKUDOS:1","summary":"payme"},"lock_uuids":["luck"],"inventory_products":[{"product_id":"'$MANAGED_PRODUCT_ID'","quantity":1}]}' \ | ||
162 | -w "%{http_code}" -s -o $LAST_RESPONSE) | ||
163 | |||
164 | if [ "$STATUS" != "200" ] | ||
165 | then | ||
166 | echo 'should respond ok, lock should apply. got:' $STATUS `cat $LAST_RESPONSE` | ||
167 | exit 1 | ||
168 | fi | ||
169 | |||
170 | |||
171 | echo " OK" | ||
120 | 172 | ||
121 | echo -n "First withdraw wallet" | 173 | echo -n "First withdraw wallet" |
122 | rm $WALLET_DB | 174 | rm $WALLET_DB |
@@ -146,7 +198,7 @@ STATUS=$(curl "http://localhost:9966/instances/default/private/orders/${ORDER_ID | |||
146 | 198 | ||
147 | if [ "$STATUS" != "200" ] | 199 | if [ "$STATUS" != "200" ] |
148 | then | 200 | then |
149 | echo 'should response ok, after pay. got:' $STATUS `cat $LAST_RESPONSE` | 201 | echo 'should respond ok, after pay. got:' $STATUS `cat $LAST_RESPONSE` |
150 | exit 1 | 202 | exit 1 |
151 | fi | 203 | fi |
152 | 204 | ||
diff --git a/src/testing/testing_api_cmd_lock_product.c b/src/testing/testing_api_cmd_lock_product.c index abb5920c..49f815d6 100644 --- a/src/testing/testing_api_cmd_lock_product.c +++ b/src/testing/testing_api_cmd_lock_product.c | |||
@@ -57,7 +57,7 @@ struct LockProductState | |||
57 | /** | 57 | /** |
58 | * UUID that identifies the client holding the lock | 58 | * UUID that identifies the client holding the lock |
59 | */ | 59 | */ |
60 | struct GNUNET_Uuid uuid; | 60 | char *uuid; |
61 | 61 | ||
62 | /** | 62 | /** |
63 | * duration how long should the lock be held | 63 | * duration how long should the lock be held |
@@ -138,7 +138,7 @@ lock_product_run (void *cls, | |||
138 | pis->iph = TALER_MERCHANT_product_lock (is->ctx, | 138 | pis->iph = TALER_MERCHANT_product_lock (is->ctx, |
139 | pis->merchant_url, | 139 | pis->merchant_url, |
140 | pis->product_id, | 140 | pis->product_id, |
141 | &pis->uuid, | 141 | pis->uuid, |
142 | pis->duration, | 142 | pis->duration, |
143 | pis->quantity, | 143 | pis->quantity, |
144 | &lock_product_cb, | 144 | &lock_product_cb, |
@@ -166,6 +166,7 @@ lock_product_cleanup (void *cls, | |||
166 | "POST /product/$ID/lock operation did not complete\n"); | 166 | "POST /product/$ID/lock operation did not complete\n"); |
167 | TALER_MERCHANT_product_lock_cancel (pis->iph); | 167 | TALER_MERCHANT_product_lock_cancel (pis->iph); |
168 | } | 168 | } |
169 | GNUNET_free (pis->uuid); | ||
169 | GNUNET_free (pis); | 170 | GNUNET_free (pis); |
170 | } | 171 | } |
171 | 172 | ||
@@ -188,7 +189,7 @@ lock_product_traits (void *cls, | |||
188 | struct LockProductState *lps = cls; | 189 | struct LockProductState *lps = cls; |
189 | 190 | ||
190 | struct TALER_TESTING_Trait traits[] = { | 191 | struct TALER_TESTING_Trait traits[] = { |
191 | TALER_TESTING_make_trait_uuid (0, &lps->uuid), | 192 | TALER_TESTING_make_trait_string (0, lps->uuid), |
192 | TALER_TESTING_trait_end () | 193 | TALER_TESTING_trait_end () |
193 | }; | 194 | }; |
194 | 195 | ||
@@ -209,14 +210,17 @@ TALER_TESTING_cmd_merchant_lock_product ( | |||
209 | unsigned int http_status) | 210 | unsigned int http_status) |
210 | { | 211 | { |
211 | struct LockProductState *pis; | 212 | struct LockProductState *pis; |
213 | struct GNUNET_Uuid uuid; | ||
212 | 214 | ||
213 | pis = GNUNET_new (struct LockProductState); | 215 | pis = GNUNET_new (struct LockProductState); |
214 | pis->merchant_url = merchant_url; | 216 | pis->merchant_url = merchant_url; |
215 | pis->product_id = product_id; | 217 | pis->product_id = product_id; |
216 | pis->http_status = http_status; | 218 | pis->http_status = http_status; |
217 | GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK, | 219 | GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK, |
218 | &pis->uuid, | 220 | &uuid, |
219 | sizeof (struct GNUNET_Uuid)); | 221 | sizeof (struct GNUNET_Uuid)); |
222 | pis->uuid = GNUNET_STRINGS_data_to_string_alloc (&uuid, | ||
223 | sizeof (uuid)); | ||
220 | pis->duration = duration; | 224 | pis->duration = duration; |
221 | pis->quantity = quantity; | 225 | pis->quantity = quantity; |
222 | 226 | ||
diff --git a/src/testing/testing_api_cmd_post_orders.c b/src/testing/testing_api_cmd_post_orders.c index 5b9e533f..f7c00388 100644 --- a/src/testing/testing_api_cmd_post_orders.c +++ b/src/testing/testing_api_cmd_post_orders.c | |||
@@ -1,6 +1,6 @@ | |||
1 | /* | 1 | /* |
2 | This file is part of TALER | 2 | This file is part of TALER |
3 | Copyright (C) 2014-2018 Taler Systems SA | 3 | Copyright (C) 2014-2021 Taler Systems SA |
4 | 4 | ||
5 | TALER is free software; you can redistribute it and/or modify | 5 | TALER is free software; you can redistribute it and/or modify |
6 | it under the terms of the GNU General Public License as | 6 | it under the terms of the GNU General Public License as |
@@ -439,7 +439,7 @@ orders_run2 (void *cls, | |||
439 | char *token; | 439 | char *token; |
440 | struct TALER_MERCHANT_InventoryProduct *products = NULL; | 440 | struct TALER_MERCHANT_InventoryProduct *products = NULL; |
441 | unsigned int products_length = 0; | 441 | unsigned int products_length = 0; |
442 | struct GNUNET_Uuid *locks = NULL; | 442 | const char **locks = NULL; |
443 | unsigned int locks_length = 0; | 443 | unsigned int locks_length = 0; |
444 | 444 | ||
445 | ps->is = is; | 445 | ps->is = is; |
@@ -527,16 +527,16 @@ orders_run2 (void *cls, | |||
527 | token = strtok (NULL, ";")) | 527 | token = strtok (NULL, ";")) |
528 | { | 528 | { |
529 | const struct TALER_TESTING_Command *lock_cmd; | 529 | const struct TALER_TESTING_Command *lock_cmd; |
530 | struct GNUNET_Uuid *uuid; | 530 | const char *uuid; |
531 | 531 | ||
532 | lock_cmd = TALER_TESTING_interpreter_lookup_command ( | 532 | lock_cmd = TALER_TESTING_interpreter_lookup_command ( |
533 | is, | 533 | is, |
534 | token); | 534 | token); |
535 | 535 | ||
536 | if (GNUNET_OK != | 536 | if (GNUNET_OK != |
537 | TALER_TESTING_get_trait_uuid (lock_cmd, | 537 | TALER_TESTING_get_trait_string (lock_cmd, |
538 | 0, | 538 | 0, |
539 | &uuid)) | 539 | &uuid)) |
540 | { | 540 | { |
541 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 541 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
542 | "Could not fetch lock uuid\n"); | 542 | "Could not fetch lock uuid\n"); |
@@ -546,7 +546,7 @@ orders_run2 (void *cls, | |||
546 | 546 | ||
547 | GNUNET_array_append (locks, | 547 | GNUNET_array_append (locks, |
548 | locks_length, | 548 | locks_length, |
549 | *uuid); | 549 | uuid); |
550 | } | 550 | } |
551 | ps->po = TALER_MERCHANT_orders_post2 (is->ctx, | 551 | ps->po = TALER_MERCHANT_orders_post2 (is->ctx, |
552 | ps->merchant_url, | 552 | ps->merchant_url, |