[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[taler-anastasis] branch master updated: Worked on policy upload. Still
From: |
gnunet |
Subject: |
[taler-anastasis] branch master updated: Worked on policy upload. Still not working... |
Date: |
Thu, 23 Jan 2020 11:48:41 +0100 |
This is an automated email from the git hooks/post-receive script.
dennis-neufeld pushed a commit to branch master
in repository anastasis.
The following commit(s) were added to refs/heads/master by this push:
new 98eed9d Worked on policy upload. Still not working...
98eed9d is described below
commit 98eed9df77d7d5eee4481725bc57fbc4c641b316
Author: Dennis Neufeld <address@hidden>
AuthorDate: Thu Jan 23 10:48:37 2020 +0000
Worked on policy upload. Still not working...
---
src/backend/anastasis-httpd_policy_upload.c | 89 ++++---
src/include/anastasis_database_plugin.h | 63 ++---
src/include/anastasis_service.h | 3 +-
src/lib/anastasis_api_policy_store.c | 16 +-
src/lib/testing_api_cmd_policy_store.c | 18 +-
src/stasis/plugin_anastasis_postgres.c | 391 ++++++++++++++++++++++++----
src/stasis/test_anastasis_db.c | 18 +-
src/stasis/test_anastasis_db_postgres.conf | 3 +
8 files changed, 446 insertions(+), 155 deletions(-)
diff --git a/src/backend/anastasis-httpd_policy_upload.c
b/src/backend/anastasis-httpd_policy_upload.c
index 149e21d..5fb7a0f 100644
--- a/src/backend/anastasis-httpd_policy_upload.c
+++ b/src/backend/anastasis-httpd_policy_upload.c
@@ -298,7 +298,8 @@ proposal_cb (void *cls,
qs = db->record_payment (db->cls,
&puc->account,
post_counter,
- &puc->payment_identifier);
+ &puc->payment_identifier,
+ &AH_annual_fee);
if (0 >= qs)
{
GNUNET_break (0);
@@ -315,6 +316,35 @@ proposal_cb (void *cls,
puc->response_code = MHD_HTTP_PAYMENT_REQUIRED;
}
+/**
+ * Function called on all pending payments for the right
+ * account.
+ *
+ * @param cls closure, our `struct BackupContext`
+ * @param timestamp for how long have we been waiting
+ * @param order_id order id in the backend
+ * @param amount how much is the order for
+ */
+static void
+ongoing_payment_cb (void *cls,
+ struct GNUNET_TIME_Absolute timestamp,
+ const char *order_id,
+ const struct TALER_Amount *amount)
+{
+ struct PolicyUploadContext *puc = cls;
+
+ (void) amount;
+ if (0 != TALER_amount_cmp (amount,
+ &AH_annual_fee))
+ return; /* can't re-use, fees changed */
+ if ( (NULL == puc->existing_order_id) ||
+ (puc->existing_order_timestamp.abs_value_us < timestamp.abs_value_us) )
+ {
+ GNUNET_free_non_null (puc->existing_order_id);
+ puc->existing_order_id = GNUNET_strdup (order_id);
+ puc->existing_order_timestamp = timestamp;
+ }
+}
/**
* Callback to process a GET /check-payment request
@@ -438,9 +468,10 @@ begin_payment (struct PolicyUploadContext *puc,
enum ANASTASIS_DB_QueryStatus qs;
const char *order_id;
- qs = db->lookup_expired_payment_by_account (db->cls,
- &puc->account,
- puc);
+ qs = db->lookup_pending_payments_by_account (db->cls,
+ &puc->account,
+ &ongoing_payment_cb,
+ puc);
if (qs < 0)
{
struct MHD_Response *resp;
@@ -455,29 +486,6 @@ begin_payment (struct PolicyUploadContext *puc,
return ret;
}
- if (NULL == puc->order_id)
- {
- // generate new payment identifier
- GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK,
- &puc->payment_identifier,
- sizeof (
- struct ANASTASIS_PaymentSecretP));
-
- order_id = GNUNET_STRINGS_data_to_string_alloc (&puc->payment_identifier,
- sizeof(
- struct
-
ANASTASIS_PaymentSecretP));
- }
-
- if (qs == ANASTASIS_DB_STATUS_NO_RESULTS)
- {
- // create new user
- qs = db->increment_lifetime (db->cls,
- &puc->account,
- &puc->payment_identifier,
- GNUNET_TIME_UNIT_ZERO);
- }
-
if (NULL != puc->existing_order_id)
{
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
@@ -488,6 +496,16 @@ begin_payment (struct PolicyUploadContext *puc,
puc->existing_order_id);
return MHD_YES;
}
+ // generate new payment identifier
+ GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_WEAK,
+ &puc->payment_identifier,
+ sizeof (
+ struct ANASTASIS_PaymentSecretP));
+
+ order_id = GNUNET_STRINGS_data_to_string_alloc (&puc->payment_identifier,
+ sizeof(
+ struct
+ ANASTASIS_PaymentSecretP));
GNUNET_CONTAINER_DLL_insert (puc_head,
puc_tail,
@@ -508,8 +526,6 @@ begin_payment (struct PolicyUploadContext *puc,
&proposal_cb,
puc);
- puc->existing_order_id = order_id;
-
AH_trigger_curl ();
json_decref (order);
return MHD_YES;
@@ -540,13 +556,13 @@ handle_database_error (struct PolicyUploadContext *puc,
"Cannot update, unknown previous
recovery document");
case ANASTASIS_DB_STATUS_PAYMENT_REQUIRED:
{
- char *order_id;
+ const char *order_id;
order_id = MHD_lookup_connection_value (puc->con,
MHD_GET_ARGUMENT_KIND,
"paying");
- if ((NULL == order_id) || GNUNET_is_zero (order_id))
+ if (NULL == order_id)
{
GNUNET_log (GNUNET_ERROR_TYPE_INFO,
"Payment required, starting payment process\n");
@@ -793,15 +809,8 @@ AH_handler_policy_post (struct MHD_Connection *connection,
if (qs < 0)
return handle_database_error (puc,
qs);
- if (qs == ANASTASIS_DB_STATUS_NO_RESULTS)
- {
+ if (ANASTASIS_DB_STATUS_NO_RESULTS == qs)
memset (&hc, 0, sizeof (hc));
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "User not known. Payment required to create new
account\n");
- qs = ANASTASIS_DB_STATUS_PAYMENT_REQUIRED;
- return handle_database_error (puc,
- qs);
- }
if (0 == GNUNET_memcmp (&hc,
&puc->new_policy_upload_hash))
{
@@ -945,6 +954,7 @@ AH_handler_policy_post (struct MHD_Connection *connection,
ret = MHD_queue_response (connection,
MHD_HTTP_NOT_MODIFIED,
resp);
+ GNUNET_break (MHD_YES == ret);
MHD_destroy_response (resp);
return ret;
}
@@ -962,6 +972,7 @@ AH_handler_policy_post (struct MHD_Connection *connection,
ret = MHD_queue_response (connection,
MHD_HTTP_NO_CONTENT,
resp);
+ GNUNET_break (MHD_YES == ret);
MHD_destroy_response (resp);
return ret;
}
diff --git a/src/include/anastasis_database_plugin.h
b/src/include/anastasis_database_plugin.h
index f2798d7..df0a68c 100644
--- a/src/include/anastasis_database_plugin.h
+++ b/src/include/anastasis_database_plugin.h
@@ -311,27 +311,30 @@ struct ANASTASIS_DatabasePlugin
ANASTASIS_AccountPubP *anastasis_pub);
/**
- * Lookup pending payments by account.
- *
- * @param cls closure
- * @param account_pub account to look for pending payment under
- */
- enum ANASTASIS_DB_QueryStatus
- (*lookup_expired_payment_by_account)(void *cls,
- const struct
- ANASTASIS_AccountPubP *account_pub,
- void *it_cls);
-
-/**
- * Increment account lifetime.
+ * Lookup pending payments by account.
*
* @param cls closure
- * @param account_pub which account received a payment
- * @param payment_identifier proof of payment, must be unique and match
pending payment
- * @param lifetime for how long is the account now paid (increment)
- * @return transaction status
+ * @param anastasis_pub account to look for pending payment under
+ * @param it iterator to call on all pending payments
+ * @param it_cls closure for @a it
*/
enum ANASTASIS_DB_QueryStatus
+ (*lookup_pending_payments_by_account)(void *cls,
+ const struct
+ ANASTASIS_AccountPubP *anastasis_pub,
+ ANASTASIS_DB_PaymentPendingIterator it,
+ void *it_cls);
+
+ /**
+ * Increment account lifetime.
+ *
+ * @param cls closure
+ * @param account_pub which account received a payment
+ * @param payment_identifier proof of payment, must be unique and match
pending payment
+ * @param lifetime for how long is the account now paid (increment)
+ * @return transaction status
+ */
+ enum ANASTASIS_DB_QueryStatus
(*increment_lifetime)(void *cls,
const struct ANASTASIS_AccountPubP *anastasis_pub,
const struct
@@ -339,21 +342,23 @@ struct ANASTASIS_DatabasePlugin
struct GNUNET_TIME_Relative lifetime);
-/**
- * Store payment. Used to begin a payment, not indicative
- * that the payment actually was made. (That is done
- * when we increment the account's lifetime.)
- *
- * @param cls closure
- * @param anastasis_pub anastasis's public key
- * @param post_counter how many uploads does @a amount pay for
- * @param payment_secret payment secret which the user must provide with every
upload
- * @return transaction status
- */
+ /**
+ * Store payment. Used to begin a payment, not indicative
+ * that the payment actually was made. (That is done
+ * when we increment the account's lifetime.)
+ *
+ * @param cls closure
+ * @param anastasis_pub anastasis's public key
+ * @param post_counter how many uploads does @a amount pay for
+ * @param payment_secret payment secret which the user must provide with
every upload
+ * @param amount how much we asked for
+ * @return transaction status
+ */
enum ANASTASIS_DB_QueryStatus
(*record_payment)(void *cls,
const struct ANASTASIS_AccountPubP *anastasis_pub,
uint32_t post_counter,
- const struct ANASTASIS_PaymentSecretP *payment_secret);
+ const struct ANASTASIS_PaymentSecretP *payment_secret,
+ const struct TALER_Amount *amount);
};
#endif
diff --git a/src/include/anastasis_service.h b/src/include/anastasis_service.h
index a568491..f02b762 100644
--- a/src/include/anastasis_service.h
+++ b/src/include/anastasis_service.h
@@ -398,8 +398,7 @@ ANASTASIS_policy_store (struct GNUNET_CURL_Context *ctx,
const void *recovery_data,
size_t recovery_data_size,
int payment_requested,
- const struct
- ANASTASIS_PaymentSecretP paymentSecretP,
+ const char *payment_order_id,
ANASTASIS_PolicyStoreCallback cb,
void *cb_cls);
diff --git a/src/lib/anastasis_api_policy_store.c
b/src/lib/anastasis_api_policy_store.c
index f0acabd..de226e5 100644
--- a/src/lib/anastasis_api_policy_store.c
+++ b/src/lib/anastasis_api_policy_store.c
@@ -276,8 +276,7 @@ ANASTASIS_policy_store (struct GNUNET_CURL_Context *ctx,
const void *recovery_data,
size_t recovery_data_size,
int payment_requested,
- const struct
- ANASTASIS_PaymentSecretP paymentSecretP,
+ const char *paid_order_id,
ANASTASIS_PolicyStoreCallback cb,
void *cb_cls)
{
@@ -369,15 +368,11 @@ ANASTASIS_policy_store (struct GNUNET_CURL_Context *ctx,
job_headers = ext;
}
/* Setup Payment-Identifier header */
- if (NULL != &paymentSecretP)
+ if (NULL != paid_order_id)
{
- val = GNUNET_STRINGS_data_to_string_alloc (&paymentSecretP,
- sizeof (struct
-
ANASTASIS_PaymentSecretP));
GNUNET_asprintf (&hdr,
"Payment-Identifier: %s",
- val);
- GNUNET_free (val);
+ paid_order_id);
ext = curl_slist_append (job_headers,
hdr);
@@ -410,10 +405,6 @@ ANASTASIS_policy_store (struct GNUNET_CURL_Context *ctx,
acc_pub_str);
GNUNET_free (acc_pub_str);
- char *paid_order_id;
- paid_order_id = GNUNET_STRINGS_data_to_string_alloc (&paymentSecretP,
- sizeof (struct
-
ANASTASIS_PaymentSecretP));
pso->url = (GNUNET_YES == payment_requested)
? TALER_url_join (backend_url,
path,
@@ -431,7 +422,6 @@ ANASTASIS_policy_store (struct GNUNET_CURL_Context *ctx,
: NULL,
paid_order_id,
NULL);
- GNUNET_free_non_null (paid_order_id);
GNUNET_free (path);
}
pso->ctx = ctx;
diff --git a/src/lib/testing_api_cmd_policy_store.c
b/src/lib/testing_api_cmd_policy_store.c
index 6204f2c..5830ff8 100644
--- a/src/lib/testing_api_cmd_policy_store.c
+++ b/src/lib/testing_api_cmd_policy_store.c
@@ -336,18 +336,6 @@ policy_store_run (void *cls,
TALER_TESTING_interpreter_fail (pss->is);
return;
}
-
- if (GNUNET_OK !=
- GNUNET_STRINGS_string_to_data (order_id,
- strlen (order_id),
- &pss->payment_id,
- sizeof (struct
- ANASTASIS_PaymentSecretP)))
- {
- GNUNET_break (0);
- TALER_TESTING_interpreter_fail (pss->is);
- return;
- }
}
}
}
@@ -389,7 +377,7 @@ policy_store_run (void *cls,
(0 !=
(ANASTASIS_TESTING_PSO_REQUEST_PAYMENT
& pss->psopt)),
- pss->payment_id,
+ pss->payment_order_req,
&policy_store_cb,
pss);
if (NULL == pss->pso)
@@ -423,7 +411,7 @@ policy_store_cleanup (void *cls,
pss->pso = NULL;
}
- GNUNET_free_non_null ((void *) pss->payment_order_id);
+ GNUNET_free_non_null (pss->payment_order_id);
GNUNET_free (pss);
}
@@ -447,6 +435,8 @@ policy_store_traits (void *cls,
struct TALER_TESTING_Trait traits[] = {
ANASTASIS_TESTING_make_trait_hash (ANASTASIS_TESTING_TRAIT_HASH_CURRENT,
&pss->curr_hash),
+ ANASTASIS_TESTING_make_trait_hash (ANASTASIS_TESTING_TRAIT_HASH_PREVIOUS,
+ &pss->prev_hash),
ANASTASIS_TESTING_make_trait_account_pub (0,
&pss->anastasis_pub),
ANASTASIS_TESTING_make_trait_account_priv (0,
diff --git a/src/stasis/plugin_anastasis_postgres.c
b/src/stasis/plugin_anastasis_postgres.c
index 65029d1..bc8228c 100644
--- a/src/stasis/plugin_anastasis_postgres.c
+++ b/src/stasis/plugin_anastasis_postgres.c
@@ -57,6 +57,11 @@ struct PostgresClosure
*/
const char *transaction_name;
+ /**
+ * Currency we accept payments in.
+ */
+ char *currency;
+
};
@@ -214,50 +219,167 @@ commit_transaction (void *cls)
return qs;
}
-
/**
- * Lookup pending payments by account.
+ * Function called to perform "garbage collection" on the
+ * database, expiring records we no longer require. Deletes
+ * all user records that are not paid up (and by cascade deletes
+ * the associated recovery documents). Also deletes expired
+ * truth and financial records older than @a fin_expire.
*
* @param cls closure
- * @param anastasis_pub account to look for pending payment under
- * @param it iterator to call on all pending payments
- * @param it_cls closure for @a it
+ * @param expire_backups backups older than the given time stamp should be
garbage collected
+ * @param expire_pending_payments payments still pending from since before
+ * this value should be garbage collected
+ * @return transaction status
*/
static enum ANASTASIS_DB_QueryStatus
-postgres_lookup_expired_payment_by_account (void *cls,
- const struct
- ANASTASIS_AccountPubP
*anastasis_pub,
- void *it_cls)
+postgres_gc (void *cls,
+ struct GNUNET_TIME_Absolute expire_backups,
+ struct GNUNET_TIME_Absolute expire_pending_payments)
{
- struct GNUNET_TIME_Absolute paid_until;
- struct GNUNET_TIME_Relative time_remaining;
struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_QueryParam params[] = {
+ TALER_PQ_query_param_absolute_time (&expire_backups),
+ GNUNET_PQ_query_param_end
+ };
+ struct GNUNET_PQ_QueryParam params2[] = {
+ TALER_PQ_query_param_absolute_time (&expire_pending_payments),
+ GNUNET_PQ_query_param_end
+ };
enum ANASTASIS_DB_QueryStatus qs;
- /* Check if user has paid */
+ check_connection (pg);
+ postgres_preflight (pg);
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "gc_accounts",
+ params);
+ if (qs < 0)
+ return qs;
+ return GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "gc_pending_payments",
+ params2);
+}
+
+
+/**
+ * Closure for #payment_by_account_cb.
+ */
+struct PaymentIteratorContext
+{
+ /**
+ * Function to call on each result
+ */
+ ANASTASIS_DB_PaymentPendingIterator it;
+
+ /**
+ * Closure for @e it.
+ */
+ void *it_cls;
+
+ /**
+ * Plugin context.
+ */
+ struct PostgresClosure *pg;
+
+ /**
+ * Query status to return.
+ */
+ enum GNUNET_DB_QueryStatus qs;
+
+};
+
+
+/**
+ * Helper function for #postgres_lookup_pending_payments_by_account().
+ * To be called with the results of a SELECT statement
+ * that has returned @a num_results results.
+ *
+ * @param cls closure of type `struct PaymentIteratorContext *`
+ * @param result the postgres result
+ * @param num_result the number of results in @a result
+ */
+static void
+payment_by_account_cb (void *cls,
+ PGresult *result,
+ unsigned int num_results)
+{
+ struct PaymentIteratorContext *pic = cls;
+ for (unsigned int i = 0; i < num_results; i++)
{
- struct GNUNET_PQ_QueryParam params[] = {
- GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
- GNUNET_PQ_query_param_end
- };
+ struct GNUNET_TIME_Absolute timestamp;
+ struct ANASTASIS_PaymentSecretP payment_identifier;
+ struct TALER_Amount amount;
struct GNUNET_PQ_ResultSpec rs[] = {
- TALER_PQ_result_spec_absolute_time ("paid_until",
- &paid_until),
+ GNUNET_PQ_result_spec_absolute_time ("timestamp",
+ ×tamp),
+ GNUNET_PQ_result_spec_auto_from_type ("payment_identifier",
+ &payment_identifier),
+ TALER_PQ_result_spec_amount ("amount",
+ pic->pg->currency,
+ &amount),
GNUNET_PQ_result_spec_end
};
- qs = GNUNET_PQ_eval_prepared_singleton_select (pg->conn,
- "user_select",
- params,
- rs);
+ if (GNUNET_OK !=
+ GNUNET_PQ_extract_result (result,
+ rs,
+ i))
+ {
+ GNUNET_break (0);
+ pic->qs = GNUNET_DB_STATUS_HARD_ERROR;
+ return;
+ }
+ const char *order_id;
+ order_id = GNUNET_STRINGS_data_to_string_alloc (&payment_identifier,
+ sizeof (struct
+
ANASTASIS_PaymentSecretP));
+ pic->qs = i + 1;
+ pic->it (pic->it_cls,
+ timestamp,
+ order_id,
+ &amount);
+ GNUNET_PQ_cleanup_result (rs);
}
+}
- if (qs == ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT)
- {
- time_remaining = GNUNET_TIME_absolute_get_remaining (paid_until);
- if (GNUNET_TIME_round_rel (&time_remaining) == 0)
- return ANASTASIS_DB_STATUS_PAYMENT_REQUIRED;
- }
+/**
+ * Lookup pending payments by account.
+ *
+ * @param cls closure
+ * @param anastasis_pub account to look for pending payment under
+ * @param it iterator to call on all pending payments
+ * @param it_cls closure for @a it
+ */
+static enum ANASTASIS_DB_QueryStatus
+postgres_lookup_pending_payments_by_account (void *cls,
+ const struct
+ ANASTASIS_AccountPubP *
+ anastasis_pub,
+
ANASTASIS_DB_PaymentPendingIterator
+ it,
+ void *it_cls)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
+ GNUNET_PQ_query_param_end
+ };
+ struct PaymentIteratorContext pic = {
+ .it = it,
+ .it_cls = it_cls,
+ .pg = pg
+ };
+ enum GNUNET_DB_QueryStatus qs;
+
+ check_connection (pg);
+ postgres_preflight (pg);
+ qs = GNUNET_PQ_eval_prepared_multi_select (pg->conn,
+ "payments_select_by_account",
+ params,
+ &payment_by_account_cb,
+ &pic);
+ if (qs > 0)
+ return pic.qs;
GNUNET_break (GNUNET_DB_STATUS_HARD_ERROR != qs);
return qs;
}
@@ -344,7 +466,7 @@ postgres_store_recovery_document (void *cls,
GNUNET_PQ_query_param_end
};
struct GNUNET_PQ_ResultSpec rs[] = {
- GNUNET_PQ_result_spec_auto_from_type ("paid_until",
+ GNUNET_PQ_result_spec_auto_from_type ("expiration_date",
&ed),
GNUNET_PQ_result_spec_end
};
@@ -556,13 +678,31 @@ postgres_increment_lifetime (void *cls,
return GNUNET_DB_STATUS_HARD_ERROR;
}
+ {
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (payment_identifier),
+ GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
+ GNUNET_PQ_query_param_end
+ };
+
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "payment_done",
+ params);
+ if (0 >= qs)
+ {
+ /* payment made before, or unknown, or error => no further action! */
+ rollback (pg);
+ return qs;
+ }
+ }
+
{
struct GNUNET_PQ_QueryParam params[] = {
GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
GNUNET_PQ_query_param_end
};
struct GNUNET_PQ_ResultSpec rs[] = {
- TALER_PQ_result_spec_absolute_time ("paid_until",
+ TALER_PQ_result_spec_absolute_time ("expiration_date",
&expiration),
GNUNET_PQ_result_spec_end
};
@@ -598,7 +738,7 @@ postgres_increment_lifetime (void *cls,
break;
case GNUNET_DB_STATUS_SUCCESS_ONE_RESULT:
{
- // user exists, update paid_until
+ // user exists, update expiration_date
struct GNUNET_PQ_QueryParam params[] = {
GNUNET_PQ_query_param_absolute_time (&expiration),
GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
@@ -653,7 +793,6 @@ postgres_increment_lifetime (void *cls,
}
}
-
/**
* Store payment. Used to begin a payment, not indicative
* that the payment actually was made. (That is done
@@ -663,20 +802,24 @@ postgres_increment_lifetime (void *cls,
* @param anastasis_pub anastasis's public key
* @param post_counter how many uploads does @a amount pay for
* @param payment_secret payment secret which the user must provide with every
upload
+ * @param amount how much we asked for
* @return transaction status
*/
static enum ANASTASIS_DB_QueryStatus
postgres_record_payment (void *cls,
const struct ANASTASIS_AccountPubP *anastasis_pub,
uint32_t post_counter,
- const struct ANASTASIS_PaymentSecretP *payment_secret)
+ const struct ANASTASIS_PaymentSecretP *payment_secret,
+ const struct TALER_Amount *amount)
{
struct PostgresClosure *pg = cls;
enum ANASTASIS_DB_QueryStatus qs;
struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get ();
+ struct GNUNET_TIME_Absolute expiration;
struct GNUNET_PQ_QueryParam params[] = {
GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
GNUNET_PQ_query_param_uint32 (&post_counter),
+ TALER_PQ_query_param_amount (amount),
GNUNET_PQ_query_param_auto_from_type (payment_secret),
GNUNET_PQ_query_param_absolute_time (&now),
GNUNET_PQ_query_param_end
@@ -684,6 +827,73 @@ postgres_record_payment (void *cls,
check_connection (pg);
postgres_preflight (pg);
+
+ // because of constraint at user_id, first we have to verify
+ // if user exists, otherwise we have to create one
+ {
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
+ GNUNET_PQ_query_param_end
+ };
+ struct GNUNET_PQ_ResultSpec rs[] = {
+ TALER_PQ_result_spec_absolute_time ("expiration_date",
+ &expiration),
+ GNUNET_PQ_result_spec_end
+ };
+
+ qs = GNUNET_PQ_eval_prepared_singleton_select (pg->conn,
+ "user_select",
+ params,
+ rs);
+ }
+ switch (qs)
+ {
+ case GNUNET_DB_STATUS_HARD_ERROR:
+ rollback (pg);
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ case GNUNET_DB_STATUS_SOFT_ERROR:
+ rollback (pg);
+ return ANASTASIS_DB_STATUS_SOFT_ERROR;
+ case GNUNET_DB_STATUS_SUCCESS_NO_RESULTS:
+ {
+ // create new user
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
+ GNUNET_PQ_query_param_absolute_time (&now),
+ GNUNET_PQ_query_param_end
+ };
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "user_insert",
+ params);
+ }
+ break;
+ case GNUNET_DB_STATUS_SUCCESS_ONE_RESULT:
+ // handle case below
+ break;
+ default:
+ GNUNET_break (0);
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ }
+ switch (qs)
+ {
+ case GNUNET_DB_STATUS_HARD_ERROR:
+ rollback (pg);
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ case GNUNET_DB_STATUS_SOFT_ERROR:
+ rollback (pg);
+ GNUNET_break (0);
+ return ANASTASIS_DB_STATUS_SOFT_ERROR;
+ case GNUNET_DB_STATUS_SUCCESS_NO_RESULTS:
+ GNUNET_break (0);
+ rollback (pg);
+ return ANASTASIS_DB_STATUS_NO_RESULTS;
+ case GNUNET_DB_STATUS_SUCCESS_ONE_RESULT:
+ break;
+ default:
+ GNUNET_break (0);
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ }
+
qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
"payment_insert",
params);
@@ -894,15 +1104,15 @@ postgres_lookup_account (void *cls,
ANASTASIS_AccountPubP *anastasis_pub)
{
struct PostgresClosure *pg = cls;
- struct GNUNET_TIME_Absolute paid_until;
+ struct GNUNET_TIME_Absolute expiration_date;
enum ANASTASIS_DB_QueryStatus qs;
struct GNUNET_PQ_QueryParam params[] = {
GNUNET_PQ_query_param_auto_from_type (anastasis_pub),
GNUNET_PQ_query_param_end
};
struct GNUNET_PQ_ResultSpec rs[] = {
- TALER_PQ_result_spec_absolute_time ("paid_until",
- &paid_until),
+ TALER_PQ_result_spec_absolute_time ("expiration_date",
+ &expiration_date),
GNUNET_PQ_result_spec_end
};
@@ -913,7 +1123,22 @@ postgres_lookup_account (void *cls,
rs);
GNUNET_break (GNUNET_DB_STATUS_HARD_ERROR != qs);
- return qs;
+
+ switch (qs)
+ {
+ case GNUNET_DB_STATUS_HARD_ERROR:
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ case GNUNET_DB_STATUS_SOFT_ERROR:
+ GNUNET_break (0);
+ return ANASTASIS_DB_STATUS_SOFT_ERROR;
+ case GNUNET_DB_STATUS_SUCCESS_NO_RESULTS:
+ return ANASTASIS_DB_STATUS_PAYMENT_REQUIRED;
+ case GNUNET_DB_STATUS_SUCCESS_ONE_RESULT:
+ return ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT;
+ default:
+ GNUNET_break (0);
+ return ANASTASIS_DB_STATUS_HARD_ERROR;
+ }
}
@@ -1067,7 +1292,7 @@ libanastasis_plugin_db_postgres_init (void *cls)
The contract terms will change (nonce will be added) when moved to the
contract terms table */
GNUNET_PQ_make_execute ("CREATE TABLE IF NOT EXISTS anastasis_truth"
- "( truth_id UUID PRIMARY KEY NOT NULL,"
+ "(truth_id UUID PRIMARY KEY NOT NULL,"
" key_share_data BYTEA NOT NULL,"
" method VARCHAR,"
" nonce BYTEA NOT NULL,"
@@ -1079,14 +1304,17 @@ libanastasis_plugin_db_postgres_init (void *cls)
");"),
GNUNET_PQ_make_execute ("CREATE TABLE IF NOT EXISTS anastasis_user"
"( user_id BYTEA PRIMARY KEY
CHECK(LENGTH(user_id)=32),"
- " paid_until TIMESTAMP NOT NULL"
+ " expiration_date TIMESTAMP NOT NULL"
");"),
GNUNET_PQ_make_execute ("CREATE TABLE IF NOT EXISTS anastasis_payment"
- "( payment_id BIGSERIAL PRIMARY KEY,"
- " user_id BYTEA NOT NULL REFERENCES
anastasis_user(user_id),"
- " post_counter INTEGER,"
- " payment_identifier BYTEA NOT NULL
CHECK(LENGTH(payment_identifier)=32),"
- " transaction_time TIMESTAMP NOT NULL DEFAULT
NOW()"
+ "(payment_id BIGSERIAL PRIMARY KEY,"
+ " user_id BYTEA NOT NULL REFERENCES
anastasis_user(user_id),"
+ " post_counter INTEGER,"
+ " amount_val INT8 NOT NULL," /* amount we were
paid */
+ " amount_frac INT4 NOT NULL,"
+ " payment_identifier BYTEA NOT NULL
CHECK(LENGTH(payment_identifier)=32),"
+ " timestamp TIMESTAMP NOT NULL DEFAULT NOW(),"
+ " paid BOOLEAN NOT NULL DEFAULT FALSE"
");"),
GNUNET_PQ_make_execute (
"CREATE TABLE IF NOT EXISTS anastasis_recoverydocument"
@@ -1103,7 +1331,7 @@ libanastasis_plugin_db_postgres_init (void *cls)
GNUNET_PQ_make_prepare ("user_insert",
"INSERT INTO anastasis_user "
"(user_id"
- ",paid_until"
+ ",expiration_date"
") VALUES "
"($1, $2);",
2),
@@ -1112,7 +1340,7 @@ libanastasis_plugin_db_postgres_init (void *cls)
0),
GNUNET_PQ_make_prepare ("user_select",
"SELECT"
- " paid_until "
+ " expiration_date "
"FROM anastasis_user"
" WHERE user_id=$1"
" FOR UPDATE;",
@@ -1120,18 +1348,64 @@ libanastasis_plugin_db_postgres_init (void *cls)
GNUNET_PQ_make_prepare ("user_update",
"UPDATE anastasis_user"
" SET "
- " paid_until=$1"
+ " expiration_date=$1"
" WHERE user_id=$2;",
2),
GNUNET_PQ_make_prepare ("payment_insert",
"INSERT INTO anastasis_payment "
"(user_id"
",post_counter"
+ ",amount_val"
+ ",amount_frac"
",payment_identifier"
- ",transaction_time"
+ ",timestamp"
") VALUES "
- "($1, $2, $3, $4);",
+ "($1, $2, $3, $4, $5, $6);",
4),
+ GNUNET_PQ_make_prepare ("payment_done",
+ "UPDATE anastasis_payment "
+ "SET"
+ " paid=TRUE "
+ "WHERE"
+ " payment_identifier=$1"
+ " AND"
+ " user_id=$2"
+ " AND"
+ " paid=FALSE;",
+ 2),
+ GNUNET_PQ_make_prepare ("payments_select",
+ "SELECT"
+ " user_id"
+ ",payment_identifier"
+ ",amount_val"
+ ",amount_frac"
+ " FROM anastasis_payment"
+ " WHERE paid=FALSE;",
+ 0),
+ GNUNET_PQ_make_prepare ("payments_select_by_account",
+ "SELECT"
+ " timestamp"
+ ",payment_identifier"
+ ",amount_val"
+ ",amount_frac"
+ " FROM anastasis_payment"
+ " WHERE"
+ " paid=FALSE"
+ " AND"
+ " user_id=$1;",
+ 1),
+ GNUNET_PQ_make_prepare ("gc_accounts",
+ "DELETE FROM anastasis_user "
+ "WHERE"
+ " expiration_date < $1;",
+ 1),
+ GNUNET_PQ_make_prepare ("gc_pending_payments",
+ "DELETE FROM anastasis_payment "
+ "WHERE"
+ " paid=FALSE"
+ " AND"
+ " timestamp < $1;",
+ 1),
GNUNET_PQ_make_prepare ("truth_insert",
"INSERT INTO anastasis_truth "
"(truth_id"
@@ -1244,6 +1518,19 @@ libanastasis_plugin_db_postgres_init (void *cls)
GNUNET_free (pg);
return NULL;
}
+ if (GNUNET_OK !=
+ GNUNET_CONFIGURATION_get_value_string (cfg,
+ "taler",
+ "CURRENCY",
+ &pg->currency))
+ {
+ GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR,
+ "taler",
+ "CURRENCY");
+ GNUNET_PQ_disconnect (pg->conn);
+ GNUNET_free (pg);
+ return NULL;
+ }
plugin = GNUNET_new (struct ANASTASIS_DatabasePlugin);
plugin->cls = pg;
plugin->drop_tables = &postgres_drop_tables;
@@ -1258,8 +1545,8 @@ libanastasis_plugin_db_postgres_init (void *cls)
plugin->get_latest_recovery_document =
&postgres_get_latest_recovery_document;
plugin->get_recovery_document = &postgres_get_recovery_document;
plugin->lookup_account = &postgres_lookup_account;
- plugin->lookup_expired_payment_by_account =
- &postgres_lookup_expired_payment_by_account;
+ plugin->lookup_pending_payments_by_account =
+ &postgres_lookup_pending_payments_by_account;
plugin->increment_lifetime = &postgres_increment_lifetime;
plugin->start = &begin_transaction;
plugin->check_connection = &check_connection;
@@ -1271,7 +1558,7 @@ libanastasis_plugin_db_postgres_init (void *cls)
/**
* Shutdown Postgres database subsystem.
*
- * @param cls a `struct ANASTASIS_DB_Plugin`
+ * @param cls a `struct ANASTASIS_DB_STATUS_Plugin`
* @return NULL (always)
*/
void *
diff --git a/src/stasis/test_anastasis_db.c b/src/stasis/test_anastasis_db.c
index a394c16..1df178b 100644
--- a/src/stasis/test_anastasis_db.c
+++ b/src/stasis/test_anastasis_db.c
@@ -166,6 +166,7 @@ static void
run (void *cls)
{
struct GNUNET_CONFIGURATION_Handle *cfg = cls;
+ struct TALER_Amount amount;
if (NULL == (plugin = ANASTASIS_DB_plugin_load (cfg)))
{
@@ -245,6 +246,17 @@ run (void *cls)
struct GNUNET_TIME_Relative rel_time;
rel_time = GNUNET_TIME_UNIT_MONTHS;
+ GNUNET_assert (GNUNET_OK ==
+ TALER_string_to_amount ("EUR:1",
+ &amount));
+
+ FAILIF (ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT !=
+ plugin->record_payment (plugin->cls,
+ &accountPubP,
+ post_counter,
+ &paymentSecretP,
+ &amount));
+
FAILIF (ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT !=
plugin->increment_lifetime (plugin->cls,
&accountPubP,
@@ -255,12 +267,6 @@ run (void *cls)
plugin->lookup_account (plugin->cls,
&accountPubP));
- FAILIF (ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT !=
- plugin->record_payment (plugin->cls,
- &accountPubP,
- post_counter,
- &paymentSecretP));
-
FAILIF (ANASTASIS_DB_STATUS_SUCCESS_ONE_RESULT !=
plugin->store_truth (plugin->cls,
&uuid,
diff --git a/src/stasis/test_anastasis_db_postgres.conf
b/src/stasis/test_anastasis_db_postgres.conf
index f91dea1..b00e4e8 100644
--- a/src/stasis/test_anastasis_db_postgres.conf
+++ b/src/stasis/test_anastasis_db_postgres.conf
@@ -2,6 +2,9 @@
#The DB plugin to use
DB = postgres
+[taler]
+CURRENCY = EUR
+
[anastasisdb-postgres]
#The connection string the plugin has to use for connecting to the database
CONFIG = postgres:///anastasischeck
--
To stop receiving notification emails like this one, please contact
address@hidden.
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [taler-anastasis] branch master updated: Worked on policy upload. Still not working...,
gnunet <=