diff options
Diffstat (limited to 'src/backend/taler-merchant-httpd_get-orders-ID.c')
-rw-r--r-- | src/backend/taler-merchant-httpd_get-orders-ID.c | 154 |
1 files changed, 117 insertions, 37 deletions
diff --git a/src/backend/taler-merchant-httpd_get-orders-ID.c b/src/backend/taler-merchant-httpd_get-orders-ID.c index 72b96eb8..0025a6ce 100644 --- a/src/backend/taler-merchant-httpd_get-orders-ID.c +++ b/src/backend/taler-merchant-httpd_get-orders-ID.c @@ -78,7 +78,12 @@ struct GetOrderData /** * Database event we are waiting on to be resuming. */ - struct GNUNET_DB_EventHandler *eh; + struct GNUNET_DB_EventHandler *pay_eh; + + /** + * Database event we are waiting on to be resuming. + */ + struct GNUNET_DB_EventHandler *refund_eh; /** * Which merchant instance is this for? @@ -200,17 +205,75 @@ resume_by_event (void *cls, size_t extra_size) { struct GetOrderData *god = cls; + struct GNUNET_AsyncScopeSave old; - (void) extra; - (void) extra_size; + GNUNET_async_scope_enter (&god->hc->async_scope_id, + &old); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received event for %s with argument `%.*s`\n", + god->order_id, + (int) extra_size, + (const char *) extra); if (! god->suspended) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Not suspended, ignoring event\n"); + GNUNET_async_scope_restore (&old); return; /* duplicate event is possible */ + } + if (GNUNET_TIME_absolute_is_future (god->sc.long_poll_timeout) && + god->sc.awaiting_refund) + { + char *as; + struct TALER_Amount a; + + if (0 == extra_size) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No amount given, but need refund above threshold\n"); + GNUNET_async_scope_restore (&old); + return; /* not relevant */ + } + as = GNUNET_strndup (extra, + extra_size); + if (GNUNET_OK != + TALER_string_to_amount (as, + &a)) + { + GNUNET_break (0); + GNUNET_async_scope_restore (&old); + return; + } + if (GNUNET_OK != + TALER_amount_cmp_currency (&god->sc.refund_expected, + &a)) + { + GNUNET_break (0); + GNUNET_async_scope_restore (&old); + return; /* bad currency!? */ + } + if (1 == TALER_amount_cmp (&god->sc.refund_expected, + &a)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Amount too small to trigger resuming\n"); + GNUNET_async_scope_restore (&old); + return; /* refund too small */ + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Resuming (%d/%d) by event with argument `%.*s`\n", + (int) GNUNET_TIME_absolute_is_future (god->sc.long_poll_timeout), + god->sc.awaiting_refund, + (int) extra_size, + (const char *) extra); god->suspended = false; - GNUNET_CONTAINER_DLL_insert (god_head, + GNUNET_CONTAINER_DLL_remove (god_head, god_tail, god); MHD_resume_connection (god->sc.con); TALER_MHD_daemon_trigger (); /* we resumed, kick MHD */ + GNUNET_async_scope_restore (&old); } @@ -222,7 +285,7 @@ resume_by_event (void *cls, static void suspend_god (struct GetOrderData *god) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suspending GET /orders/%s\n", god->order_id); if (NULL != god->contract_terms) @@ -236,14 +299,7 @@ suspend_god (struct GetOrderData *god) GNUNET_CONTAINER_DLL_insert (god_head, god_tail, god); - TMH_long_poll_suspend (god->order_id, - god->session_id, - god->fulfillment_url, - god->hc->instance, - &god->sc, - god->sc.awaiting_refund - ? &god->sc.refund_expected - : NULL); + MHD_suspend_connection (god->sc.con); } @@ -536,7 +592,7 @@ send_pay_request (struct GetOrderData *god, (NULL == already_paid_order_id) ) { /* long polling: do not queue a response, suspend connection instead */ - GNUNET_log (GNUNET_ERROR_TYPE_INFO, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suspending request: long polling for payment\n"); suspend_god (god); return MHD_YES; @@ -726,10 +782,15 @@ god_cleanup (void *cls) json_decref (god->contract_terms); god->contract_terms = NULL; } - if (NULL != god->eh) + if (NULL != god->refund_eh) + { + TMH_db->event_listen_cancel (god->refund_eh); + god->refund_eh = NULL; + } + if (NULL != god->pay_eh) { - TMH_db->event_listen_cancel (god->eh); - god->eh = NULL; + TMH_db->event_listen_cancel (god->pay_eh); + god->pay_eh = NULL; } GNUNET_free (god); } @@ -824,6 +885,9 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, ? 0 == strcasecmp (await_refund_obtained_s, "yes") : false; + if (god->sc.awaiting_refund_obtained) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Awaiting refund obtained\n"); } { @@ -847,6 +911,9 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, "refund"); } god->sc.awaiting_refund = true; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Awaiting minimum refund of %s\n", + min_refund); } } @@ -886,37 +953,50 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, = GNUNET_TIME_relative_to_absolute (timeout); if (! GNUNET_TIME_relative_is_zero (timeout)) { - if (god->sc.awaiting_refund) + if (god->sc.awaiting_refund || + god->sc.awaiting_refund_obtained) { - struct TMH_OrderPayEvent refund_eh = { +#ifndef TALER_API_VERSION +#define TALER_DBEVENT_MERCHANT_REFUND_OBTAINED 1104 +#endif + struct TMH_OrderPayEventP refund_eh = { .header.size = htons (sizeof (refund_eh)), - .header.type = htons (TALER_DBEVENT_MERCHANT_ORDER_REFUND) + .header.type = htons (god->sc.awaiting_refund_obtained + ? TALER_DBEVENT_MERCHANT_REFUND_OBTAINED + : TALER_DBEVENT_MERCHANT_ORDER_REFUND), + .merchant_pub = hc->instance->merchant_pub }; GNUNET_CRYPTO_hash (god->order_id, strlen (god->order_id), &refund_eh.h_order_id); - god->eh = TMH_db->event_listen (TMH_db->cls, - &refund_eh.header, - timeout, - &resume_by_event, - god); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Subscribing to refunds on %s\n", + god->order_id); + god->refund_eh = TMH_db->event_listen (TMH_db->cls, + &refund_eh.header, + timeout, + &resume_by_event, + god); } - else /* ! waiting for refund */ { - struct TMH_OrderPayEvent pay_eh = { + struct TMH_OrderPayEventP pay_eh = { .header.size = htons (sizeof (pay_eh)), - .header.type = htons (TALER_DBEVENT_MERCHANT_ORDER_PAID) + .header.type = htons (TALER_DBEVENT_MERCHANT_ORDER_PAID), + .merchant_pub = hc->instance->merchant_pub }; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Subscribing to payments on %s\n", + god->order_id); GNUNET_CRYPTO_hash (god->order_id, strlen (god->order_id), &pay_eh.h_order_id); - god->eh = TMH_db->event_listen (TMH_db->cls, - &pay_eh.header, - timeout, - &resume_by_event, - god); + god->pay_eh = TMH_db->event_listen (TMH_db->cls, + &pay_eh.header, + timeout, + &resume_by_event, + god); } } /* end of timeout non-zero */ } /* end of HTML generation NOT requested */ @@ -1156,7 +1236,7 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, public_reorder_url)); } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Claim token or contract matched\n"); if ( (NULL != god->session_id) && @@ -1276,8 +1356,8 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, ( (! god->refunded) || (1 != TALER_amount_cmp (&god->refund_amount, &god->sc.refund_expected)) )) || - ((god->sc.awaiting_refund_obtained) && - (god->refund_available)) ) + ( (god->sc.awaiting_refund_obtained) && + (god->refund_available) ) ) { /* Client is waiting for a refund larger than what we have, suspend until timeout */ @@ -1292,7 +1372,7 @@ TMH_get_orders_ID (const struct TMH_RequestHandler *rh, "Awaiting refund exceeding %s\n", TALER_amount2s (&god->sc.refund_expected)); if (god->sc.awaiting_refund_obtained) - GNUNET_log (GNUNET_ERROR_TYPE_INFO, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Awaiting pending refunds\n"); suspend_god (god); return MHD_YES; |