[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[taler-anastasis] branch master updated: separate DB creation from plugi
From: |
gnunet |
Subject: |
[taler-anastasis] branch master updated: separate DB creation from plugin loading; fix misc. Debian package issues |
Date: |
Wed, 01 Sep 2021 00:59:37 +0200 |
This is an automated email from the git hooks/post-receive script.
grothoff pushed a commit to branch master
in repository anastasis.
The following commit(s) were added to refs/heads/master by this push:
new c3a1a4e separate DB creation from plugin loading; fix misc. Debian
package issues
c3a1a4e is described below
commit c3a1a4ecbea0c8df729b7a29da5d31c1f9dab9c9
Author: Christian Grothoff <christian@grothoff.org>
AuthorDate: Wed Sep 1 00:59:34 2021 +0200
separate DB creation from plugin loading; fix misc. Debian package issues
---
debian/anastasis-httpd.postinst | 6 +
debian/db/install/pgsql | 2 +-
debian/etc/anastasis/anastasis.conf | 21 +
debian/rules | 2 +-
doc/sphinx/manpages/anastasis.conf.5.rst | 3 +
.../anastasis-helper-authorization-iban.c | 10 +
src/backend/anastasis-httpd.c | 8 +
src/include/anastasis_database_plugin.h | 22 +-
src/stasis/anastasis-dbinit.c | 8 +-
src/stasis/plugin_anastasis_postgres.c | 1408 ++++++++++----------
src/stasis/test_anastasis_db.c | 10 +-
11 files changed, 805 insertions(+), 695 deletions(-)
diff --git a/debian/anastasis-httpd.postinst b/debian/anastasis-httpd.postinst
index fe89acb..994b06b 100644
--- a/debian/anastasis-httpd.postinst
+++ b/debian/anastasis-httpd.postinst
@@ -20,6 +20,12 @@ configure)
adduser --quiet --system --ingroup ${_GROUPNAME} --no-create-home --home
${TALER_HOME} ${_USERNAME}
fi
+ if ! dpkg-statoverride --list
/etc/anastasis/secrets/anastasis-db.secret.conf >/dev/null 2>&1; then
+ dpkg-statoverride --add --update \
+ anastasis-httpd root 460 \
+ /etc/anastasis/secrets/anastasis-db.secret.conf
+ fi
+
# Setup postgres database (needs dbconfig-pgsql package)
if [ -f /usr/share/dbconfig-common/dpkg/postinst.pgsql ]; then
. /usr/share/dbconfig-common/dpkg/postinst.pgsql
diff --git a/debian/db/install/pgsql b/debian/db/install/pgsql
index dab5d1e..f695fed 100755
--- a/debian/db/install/pgsql
+++ b/debian/db/install/pgsql
@@ -1,4 +1,4 @@
-#!/bin/sh
+#!/bin/bash
set -eu
diff --git a/debian/etc/anastasis/anastasis.conf
b/debian/etc/anastasis/anastasis.conf
index e662a43..4d0deda 100644
--- a/debian/etc/anastasis/anastasis.conf
+++ b/debian/etc/anastasis/anastasis.conf
@@ -1,5 +1,26 @@
[anastasis]
DATABASE = postgres
+SERVE = unix
+
+# You must set each of the following options
+# before starting anastasis-httpd!
+#
+# Storage fee for policies (per year)
+#ANNUAL_FEE = KUDOS:0
+#
+# Storage fee for truth
+#TRUTH_UPLOAD_FEE = KUDOS:0
+
+# Name of your business
+#BUSINESS_NAME = ""
+
+# Random server salt. Use output of 'uuidgen'
+#SERVER_SALT = ""
+
+# How high is the per key share insurance offered
+# by your business?
+#INSURANCE = KUDOS:0
+
[taler]
# Currency accepted by anastasis via GNU Taler payments.
diff --git a/debian/rules b/debian/rules
index e3c7db5..cfd43c7 100755
--- a/debian/rules
+++ b/debian/rules
@@ -34,7 +34,7 @@ override_dh_install:
dh_install
# Done manually for debhelper-compat<13
dh_installtmpfiles
-# Remove files already present in libtalerexchange from main taler-exchange
package
+# Remove files already present in libanastasis-dev/cli from
anastasis-httpd/libanastasis packages
cd debian/libanastasis-dev; find . -type f,l -exec rm -f
../anastasis-httpd/{} \;
cd debian/anastasis-cli; find . -type f -exec rm -f
../anastasis-httpd/{} \;
cd debian/libanastasis-dev; find . -type f,l -exec rm -f
../libanastasis/{} \;
diff --git a/doc/sphinx/manpages/anastasis.conf.5.rst
b/doc/sphinx/manpages/anastasis.conf.5.rst
index 1f6b49e..000d8f0 100644
--- a/doc/sphinx/manpages/anastasis.conf.5.rst
+++ b/doc/sphinx/manpages/anastasis.conf.5.rst
@@ -67,6 +67,9 @@ ANNUAL_FEE
TRUTH_UPLOAD_FEE
Annual fee to be paid for truth uploads, i.e. "EUR:1.5".
+INSURANCE
+ Amount up to which key shares are warranted, i.e. "EUR:1000000".
+
DB
Database backend to use, only ``postgres`` is supported right now.
diff --git a/src/authorization/anastasis-helper-authorization-iban.c
b/src/authorization/anastasis-helper-authorization-iban.c
index 04dfa03..c6e5335 100644
--- a/src/authorization/anastasis-helper-authorization-iban.c
+++ b/src/authorization/anastasis-helper-authorization-iban.c
@@ -389,6 +389,16 @@ run (void *cls,
global_ret = EXIT_NOTCONFIGURED;
return;
}
+ if (GNUNET_OK !=
+ db_plugin->connect (db_plugin->cls))
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Database not set up. Did you run anastasis-dbinit?\n");
+ global_ret = EXIT_NOTCONFIGURED;
+ ANASTASIS_DB_plugin_unload (db_plugin);
+ db_plugin = NULL;
+ return;
+ }
if (GNUNET_OK !=
GNUNET_CONFIGURATION_get_value_string (cfg,
"authorization-iban",
diff --git a/src/backend/anastasis-httpd.c b/src/backend/anastasis-httpd.c
index fdf17ff..9f5c87b 100644
--- a/src/backend/anastasis-httpd.c
+++ b/src/backend/anastasis-httpd.c
@@ -888,6 +888,14 @@ run (void *cls,
GNUNET_SCHEDULER_shutdown ();
return;
}
+ if (GNUNET_OK !=
+ db->connect (db->cls))
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "Database not setup. Did you run anastasis-dbinit?\n");
+ GNUNET_SCHEDULER_shutdown ();
+ return;
+ }
fh = TALER_MHD_bind (config,
"anastasis",
diff --git a/src/include/anastasis_database_plugin.h
b/src/include/anastasis_database_plugin.h
index 565ad69..bc4b0e6 100644
--- a/src/include/anastasis_database_plugin.h
+++ b/src/include/anastasis_database_plugin.h
@@ -187,8 +187,26 @@ struct ANASTASIS_DatabasePlugin
* @param cls closure
* @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
*/
- int
- (*drop_tables) (void *cls);
+ enum GNUNET_GenericReturnValue
+ (*drop_tables)(void *cls);
+
+ /**
+ * Connect to the database.
+ *
+ * @param cls closure
+ * @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
+ */
+ enum GNUNET_GenericReturnValue
+ (*connect)(void *cls);
+
+ /**
+ * Initialize merchant tables
+ *
+ * @param cls closure
+ * @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
+ */
+ enum GNUNET_GenericReturnValue
+ (*create_tables)(void *cls);
/**
* Function called to perform "garbage collection" on the
diff --git a/src/stasis/anastasis-dbinit.c b/src/stasis/anastasis-dbinit.c
index 038fb7c..17b3c56 100644
--- a/src/stasis/anastasis-dbinit.c
+++ b/src/stasis/anastasis-dbinit.c
@@ -54,7 +54,7 @@ run (void *cls,
{
fprintf (stderr,
"Failed to initialize database plugin.\n");
- global_ret = 1;
+ global_ret = EXIT_FAILURE;
return;
}
if (reset_db)
@@ -63,6 +63,12 @@ run (void *cls,
ANASTASIS_DB_plugin_unload (plugin);
plugin = ANASTASIS_DB_plugin_load (cfg);
}
+ if (GNUNET_OK !=
+ plugin->create_tables (plugin->cls))
+ {
+ global_ret = EXIT_FAILURE;
+ return;
+ }
ANASTASIS_DB_plugin_unload (plugin);
}
diff --git a/src/stasis/plugin_anastasis_postgres.c
b/src/stasis/plugin_anastasis_postgres.c
index 8ee16ad..b78dbdb 100644
--- a/src/stasis/plugin_anastasis_postgres.c
+++ b/src/stasis/plugin_anastasis_postgres.c
@@ -81,7 +81,7 @@ struct PostgresClosure
* @param cls closure our `struct Plugin`
* @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
*/
-static int
+static enum GNUNET_GenericReturnValue
postgres_drop_tables (void *cls)
{
struct PostgresClosure *pg = cls;
@@ -100,266 +100,676 @@ postgres_drop_tables (void *cls)
/**
- * Check that the database connection is still up.
- *
- * @param cls a `struct PostgresClosure` with connection to check
- */
-static void
-check_connection (void *cls)
-{
- struct PostgresClosure *pg = cls;
-
- GNUNET_PQ_reconnect_if_down (pg->conn);
-}
-
-
-/**
- * Do a pre-flight check that we are not in an uncommitted transaction.
- * If we are, try to commit the previous transaction and output a warning.
- * Does not return anything, as we will continue regardless of the outcome.
- *
- * @param cls the `struct PostgresClosure` with the plugin-specific state
- */
-static void
-postgres_preflight (void *cls)
-{
- struct PostgresClosure *pg = cls;
- struct GNUNET_PQ_ExecuteStatement es[] = {
- GNUNET_PQ_make_execute ("COMMIT"),
- GNUNET_PQ_EXECUTE_STATEMENT_END
- };
-
- if (NULL == pg->transaction_name)
- return; /* all good */
- if (GNUNET_OK ==
- GNUNET_PQ_exec_statements (pg->conn,
- es))
- {
- GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "BUG: Preflight check committed transaction `%s'!\n",
- pg->transaction_name);
- }
- else
- {
- GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "BUG: Preflight check failed to commit transaction `%s'!\n",
- pg->transaction_name);
- }
- pg->transaction_name = NULL;
-}
-
-
-/**
- * Start a transaction.
+ * Initialize tables.
*
* @param cls the `struct PostgresClosure` with the plugin-specific state
- * @param name unique name identifying the transaction (for debugging),
- * must point to a constant
- * @return #GNUNET_OK on success
+ * @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
*/
-static int
-begin_transaction (void *cls,
- const char *name)
+static enum GNUNET_GenericReturnValue
+postgres_create_tables (void *cls)
{
- struct PostgresClosure *pg = cls;
- struct GNUNET_PQ_ExecuteStatement es[] = {
- GNUNET_PQ_make_execute ("START TRANSACTION ISOLATION LEVEL SERIALIZABLE"),
- GNUNET_PQ_EXECUTE_STATEMENT_END
- };
+ struct PostgresClosure *pc = cls;
+ struct GNUNET_PQ_Context *conn;
- check_connection (pg);
- postgres_preflight (pg);
- pg->transaction_name = name;
- if (GNUNET_OK !=
- GNUNET_PQ_exec_statements (pg->conn,
- es))
- {
- TALER_LOG_ERROR ("Failed to start transaction\n");
- GNUNET_break (0);
+ conn = GNUNET_PQ_connect_with_cfg (pc->cfg,
+ "stasis-postgres",
+ "stasis-",
+ NULL,
+ NULL);
+ if (NULL == conn)
return GNUNET_SYSERR;
- }
+ GNUNET_PQ_disconnect (conn);
return GNUNET_OK;
}
/**
-* Roll back the current transaction of a database connection.
-*
-* @param cls the `struct PostgresClosure` with the plugin-specific state
-* @return #GNUNET_OK on success
-*/
-static void
-rollback (void *cls)
-{
- struct PostgresClosure *pg = cls;
- struct GNUNET_PQ_ExecuteStatement es[] = {
- GNUNET_PQ_make_execute ("ROLLBACK"),
- GNUNET_PQ_EXECUTE_STATEMENT_END
- };
-
- if (GNUNET_OK !=
- GNUNET_PQ_exec_statements (pg->conn,
- es))
- {
- TALER_LOG_ERROR ("Failed to rollback transaction\n");
- GNUNET_break (0);
- }
- pg->transaction_name = NULL;
-}
-
-
-/**
- * Commit the current transaction of a database connection.
- *
- * @param cls the `struct PostgresClosure` with the plugin-specific state
- * @return transaction status code
- */
-static enum GNUNET_DB_QueryStatus
-commit_transaction (void *cls)
-{
- struct PostgresClosure *pg = cls;
- enum GNUNET_DB_QueryStatus qs;
- struct GNUNET_PQ_QueryParam no_params[] = {
- GNUNET_PQ_query_param_end
- };
-
- qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
- "do_commit",
- no_params);
- pg->transaction_name = NULL;
- return qs;
-}
-
-
-/**
- * Register callback to be invoked on events of type @a es.
- *
- * @param cls database context to use
- * @param es specification of the event to listen for
- * @param timeout how long to wait for the event
- * @param cb function to call when the event happens, possibly
- * multiple times (until cancel is invoked)
- * @param cb_cls closure for @a cb
- * @return handle useful to cancel the listener
- */
-static struct GNUNET_DB_EventHandler *
-postgres_event_listen (void *cls,
- const struct GNUNET_DB_EventHeaderP *es,
- struct GNUNET_TIME_Relative timeout,
- GNUNET_DB_EventCallback cb,
- void *cb_cls)
-{
- struct PostgresClosure *pg = cls;
-
- return GNUNET_PQ_event_listen (pg->conn,
- es,
- timeout,
- cb,
- cb_cls);
-}
-
-
-/**
- * Stop notifications.
- *
- * @param eh handle to unregister.
- */
-static void
-postgres_event_listen_cancel (struct GNUNET_DB_EventHandler *eh)
-{
- GNUNET_PQ_event_listen_cancel (eh);
-}
-
-
-/**
- * Notify all that listen on @a es of an event.
- *
- * @param cls database context to use
- * @param es specification of the event to generate
- * @param extra additional event data provided
- * @param extra_size number of bytes in @a extra
- */
-static void
-postgres_event_notify (void *cls,
- const struct GNUNET_DB_EventHeaderP *es,
- const void *extra,
- size_t extra_size)
-{
- struct PostgresClosure *pg = cls;
-
- return GNUNET_PQ_event_notify (pg->conn,
- es,
- extra,
- extra_size);
-}
-
-
-/**
- * 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 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 GNUNET_DB_QueryStatus
-postgres_gc (void *cls,
- struct GNUNET_TIME_Absolute expire_backups,
- struct GNUNET_TIME_Absolute expire_pending_payments)
-{
- struct PostgresClosure *pg = cls;
- struct GNUNET_PQ_QueryParam params[] = {
- GNUNET_PQ_query_param_absolute_time (&expire_backups),
- GNUNET_PQ_query_param_end
- };
- struct GNUNET_PQ_QueryParam params2[] = {
- GNUNET_PQ_query_param_absolute_time (&expire_pending_payments),
- GNUNET_PQ_query_param_end
- };
- enum GNUNET_DB_QueryStatus qs;
-
- 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_recdoc_pending_payments",
- params2);
-}
-
-
-/**
- * Store encrypted recovery document.
+ * Establish connection to the database.
*
- * @param cls closure
- * @param account_pub public key of the user's account
- * @param account_sig signature affirming storage request
- * @param recovery_data_hash hash of @a data
- * @param recovery_data contains encrypted_recovery_document
- * @param recovery_data_size size of data blob
- * @param payment_secret identifier for the payment, used to later charge on
uploads
- * @param[out] version set to the version assigned to the document by the
database
- * @return transaction status, 0 if upload could not be finished because @a
payment_secret
- * did not have enough upload left; HARD error if @a payment_secret is
unknown, ...
+ * @param cls plugin context
+ * @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failure
*/
-static enum ANASTASIS_DB_StoreStatus
-postgres_store_recovery_document (
- void *cls,
- const struct ANASTASIS_CRYPTO_AccountPublicKeyP *account_pub,
- const struct ANASTASIS_AccountSignatureP *account_sig,
- const struct GNUNET_HashCode *recovery_data_hash,
- const void *recovery_data,
- size_t recovery_data_size,
- const struct ANASTASIS_PaymentSecretP *payment_secret,
- uint32_t *version)
+static enum GNUNET_GenericReturnValue
+postgres_connect (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_PreparedStatement ps[] = {
+ GNUNET_PQ_make_prepare ("user_insert",
+ "INSERT INTO anastasis_user "
+ "(user_id"
+ ",expiration_date"
+ ") VALUES "
+ "($1, $2);",
+ 2),
+ GNUNET_PQ_make_prepare ("do_commit",
+ "COMMIT",
+ 0),
+ GNUNET_PQ_make_prepare ("user_select",
+ "SELECT"
+ " expiration_date "
+ "FROM anastasis_user"
+ " WHERE user_id=$1"
+ " FOR UPDATE;",
+ 1),
+ GNUNET_PQ_make_prepare ("user_update",
+ "UPDATE anastasis_user"
+ " SET "
+ " expiration_date=$1"
+ " WHERE user_id=$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("recdoc_payment_insert",
+ "INSERT INTO anastasis_recdoc_payment "
+ "(user_id"
+ ",post_counter"
+ ",amount_val"
+ ",amount_frac"
+ ",payment_identifier"
+ ",creation_date"
+ ") VALUES "
+ "($1, $2, $3, $4, $5, $6);",
+ 6),
+ GNUNET_PQ_make_prepare ("challenge_payment_insert",
+ "INSERT INTO anastasis_challenge_payment "
+ "(truth_uuid"
+ ",amount_val"
+ ",amount_frac"
+ ",payment_identifier"
+ ",creation_date"
+ ") VALUES "
+ "($1, $2, $3, $4, $5);",
+ 5),
+ GNUNET_PQ_make_prepare ("truth_payment_insert",
+ "INSERT INTO anastasis_truth_payment "
+ "(truth_uuid"
+ ",amount_val"
+ ",amount_frac"
+ ",expiration"
+ ") VALUES "
+ "($1, $2, $3, $4);",
+ 4),
+ GNUNET_PQ_make_prepare ("recdoc_payment_done",
+ "UPDATE anastasis_recdoc_payment "
+ "SET"
+ " paid=TRUE "
+ "WHERE"
+ " payment_identifier=$1"
+ " AND"
+ " user_id=$2"
+ " AND"
+ " paid=FALSE;",
+ 2),
+ GNUNET_PQ_make_prepare ("challenge_refund_update",
+ "UPDATE anastasis_challenge_payment "
+ "SET"
+ " refunded=TRUE "
+ "WHERE"
+ " payment_identifier=$1"
+ " AND"
+ " paid=TRUE"
+ " AND"
+ " truth_uuid=$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("challenge_payment_done",
+ "UPDATE anastasis_challenge_payment "
+ "SET"
+ " paid=TRUE "
+ "WHERE"
+ " payment_identifier=$1"
+ " AND"
+ " refunded=FALSE"
+ " AND"
+ " truth_uuid=$2"
+ " AND"
+ " paid=FALSE;",
+ 2),
+ GNUNET_PQ_make_prepare ("recdoc_payment_select",
+ "SELECT"
+ " creation_date"
+ ",post_counter"
+ ",amount_val"
+ ",amount_frac"
+ ",paid"
+ " FROM anastasis_recdoc_payment"
+ " WHERE payment_identifier=$1;",
+ 1),
+ GNUNET_PQ_make_prepare ("truth_payment_select",
+ "SELECT"
+ " expiration"
+ " FROM anastasis_truth_payment"
+ " WHERE truth_uuid=$1"
+ " AND expiration>$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("challenge_payment_select",
+ "SELECT"
+ " creation_date"
+ ",amount_val"
+ ",amount_frac"
+ ",paid"
+ " FROM anastasis_challenge_payment"
+ " WHERE payment_identifier=$1"
+ " AND truth_uuid=$2"
+ " AND refunded=FALSE"
+ " AND counter>0;",
+ 1),
+ GNUNET_PQ_make_prepare ("challenge_pending_payment_select",
+ "SELECT"
+ " creation_date"
+ ",payment_identifier"
+ ",amount_val"
+ ",amount_frac"
+ " FROM anastasis_challenge_payment"
+ " WHERE"
+ " paid=FALSE"
+ " AND"
+ " refunded=FALSE"
+ " AND"
+ " truth_uuid=$1"
+ " AND"
+ " creation_date > $2;",
+ 1),
+ GNUNET_PQ_make_prepare ("recdoc_payments_select",
+ "SELECT"
+ " user_id"
+ ",payment_identifier"
+ ",amount_val"
+ ",amount_frac"
+ " FROM anastasis_recdoc_payment"
+ " WHERE paid=FALSE;",
+ 0),
+ GNUNET_PQ_make_prepare ("gc_accounts",
+ "DELETE FROM anastasis_user "
+ "WHERE"
+ " expiration_date < $1;",
+ 1),
+ GNUNET_PQ_make_prepare ("gc_recdoc_pending_payments",
+ "DELETE FROM anastasis_recdoc_payment "
+ "WHERE"
+ " paid=FALSE"
+ " AND"
+ " creation_date < $1;",
+ 1),
+ GNUNET_PQ_make_prepare ("gc_challenge_pending_payments",
+ "DELETE FROM anastasis_challenge_payment "
+ "WHERE"
+ " (paid=FALSE"
+ " OR"
+ " refunded=TRUE)"
+ " AND"
+ " creation_date < $1;",
+ 1),
+ GNUNET_PQ_make_prepare ("truth_insert",
+ "INSERT INTO anastasis_truth "
+ "(truth_uuid"
+ ",key_share_data"
+ ",method_name"
+ ",encrypted_truth"
+ ",truth_mime"
+ ",expiration"
+ ") VALUES "
+ "($1, $2, $3, $4, $5, $6);",
+ 6),
+
+ GNUNET_PQ_make_prepare ("test_auth_iban_payment",
+ "SELECT"
+ " credit_val"
+ ",credit_frac"
+ ",wire_subject"
+ " FROM anastasis_auth_iban_in"
+ " WHERE debit_account_details=$1"
+ " AND execution_date>=$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("store_auth_iban_payment_details",
+ "INSERT INTO anastasis_auth_iban_in "
+ "(wire_reference"
+ ",wire_subject"
+ ",credit_val"
+ ",credit_frac"
+ ",debit_account_details"
+ ",credit_account_details"
+ ",execution_date"
+ ") VALUES "
+ "($1, $2, $3, $4, $5, $6, $7);",
+ 7),
+
+
+ GNUNET_PQ_make_prepare ("recovery_document_insert",
+ "INSERT INTO anastasis_recoverydocument "
+ "(user_id"
+ ",version"
+ ",account_sig"
+ ",recovery_data_hash"
+ ",recovery_data"
+ ") VALUES "
+ "($1, $2, $3, $4, $5);",
+ 5),
+ GNUNET_PQ_make_prepare ("truth_select",
+ "SELECT "
+ " method_name"
+ ",encrypted_truth"
+ ",truth_mime"
+ " FROM anastasis_truth"
+ " WHERE truth_uuid =$1;",
+ 1),
+ GNUNET_PQ_make_prepare ("latest_recoverydocument_select",
+ "SELECT "
+ " version"
+ ",account_sig"
+ ",recovery_data_hash"
+ ",recovery_data"
+ " FROM anastasis_recoverydocument"
+ " WHERE user_id =$1 "
+ " ORDER BY version DESC"
+ " LIMIT 1;",
+ 1),
+ GNUNET_PQ_make_prepare ("latest_recovery_version_select",
+ "SELECT"
+ " version"
+ ",recovery_data_hash"
+ ",expiration_date"
+ " FROM anastasis_recoverydocument"
+ " JOIN anastasis_user USING (user_id)"
+ " WHERE user_id=$1"
+ " ORDER BY version DESC"
+ " LIMIT 1;",
+ 1),
+ GNUNET_PQ_make_prepare ("recoverydocument_select",
+ "SELECT "
+ " account_sig"
+ ",recovery_data_hash"
+ ",recovery_data"
+ " FROM anastasis_recoverydocument"
+ " WHERE user_id=$1"
+ " AND version=$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("postcounter_select",
+ "SELECT"
+ " post_counter"
+ " FROM anastasis_recdoc_payment"
+ " WHERE user_id=$1"
+ " AND payment_identifier=$2;",
+ 2),
+ GNUNET_PQ_make_prepare ("postcounter_update",
+ "UPDATE "
+ "anastasis_recdoc_payment "
+ "SET "
+ "post_counter=$1 "
+ "WHERE user_id =$2 "
+ "AND payment_identifier=$3;",
+ 3),
+ GNUNET_PQ_make_prepare ("key_share_select",
+ "SELECT "
+ "key_share_data "
+ "FROM "
+ "anastasis_truth "
+ "WHERE truth_uuid =$1;",
+ 1),
+ GNUNET_PQ_make_prepare ("challengecode_insert",
+ "INSERT INTO anastasis_challengecode "
+ "(truth_uuid"
+ ",code"
+ ",creation_date"
+ ",expiration_date"
+ ",retry_counter"
+ ") VALUES "
+ "($1, $2, $3, $4, $5);",
+ 5),
+ GNUNET_PQ_make_prepare ("challengecode_select",
+ "SELECT "
+ " code"
+ ",satisfied"
+ " FROM anastasis_challengecode"
+ " WHERE truth_uuid=$1"
+ " AND expiration_date > $2"
+ " AND retry_counter != 0;",
+ 2),
+ GNUNET_PQ_make_prepare ("challengecode_set_satisfied",
+ "UPDATE anastasis_challengecode"
+ " SET satisfied=TRUE"
+ " WHERE truth_uuid=$1"
+ " AND code=$2"
+ " AND creation_date IN"
+ " (SELECT creation_date"
+ " FROM anastasis_challengecode"
+ " WHERE truth_uuid=$1"
+ " AND code=$2"
+ " ORDER BY creation_date DESC"
+ " LIMIT 1);",
+ 2),
+ GNUNET_PQ_make_prepare ("challengecode_test_satisfied",
+ "SELECT 1 FROM anastasis_challengecode"
+ " WHERE truth_uuid=$1"
+ " AND satisfied=TRUE"
+ " AND code=$2"
+ " AND creation_date >= $3"
+ " LIMIT 1;",
+ 3),
+ GNUNET_PQ_make_prepare ("challengecode_select_meta",
+ "SELECT "
+ " code"
+ ",retry_counter"
+ ",retransmission_date"
+ " FROM anastasis_challengecode"
+ " WHERE truth_uuid=$1"
+ " AND expiration_date > $2"
+ " AND creation_date > $3"
+ " ORDER BY creation_date DESC"
+ " LIMIT 1;",
+ 2),
+ GNUNET_PQ_make_prepare ("challengecode_update_retry",
+ "UPDATE anastasis_challengecode"
+ " SET retry_counter=retry_counter - 1"
+ " WHERE truth_uuid=$1"
+ " AND code=$2"
+ " AND retry_counter != 0;",
+ 1),
+ GNUNET_PQ_make_prepare ("challengepayment_dec_counter",
+ "UPDATE anastasis_challenge_payment"
+ " SET counter=counter - 1"
+ " WHERE truth_uuid=$1"
+ " AND payment_identifier=$2"
+ " AND counter > 0;",
+ 2),
+ GNUNET_PQ_make_prepare ("challengecode_mark_sent",
+ "UPDATE anastasis_challengecode"
+ " SET retransmission_date=$3"
+ " WHERE truth_uuid=$1"
+ " AND code=$2"
+ " AND creation_date IN"
+ " (SELECT creation_date"
+ " FROM anastasis_challengecode"
+ " WHERE truth_uuid=$1"
+ " AND code=$2"
+ " ORDER BY creation_date DESC"
+ " LIMIT 1);",
+ 3),
+ GNUNET_PQ_make_prepare ("get_last_auth_iban_payment",
+ "SELECT "
+ " wire_reference"
+ " FROM anastasis_auth_iban_in"
+ " WHERE credit_account_details=$1"
+ " ORDER BY wire_reference DESC"
+ " LIMIT 1;",
+ 1),
+ GNUNET_PQ_make_prepare ("gc_challengecodes",
+ "DELETE FROM anastasis_challengecode "
+ "WHERE "
+ "expiration_date < $1;",
+ 1),
+ GNUNET_PQ_PREPARED_STATEMENT_END
+ };
+
+ pg->conn = GNUNET_PQ_connect_with_cfg (pg->cfg,
+ "stasis-postgres",
+ NULL,
+ NULL,
+ ps);
+ if (NULL == pg->conn)
+ return GNUNET_SYSERR;
+ return GNUNET_OK;
+}
+
+
+/**
+ * Check that the database connection is still up.
+ *
+ * @param cls a `struct PostgresClosure` with connection to check
+ */
+static void
+check_connection (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+
+ GNUNET_PQ_reconnect_if_down (pg->conn);
+}
+
+
+/**
+ * Do a pre-flight check that we are not in an uncommitted transaction.
+ * If we are, try to commit the previous transaction and output a warning.
+ * Does not return anything, as we will continue regardless of the outcome.
+ *
+ * @param cls the `struct PostgresClosure` with the plugin-specific state
+ */
+static void
+postgres_preflight (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_ExecuteStatement es[] = {
+ GNUNET_PQ_make_execute ("COMMIT"),
+ GNUNET_PQ_EXECUTE_STATEMENT_END
+ };
+
+ if (NULL == pg->transaction_name)
+ return; /* all good */
+ if (GNUNET_OK ==
+ GNUNET_PQ_exec_statements (pg->conn,
+ es))
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "BUG: Preflight check committed transaction `%s'!\n",
+ pg->transaction_name);
+ }
+ else
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ "BUG: Preflight check failed to commit transaction `%s'!\n",
+ pg->transaction_name);
+ }
+ pg->transaction_name = NULL;
+}
+
+
+/**
+ * Start a transaction.
+ *
+ * @param cls the `struct PostgresClosure` with the plugin-specific state
+ * @param name unique name identifying the transaction (for debugging),
+ * must point to a constant
+ * @return #GNUNET_OK on success
+ */
+static int
+begin_transaction (void *cls,
+ const char *name)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_ExecuteStatement es[] = {
+ GNUNET_PQ_make_execute ("START TRANSACTION ISOLATION LEVEL SERIALIZABLE"),
+ GNUNET_PQ_EXECUTE_STATEMENT_END
+ };
+
+ check_connection (pg);
+ postgres_preflight (pg);
+ pg->transaction_name = name;
+ if (GNUNET_OK !=
+ GNUNET_PQ_exec_statements (pg->conn,
+ es))
+ {
+ TALER_LOG_ERROR ("Failed to start transaction\n");
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+ return GNUNET_OK;
+}
+
+
+/**
+* Roll back the current transaction of a database connection.
+*
+* @param cls the `struct PostgresClosure` with the plugin-specific state
+* @return #GNUNET_OK on success
+*/
+static void
+rollback (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_ExecuteStatement es[] = {
+ GNUNET_PQ_make_execute ("ROLLBACK"),
+ GNUNET_PQ_EXECUTE_STATEMENT_END
+ };
+
+ if (GNUNET_OK !=
+ GNUNET_PQ_exec_statements (pg->conn,
+ es))
+ {
+ TALER_LOG_ERROR ("Failed to rollback transaction\n");
+ GNUNET_break (0);
+ }
+ pg->transaction_name = NULL;
+}
+
+
+/**
+ * Commit the current transaction of a database connection.
+ *
+ * @param cls the `struct PostgresClosure` with the plugin-specific state
+ * @return transaction status code
+ */
+static enum GNUNET_DB_QueryStatus
+commit_transaction (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+ enum GNUNET_DB_QueryStatus qs;
+ struct GNUNET_PQ_QueryParam no_params[] = {
+ GNUNET_PQ_query_param_end
+ };
+
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "do_commit",
+ no_params);
+ pg->transaction_name = NULL;
+ return qs;
+}
+
+
+/**
+ * Register callback to be invoked on events of type @a es.
+ *
+ * @param cls database context to use
+ * @param es specification of the event to listen for
+ * @param timeout how long to wait for the event
+ * @param cb function to call when the event happens, possibly
+ * multiple times (until cancel is invoked)
+ * @param cb_cls closure for @a cb
+ * @return handle useful to cancel the listener
+ */
+static struct GNUNET_DB_EventHandler *
+postgres_event_listen (void *cls,
+ const struct GNUNET_DB_EventHeaderP *es,
+ struct GNUNET_TIME_Relative timeout,
+ GNUNET_DB_EventCallback cb,
+ void *cb_cls)
+{
+ struct PostgresClosure *pg = cls;
+
+ return GNUNET_PQ_event_listen (pg->conn,
+ es,
+ timeout,
+ cb,
+ cb_cls);
+}
+
+
+/**
+ * Stop notifications.
+ *
+ * @param eh handle to unregister.
+ */
+static void
+postgres_event_listen_cancel (struct GNUNET_DB_EventHandler *eh)
+{
+ GNUNET_PQ_event_listen_cancel (eh);
+}
+
+
+/**
+ * Notify all that listen on @a es of an event.
+ *
+ * @param cls database context to use
+ * @param es specification of the event to generate
+ * @param extra additional event data provided
+ * @param extra_size number of bytes in @a extra
+ */
+static void
+postgres_event_notify (void *cls,
+ const struct GNUNET_DB_EventHeaderP *es,
+ const void *extra,
+ size_t extra_size)
+{
+ struct PostgresClosure *pg = cls;
+
+ return GNUNET_PQ_event_notify (pg->conn,
+ es,
+ extra,
+ extra_size);
+}
+
+
+/**
+ * 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 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 GNUNET_DB_QueryStatus
+postgres_gc (void *cls,
+ struct GNUNET_TIME_Absolute expire_backups,
+ struct GNUNET_TIME_Absolute expire_pending_payments)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_absolute_time (&expire_backups),
+ GNUNET_PQ_query_param_end
+ };
+ struct GNUNET_PQ_QueryParam params2[] = {
+ GNUNET_PQ_query_param_absolute_time (&expire_pending_payments),
+ GNUNET_PQ_query_param_end
+ };
+ enum GNUNET_DB_QueryStatus qs;
+
+ 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_recdoc_pending_payments",
+ params2);
+}
+
+
+/**
+ * Store encrypted recovery document.
+ *
+ * @param cls closure
+ * @param account_pub public key of the user's account
+ * @param account_sig signature affirming storage request
+ * @param recovery_data_hash hash of @a data
+ * @param recovery_data contains encrypted_recovery_document
+ * @param recovery_data_size size of data blob
+ * @param payment_secret identifier for the payment, used to later charge on
uploads
+ * @param[out] version set to the version assigned to the document by the
database
+ * @return transaction status, 0 if upload could not be finished because @a
payment_secret
+ * did not have enough upload left; HARD error if @a payment_secret is
unknown, ...
+ */
+static enum ANASTASIS_DB_StoreStatus
+postgres_store_recovery_document (
+ void *cls,
+ const struct ANASTASIS_CRYPTO_AccountPublicKeyP *account_pub,
+ const struct ANASTASIS_AccountSignatureP *account_sig,
+ const struct GNUNET_HashCode *recovery_data_hash,
+ const void *recovery_data,
+ size_t recovery_data_size,
+ const struct ANASTASIS_PaymentSecretP *payment_secret,
+ uint32_t *version)
{
struct PostgresClosure *pg = cls;
enum GNUNET_DB_QueryStatus qs;
@@ -2214,450 +2624,76 @@ postgres_mark_challenge_sent (
check_connection (pg);
{
struct GNUNET_TIME_Absolute now;
- struct GNUNET_PQ_QueryParam params[] = {
- GNUNET_PQ_query_param_auto_from_type (truth_uuid),
- GNUNET_PQ_query_param_uint64 (&code),
- TALER_PQ_query_param_absolute_time (&now),
- GNUNET_PQ_query_param_end
- };
-
- now = GNUNET_TIME_absolute_get ();
- GNUNET_TIME_round_abs (&now);
- qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
- "challengecode_mark_sent",
- params);
- if (qs <= 0)
- return qs;
- }
- {
- struct GNUNET_PQ_QueryParam params[] = {
- GNUNET_PQ_query_param_auto_from_type (truth_uuid),
- GNUNET_PQ_query_param_auto_from_type (payment_secret),
- GNUNET_PQ_query_param_end
- };
-
- qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
- "challengepayment_dec_counter",
- params);
- if (GNUNET_DB_STATUS_SUCCESS_NO_RESULTS == qs)
- return GNUNET_DB_STATUS_SUCCESS_ONE_RESULT; /* probably was free */
- return qs;
- }
-}
-
-
-/**
- * Function called to remove all expired codes from the database.
- *
- * @return transaction status
- */
-enum GNUNET_DB_QueryStatus
-postgres_challenge_gc (void *cls)
-{
- struct PostgresClosure *pg = cls;
- struct GNUNET_TIME_Absolute time_now = GNUNET_TIME_absolute_get ();
- struct GNUNET_PQ_QueryParam params[] = {
- GNUNET_PQ_query_param_absolute_time (&time_now),
- GNUNET_PQ_query_param_end
- };
-
- check_connection (pg);
- postgres_preflight (pg);
- return GNUNET_PQ_eval_prepared_non_select (pg->conn,
- "gc_challengecodes",
- params);
-}
-
-
-/**
- * Initialize Postgres database subsystem.
- *
- * @param cls a configuration instance
- * @return NULL on error, otherwise a `struct TALER_ANASTASISDB_Plugin`
- */
-void *
-libanastasis_plugin_db_postgres_init (void *cls)
-{
- struct GNUNET_CONFIGURATION_Handle *cfg = cls;
- struct PostgresClosure *pg;
- struct ANASTASIS_DatabasePlugin *plugin;
- struct GNUNET_PQ_PreparedStatement ps[] = {
- GNUNET_PQ_make_prepare ("user_insert",
- "INSERT INTO anastasis_user "
- "(user_id"
- ",expiration_date"
- ") VALUES "
- "($1, $2);",
- 2),
- GNUNET_PQ_make_prepare ("do_commit",
- "COMMIT",
- 0),
- GNUNET_PQ_make_prepare ("user_select",
- "SELECT"
- " expiration_date "
- "FROM anastasis_user"
- " WHERE user_id=$1"
- " FOR UPDATE;",
- 1),
- GNUNET_PQ_make_prepare ("user_update",
- "UPDATE anastasis_user"
- " SET "
- " expiration_date=$1"
- " WHERE user_id=$2;",
- 2),
- GNUNET_PQ_make_prepare ("recdoc_payment_insert",
- "INSERT INTO anastasis_recdoc_payment "
- "(user_id"
- ",post_counter"
- ",amount_val"
- ",amount_frac"
- ",payment_identifier"
- ",creation_date"
- ") VALUES "
- "($1, $2, $3, $4, $5, $6);",
- 6),
- GNUNET_PQ_make_prepare ("challenge_payment_insert",
- "INSERT INTO anastasis_challenge_payment "
- "(truth_uuid"
- ",amount_val"
- ",amount_frac"
- ",payment_identifier"
- ",creation_date"
- ") VALUES "
- "($1, $2, $3, $4, $5);",
- 5),
- GNUNET_PQ_make_prepare ("truth_payment_insert",
- "INSERT INTO anastasis_truth_payment "
- "(truth_uuid"
- ",amount_val"
- ",amount_frac"
- ",expiration"
- ") VALUES "
- "($1, $2, $3, $4);",
- 4),
- GNUNET_PQ_make_prepare ("recdoc_payment_done",
- "UPDATE anastasis_recdoc_payment "
- "SET"
- " paid=TRUE "
- "WHERE"
- " payment_identifier=$1"
- " AND"
- " user_id=$2"
- " AND"
- " paid=FALSE;",
- 2),
- GNUNET_PQ_make_prepare ("challenge_refund_update",
- "UPDATE anastasis_challenge_payment "
- "SET"
- " refunded=TRUE "
- "WHERE"
- " payment_identifier=$1"
- " AND"
- " paid=TRUE"
- " AND"
- " truth_uuid=$2;",
- 2),
- GNUNET_PQ_make_prepare ("challenge_payment_done",
- "UPDATE anastasis_challenge_payment "
- "SET"
- " paid=TRUE "
- "WHERE"
- " payment_identifier=$1"
- " AND"
- " refunded=FALSE"
- " AND"
- " truth_uuid=$2"
- " AND"
- " paid=FALSE;",
- 2),
- GNUNET_PQ_make_prepare ("recdoc_payment_select",
- "SELECT"
- " creation_date"
- ",post_counter"
- ",amount_val"
- ",amount_frac"
- ",paid"
- " FROM anastasis_recdoc_payment"
- " WHERE payment_identifier=$1;",
- 1),
- GNUNET_PQ_make_prepare ("truth_payment_select",
- "SELECT"
- " expiration"
- " FROM anastasis_truth_payment"
- " WHERE truth_uuid=$1"
- " AND expiration>$2;",
- 2),
- GNUNET_PQ_make_prepare ("challenge_payment_select",
- "SELECT"
- " creation_date"
- ",amount_val"
- ",amount_frac"
- ",paid"
- " FROM anastasis_challenge_payment"
- " WHERE payment_identifier=$1"
- " AND truth_uuid=$2"
- " AND refunded=FALSE"
- " AND counter>0;",
- 1),
- GNUNET_PQ_make_prepare ("challenge_pending_payment_select",
- "SELECT"
- " creation_date"
- ",payment_identifier"
- ",amount_val"
- ",amount_frac"
- " FROM anastasis_challenge_payment"
- " WHERE"
- " paid=FALSE"
- " AND"
- " refunded=FALSE"
- " AND"
- " truth_uuid=$1"
- " AND"
- " creation_date > $2;",
- 1),
- GNUNET_PQ_make_prepare ("recdoc_payments_select",
- "SELECT"
- " user_id"
- ",payment_identifier"
- ",amount_val"
- ",amount_frac"
- " FROM anastasis_recdoc_payment"
- " WHERE paid=FALSE;",
- 0),
- GNUNET_PQ_make_prepare ("gc_accounts",
- "DELETE FROM anastasis_user "
- "WHERE"
- " expiration_date < $1;",
- 1),
- GNUNET_PQ_make_prepare ("gc_recdoc_pending_payments",
- "DELETE FROM anastasis_recdoc_payment "
- "WHERE"
- " paid=FALSE"
- " AND"
- " creation_date < $1;",
- 1),
- GNUNET_PQ_make_prepare ("gc_challenge_pending_payments",
- "DELETE FROM anastasis_challenge_payment "
- "WHERE"
- " (paid=FALSE"
- " OR"
- " refunded=TRUE)"
- " AND"
- " creation_date < $1;",
- 1),
- GNUNET_PQ_make_prepare ("truth_insert",
- "INSERT INTO anastasis_truth "
- "(truth_uuid"
- ",key_share_data"
- ",method_name"
- ",encrypted_truth"
- ",truth_mime"
- ",expiration"
- ") VALUES "
- "($1, $2, $3, $4, $5, $6);",
- 6),
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (truth_uuid),
+ GNUNET_PQ_query_param_uint64 (&code),
+ TALER_PQ_query_param_absolute_time (&now),
+ GNUNET_PQ_query_param_end
+ };
- GNUNET_PQ_make_prepare ("test_auth_iban_payment",
- "SELECT"
- " credit_val"
- ",credit_frac"
- ",wire_subject"
- " FROM anastasis_auth_iban_in"
- " WHERE debit_account_details=$1"
- " AND execution_date>=$2;",
- 2),
- GNUNET_PQ_make_prepare ("store_auth_iban_payment_details",
- "INSERT INTO anastasis_auth_iban_in "
- "(wire_reference"
- ",wire_subject"
- ",credit_val"
- ",credit_frac"
- ",debit_account_details"
- ",credit_account_details"
- ",execution_date"
- ") VALUES "
- "($1, $2, $3, $4, $5, $6, $7);",
- 7),
+ now = GNUNET_TIME_absolute_get ();
+ GNUNET_TIME_round_abs (&now);
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "challengecode_mark_sent",
+ params);
+ if (qs <= 0)
+ return qs;
+ }
+ {
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_auto_from_type (truth_uuid),
+ GNUNET_PQ_query_param_auto_from_type (payment_secret),
+ GNUNET_PQ_query_param_end
+ };
+ qs = GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "challengepayment_dec_counter",
+ params);
+ if (GNUNET_DB_STATUS_SUCCESS_NO_RESULTS == qs)
+ return GNUNET_DB_STATUS_SUCCESS_ONE_RESULT; /* probably was free */
+ return qs;
+ }
+}
- GNUNET_PQ_make_prepare ("recovery_document_insert",
- "INSERT INTO anastasis_recoverydocument "
- "(user_id"
- ",version"
- ",account_sig"
- ",recovery_data_hash"
- ",recovery_data"
- ") VALUES "
- "($1, $2, $3, $4, $5);",
- 5),
- GNUNET_PQ_make_prepare ("truth_select",
- "SELECT "
- " method_name"
- ",encrypted_truth"
- ",truth_mime"
- " FROM anastasis_truth"
- " WHERE truth_uuid =$1;",
- 1),
- GNUNET_PQ_make_prepare ("latest_recoverydocument_select",
- "SELECT "
- " version"
- ",account_sig"
- ",recovery_data_hash"
- ",recovery_data"
- " FROM anastasis_recoverydocument"
- " WHERE user_id =$1 "
- " ORDER BY version DESC"
- " LIMIT 1;",
- 1),
- GNUNET_PQ_make_prepare ("latest_recovery_version_select",
- "SELECT"
- " version"
- ",recovery_data_hash"
- ",expiration_date"
- " FROM anastasis_recoverydocument"
- " JOIN anastasis_user USING (user_id)"
- " WHERE user_id=$1"
- " ORDER BY version DESC"
- " LIMIT 1;",
- 1),
- GNUNET_PQ_make_prepare ("recoverydocument_select",
- "SELECT "
- " account_sig"
- ",recovery_data_hash"
- ",recovery_data"
- " FROM anastasis_recoverydocument"
- " WHERE user_id=$1"
- " AND version=$2;",
- 2),
- GNUNET_PQ_make_prepare ("postcounter_select",
- "SELECT"
- " post_counter"
- " FROM anastasis_recdoc_payment"
- " WHERE user_id=$1"
- " AND payment_identifier=$2;",
- 2),
- GNUNET_PQ_make_prepare ("postcounter_update",
- "UPDATE "
- "anastasis_recdoc_payment "
- "SET "
- "post_counter=$1 "
- "WHERE user_id =$2 "
- "AND payment_identifier=$3;",
- 3),
- GNUNET_PQ_make_prepare ("key_share_select",
- "SELECT "
- "key_share_data "
- "FROM "
- "anastasis_truth "
- "WHERE truth_uuid =$1;",
- 1),
- GNUNET_PQ_make_prepare ("challengecode_insert",
- "INSERT INTO anastasis_challengecode "
- "(truth_uuid"
- ",code"
- ",creation_date"
- ",expiration_date"
- ",retry_counter"
- ") VALUES "
- "($1, $2, $3, $4, $5);",
- 5),
- GNUNET_PQ_make_prepare ("challengecode_select",
- "SELECT "
- " code"
- ",satisfied"
- " FROM anastasis_challengecode"
- " WHERE truth_uuid=$1"
- " AND expiration_date > $2"
- " AND retry_counter != 0;",
- 2),
- GNUNET_PQ_make_prepare ("challengecode_set_satisfied",
- "UPDATE anastasis_challengecode"
- " SET satisfied=TRUE"
- " WHERE truth_uuid=$1"
- " AND code=$2"
- " AND creation_date IN"
- " (SELECT creation_date"
- " FROM anastasis_challengecode"
- " WHERE truth_uuid=$1"
- " AND code=$2"
- " ORDER BY creation_date DESC"
- " LIMIT 1);",
- 2),
- GNUNET_PQ_make_prepare ("challengecode_test_satisfied",
- "SELECT 1 FROM anastasis_challengecode"
- " WHERE truth_uuid=$1"
- " AND satisfied=TRUE"
- " AND code=$2"
- " AND creation_date >= $3"
- " LIMIT 1;",
- 3),
- GNUNET_PQ_make_prepare ("challengecode_select_meta",
- "SELECT "
- " code"
- ",retry_counter"
- ",retransmission_date"
- " FROM anastasis_challengecode"
- " WHERE truth_uuid=$1"
- " AND expiration_date > $2"
- " AND creation_date > $3"
- " ORDER BY creation_date DESC"
- " LIMIT 1;",
- 2),
- GNUNET_PQ_make_prepare ("challengecode_update_retry",
- "UPDATE anastasis_challengecode"
- " SET retry_counter=retry_counter - 1"
- " WHERE truth_uuid=$1"
- " AND code=$2"
- " AND retry_counter != 0;",
- 1),
- GNUNET_PQ_make_prepare ("challengepayment_dec_counter",
- "UPDATE anastasis_challenge_payment"
- " SET counter=counter - 1"
- " WHERE truth_uuid=$1"
- " AND payment_identifier=$2"
- " AND counter > 0;",
- 2),
- GNUNET_PQ_make_prepare ("challengecode_mark_sent",
- "UPDATE anastasis_challengecode"
- " SET retransmission_date=$3"
- " WHERE truth_uuid=$1"
- " AND code=$2"
- " AND creation_date IN"
- " (SELECT creation_date"
- " FROM anastasis_challengecode"
- " WHERE truth_uuid=$1"
- " AND code=$2"
- " ORDER BY creation_date DESC"
- " LIMIT 1);",
- 3),
- GNUNET_PQ_make_prepare ("get_last_auth_iban_payment",
- "SELECT "
- " wire_reference"
- " FROM anastasis_auth_iban_in"
- " WHERE credit_account_details=$1"
- " ORDER BY wire_reference DESC"
- " LIMIT 1;",
- 1),
- GNUNET_PQ_make_prepare ("gc_challengecodes",
- "DELETE FROM anastasis_challengecode "
- "WHERE "
- "expiration_date < $1;",
- 1),
- GNUNET_PQ_PREPARED_STATEMENT_END
+
+/**
+ * Function called to remove all expired codes from the database.
+ *
+ * @return transaction status
+ */
+enum GNUNET_DB_QueryStatus
+postgres_challenge_gc (void *cls)
+{
+ struct PostgresClosure *pg = cls;
+ struct GNUNET_TIME_Absolute time_now = GNUNET_TIME_absolute_get ();
+ struct GNUNET_PQ_QueryParam params[] = {
+ GNUNET_PQ_query_param_absolute_time (&time_now),
+ GNUNET_PQ_query_param_end
};
+ check_connection (pg);
+ postgres_preflight (pg);
+ return GNUNET_PQ_eval_prepared_non_select (pg->conn,
+ "gc_challengecodes",
+ params);
+}
+
+
+/**
+ * Initialize Postgres database subsystem.
+ *
+ * @param cls a configuration instance
+ * @return NULL on error, otherwise a `struct TALER_ANASTASISDB_Plugin`
+ */
+void *
+libanastasis_plugin_db_postgres_init (void *cls)
+{
+ struct GNUNET_CONFIGURATION_Handle *cfg = cls;
+ struct PostgresClosure *pg;
+ struct ANASTASIS_DatabasePlugin *plugin;
+
pg = GNUNET_new (struct PostgresClosure);
pg->cfg = cfg;
- pg->conn = GNUNET_PQ_connect_with_cfg (cfg,
- "stasis-postgres",
- "stasis-",
- NULL,
- ps);
- if (NULL == pg->conn)
- {
- GNUNET_free (pg);
- return NULL;
- }
if (GNUNET_OK !=
GNUNET_CONFIGURATION_get_value_string (cfg,
"taler",
@@ -2673,6 +2709,8 @@ libanastasis_plugin_db_postgres_init (void *cls)
}
plugin = GNUNET_new (struct ANASTASIS_DatabasePlugin);
plugin->cls = pg;
+ plugin->connect = &postgres_connect;
+ plugin->create_tables = &postgres_create_tables;
plugin->drop_tables = &postgres_drop_tables;
plugin->gc = &postgres_gc;
plugin->preflight = &postgres_preflight;
diff --git a/src/stasis/test_anastasis_db.c b/src/stasis/test_anastasis_db.c
index 204307a..1ec9770 100644
--- a/src/stasis/test_anastasis_db.c
+++ b/src/stasis/test_anastasis_db.c
@@ -92,15 +92,15 @@ run (void *cls)
result = 77;
return;
}
- if (GNUNET_OK != plugin->drop_tables (plugin->cls))
+ (void) plugin->drop_tables (plugin->cls);
+ if (GNUNET_OK !=
+ plugin->create_tables (plugin->cls))
{
- GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
- "Dropping tables failed\n");
result = 77;
return;
}
- ANASTASIS_DB_plugin_unload (plugin);
- if (NULL == (plugin = ANASTASIS_DB_plugin_load (cfg)))
+ if (GNUNET_OK !=
+ plugin->connect (plugin->cls))
{
result = 77;
return;
--
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [taler-anastasis] branch master updated: separate DB creation from plugin loading; fix misc. Debian package issues,
gnunet <=