summaryrefslogtreecommitdiff
path: root/src/mint/mint_db.c
diff options
context:
space:
mode:
authorSree Harsha Totakura <sreeharsha@totakura.in>2015-03-05 18:16:32 +0100
committerSree Harsha Totakura <sreeharsha@totakura.in>2015-03-06 10:32:53 +0100
commit0c4579085a1b9f09b9e41efe69bf2deadfa22cd7 (patch)
tree348d11fee4063de38a4c65d2d0d676cb7d1b5768 /src/mint/mint_db.c
parent7aab16da3430a388b2437c3299e835f9b8a5f9fc (diff)
downloadexchange-0c4579085a1b9f09b9e41efe69bf2deadfa22cd7.tar.gz
exchange-0c4579085a1b9f09b9e41efe69bf2deadfa22cd7.tar.bz2
exchange-0c4579085a1b9f09b9e41efe69bf2deadfa22cd7.zip
db: Implement reserves_in_insert()
Diffstat (limited to 'src/mint/mint_db.c')
-rw-r--r--src/mint/mint_db.c164
1 files changed, 164 insertions, 0 deletions
diff --git a/src/mint/mint_db.c b/src/mint/mint_db.c
index 0bd888221..71e222008 100644
--- a/src/mint/mint_db.c
+++ b/src/mint/mint_db.c
@@ -297,6 +297,15 @@ TALER_MINT_DB_prepare (PGconn *db_conn)
"WHERE reserve_pub=$1 "
"LIMIT 1; ",
1, NULL);
+ PREPARE ("create_reserve",
+ "INSERT INTO reserves ("
+ " reserve_pub,"
+ " current_balance_value,"
+ " current_balance_fraction,"
+ " balance_currency,"
+ " expiration_date) VALUES ("
+ "$1, $2, $3, $4, $5);",
+ 5, NULL);
PREPARE ("update_reserve",
"UPDATE reserves "
"SET"
@@ -305,6 +314,14 @@ TALER_MINT_DB_prepare (PGconn *db_conn)
",expiration_date=$4 "
"WHERE reserve_pub=$1 ",
4, NULL);
+ PREPARE ("create_reserves_in_transaction",
+ "INSERT INTO reserves_in ("
+ " reserve_pub,"
+ " balance_value,"
+ " balance_fraction,"
+ " expiration_date) VALUES ("
+ " $1, $2, $3, $4);",
+ 4, NULL);
PREPARE ("insert_collectable_blindcoins",
"INSERT INTO collectable_blindcoins ( "
" blind_ev, blind_ev_sig "
@@ -732,8 +749,155 @@ TALER_MINT_DB_reserve_get (PGconn *db,
}
+/**
+ * Updates a reserve with the data from the given reserve structure.
+ *
+ * @param db the database connection
+ * @param reserve the reserve structure whose data will be used to update the
+ * corresponding record in the database.
+ * @return #GNUNET_OK upon successful update; #GNUNET_SYSERR upon any error
+ */
+int
+reserves_update (PGconn *db,
+ struct Reserve *reserve)
+{
+ PGresult *result;
+ struct TALER_AmountNBO balance_nbo;
+ struct GNUNET_TIME_AbsoluteNBO expiry_nbo;
+ int ret;
+ if ((NULL == reserve) || (NULL == reserve->pub))
+ return GNUNET_SYSERR;
+ ret = GNUNET_OK;
+ struct TALER_DB_QueryParam params[] = {
+ TALER_DB_QUERY_PARAM_PTR (reserve->pub),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.value),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.fraction),
+ TALER_DB_QUERY_PARAM_PTR (&expiry_nbo),
+ TALER_DB_QUERY_PARAM_END
+ };
+ balance_nbo = TALER_amount_hton (reserve->balance);
+ expiry_nbo = GNUNET_TIME_absolute_hton (reserve->expiry);
+ result = TALER_DB_exec_prepared (db,
+ "update_reserve",
+ params);
+ if (PGRES_COMMAND_OK != PQresultStatus(result))
+ {
+ QUERY_ERR (result);
+ ret = GNUNET_SYSERR;
+ }
+ PQclear (result);
+ return ret;
+}
+
+
+/**
+ * Insert a incoming transaction into reserves. New reserves are also created
+ * through this function.
+ *
+ * @param db the database connection handle
+ * @param reserve the reserve structure. The public key of the reserve should
+ * be set here. Upon successful execution of this function, the
+ * balance and expiration of the reserve will be updated.
+ * @param balance the amount that has to be added to the reserve
+ * @param expiry the new expiration time for the reserve
+ * @return #GNUNET_OK upon success; #GNUNET_SYSERR upon failures
+ */
+int
+TALER_MINT_DB_reserves_in_insert (PGconn *db,
+ struct Reserve *reserve,
+ const struct TALER_Amount balance,
+ const struct GNUNET_TIME_Absolute expiry)
+{
+ struct TALER_AmountNBO balance_nbo;
+ struct GNUNET_TIME_AbsoluteNBO expiry_nbo;
+ PGresult *result;
+ int reserve_exists;
+ if (NULL == reserve)
+ {
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+ if (GNUNET_OK != TALER_MINT_DB_transaction (db))
+ {
+ GNUNET_break (0);
+ return GNUNET_SYSERR;
+ }
+ reserve_exists = TALER_MINT_DB_reserve_get (db, reserve);
+ if (GNUNET_SYSERR == reserve_exists)
+ {
+ TALER_MINT_DB_rollback (db);
+ return GNUNET_SYSERR;
+ }
+ balance_nbo = TALER_amount_hton (balance);
+ expiry_nbo = GNUNET_TIME_absolute_hton (expiry);
+ if (GNUNET_NO == reserve_exists)
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "Reserve does not exist; creating a new one\n");
+ struct TALER_DB_QueryParam params[] = {
+ TALER_DB_QUERY_PARAM_PTR_SIZED (reserve->pub, sizeof (reserve->pub)),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.value),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.fraction),
+ TALER_DB_QUERY_PARAM_PTR_SIZED (balance_nbo.currency,
+ TALER_CURRENCY_LEN),
+ TALER_DB_QUERY_PARAM_PTR (&expiry_nbo),
+ TALER_DB_QUERY_PARAM_END
+ };
+ result = TALER_DB_exec_prepared (db,
+ "create_reserve",
+ params);
+ if (PGRES_COMMAND_OK != PQresultStatus(result))
+ {
+ QUERY_ERR (result);
+ goto rollback;
+ }
+ }
+ PQclear (result); result = NULL;
+ /* create new incoming transaction */
+ struct TALER_DB_QueryParam params[] = {
+ TALER_DB_QUERY_PARAM_PTR (reserve->pub),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.value),
+ TALER_DB_QUERY_PARAM_PTR (&balance_nbo.fraction),
+ TALER_DB_QUERY_PARAM_PTR (&expiry_nbo),
+ TALER_DB_QUERY_PARAM_END
+ };
+ result = TALER_DB_exec_prepared (db,
+ "create_reserves_in_transaction",
+ params);
+ if (PGRES_COMMAND_OK != result)
+ {
+ QUERY_ERR (result);
+ goto rollback;
+ }
+ PQclear (result); result = NULL;
+ if (GNUNET_NO == reserve_exists)
+ {
+ if (GNUNET_OK != TALER_MINT_DB_commit (db))
+ return GNUNET_SYSERR;
+ reserve->balance = balance;
+ reserve->expiry = expiry;
+ return GNUNET_OK;
+ }
+ /* Update reserve */
+ struct Reserve updated_reserve;
+ updated_reserve.pub = reserve->pub;
+ updated_reserve.balance = TALER_amount_add (reserve->balance, balance);
+ updated_reserve.expiry = GNUNET_TIME_absolute_max (expiry, reserve->expiry);
+ if (GNUNET_OK != reserves_update (db, &updated_reserve))
+ goto rollback;
+ if (GNUNET_OK != TALER_MINT_DB_commit (db))
+ return GNUNET_SYSERR;
+ reserve->balance = updated_reserve.balance;
+ reserve->expiry = updated_reserve.expiry;
+ return GNUNET_OK;
+
+ rollback:
+ PQclear (result);
+ TALER_MINT_DB_rollback (db);
+ return GNUNET_SYSERR;
+}
/**