summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarcello Stanisci <marcello.stanisci@inria.fr>2015-10-29 11:33:03 +0100
committerMarcello Stanisci <marcello.stanisci@inria.fr>2015-10-29 11:33:03 +0100
commitbfcb32339fbed0513090b0f546b04c90c11ea474 (patch)
tree2be543c0f888773972e745aafd9b9203f0144e2c
parent6d18f1bfba939c2446c86c1152c274029bd5d63c (diff)
downloadmerchant-bfcb32339fbed0513090b0f546b04c90c11ea474.tar.gz
merchant-bfcb32339fbed0513090b0f546b04c90c11ea474.tar.bz2
merchant-bfcb32339fbed0513090b0f546b04c90c11ea474.zip
- Adding cli debugging feature to contract generation (i.e. it is
possible to GET the frontend with 'curl' in order to invoke the backend to generate a contract. See 'generate_taler_contract.php' to get instructions on how to do it) - Removing unneeded functions from the 'contract' shared library (which presusmably will be entirely removed) - Some minor fixes
-rw-r--r--src/backend-lib/merchant_api_contract.c79
-rw-r--r--src/backend-lib/taler_merchant_contract_lib.h52
-rw-r--r--src/backend/taler-merchant-httpd.c10
-rw-r--r--src/backend/taler-merchant-httpd_contract.c67
-rw-r--r--src/frontend/generate_taler_contract.php23
-rw-r--r--src/include/merchant.h20
6 files changed, 65 insertions, 186 deletions
diff --git a/src/backend-lib/merchant_api_contract.c b/src/backend-lib/merchant_api_contract.c
index da55ce5e..20b69cd3 100644
--- a/src/backend-lib/merchant_api_contract.c
+++ b/src/backend-lib/merchant_api_contract.c
@@ -58,82 +58,3 @@ MERCHANT_get_wire_json (const struct MERCHANT_WIREFORMAT_Sepa *wire,
return root;
}
-
-
-
-/**
-* Take from the frontend the (partly) generated contract and fill
-* the missing values in it; for example, the SEPA details.
-* Moreover, it stores the contract in the DB.
-* @param j_contract parsed contract, originated by the frontend. It will be
-* hold the new values.
-* @param db_conn the handle to the local DB
-* @param contract where to store the (subset of the) contract to be (still) signed
-* @param timestamp contract's timestamp (shall be generated by the merchant)
-* @param expiry the time when the contract will expire
-* @param edate when the merchant wants to receive the wire transfer corresponding
-* to this deal (this value is also a field inside the 'wire' JSON format)
-* @param refund deadline until which the merchant can return the paid amount
-* @param nounce the nounce used to hash the wire details
-* @param a will be pointed to the (allocated) stringified 0-terminated contract
-* @return GNUNET_OK on success, GNUNET_NO if attempting to double insert the
-* same contract, GNUNET_SYSERR in case of other (mostly DB related) errors.
-*/
-
-/**
-* TODO: inspect reference counting and, accordingly, free those json_t*(s)
-* still allocated */
-
-uint32_t
-MERCHANT_handle_contract (json_t *j_contract,
- PGconn *db_conn,
- struct Contract *contract,
- struct GNUNET_TIME_Absolute timestamp,
- struct GNUNET_TIME_Absolute expiry,
- struct GNUNET_TIME_Absolute edate,
- struct GNUNET_TIME_Absolute refund,
- char **a,
- uint64_t nounce)
-{
- json_t *j_amount;
- json_int_t j_product_id;
- json_int_t j_trans_id;
- char *contract_str;
-
- struct TALER_Amount amount;
-
-
-
- /* Extracting values useful for DB work. Only gettable from the JSON
- since they are generated by the frontend */
- if (-1 == json_unpack (j_contract, "{s:o, s:I, s:{s:I}}",
- "amount", &j_amount,
- "trans_id", &j_trans_id,
- "details", "product_id",
- &j_product_id))
- {
- printf ("no unpacking\n");
- return GNUNET_SYSERR;
- }
-
- TALER_json_to_amount (j_amount, &amount);
- contract_str = json_dumps (j_contract, JSON_COMPACT | JSON_PRESERVE_ORDER);
- *a = contract_str;
- GNUNET_CRYPTO_hash (contract_str, strlen (contract_str) + 1,
- &contract->h_contract_details);
- contract->purpose.purpose = htonl (TALER_SIGNATURE_MERCHANT_CONTRACT);
- contract->purpose.size = htonl (sizeof (struct Contract));
-
- // DB mgmt
- return MERCHANT_DB_contract_create (db_conn,
- timestamp,
- expiry,
- edate,
- refund,
- &amount,
- &contract->h_contract_details,
- (uint64_t) j_trans_id, // safe?
- contract_str,
- nounce,
- (uint64_t) j_product_id);
-}
diff --git a/src/backend-lib/taler_merchant_contract_lib.h b/src/backend-lib/taler_merchant_contract_lib.h
index 1d2d0eba..3f95841f 100644
--- a/src/backend-lib/taler_merchant_contract_lib.h
+++ b/src/backend-lib/taler_merchant_contract_lib.h
@@ -1,22 +1,4 @@
/**
- * The contract sent by the merchant to the wallet
- */
-struct Contract
-{
- /**
- * Purpose header for the signature over contract
- */
- struct GNUNET_CRYPTO_EccSignaturePurpose purpose;
-
- /**
- * Hash of the JSON contract in UTF-8 including 0-termination,
- * using JSON_COMPACT encoding with sorted fields.
- */
- struct GNUNET_HashCode h_contract_details;
-
-};
-
-/**
* Take the global wire details and return a JSON containing them,
* compliantly with the Taler's API.
* @param wire the merchant's wire details
@@ -27,37 +9,3 @@ struct Contract
json_t *
MERCHANT_get_wire_json (const struct MERCHANT_WIREFORMAT_Sepa *wire,
uint64_t salt);
-
-/**
-* Take from the frontend the (partly) generated contract and fill
-* the missing values in it; for example, the SEPA details.
-* Moreover, it stores the contract in the DB.
-* @param j_contract parsed contract, originated by the frontend. It will be
-* hold the new values.
-* @param db_conn the handle to the local DB
-* @param contract where to store the (subset of the) contract to be (still) signed
-* @param timestamp contract's timestamp (shall be generated by the merchant)
-* @param expiry the time when the contract will expire
-* @param edate when the merchant wants to receive the wire transfer corresponding
-* to this deal (this value is also a field inside the 'wire' JSON format)
-* @param refund deadline until which the merchant can return the paid amount
-* @param nounce the nounce used to hash the wire details
-* @param a will be pointed to the (allocated) stringified 0-terminated contract
-* @return GNUNET_OK on success, GNUNET_NO if attempting to double insert the
-* same contract, GNUNET_SYSERR in case of other (mostly DB related) errors.
-*/
-
-/**
-* TODO: inspect reference counting and, accordingly, free those json_t*(s)
-* still allocated */
-
-uint32_t
-MERCHANT_handle_contract (json_t *j_contract,
- PGconn *db_conn,
- struct Contract *contract,
- struct GNUNET_TIME_Absolute timestamp,
- struct GNUNET_TIME_Absolute expiry,
- struct GNUNET_TIME_Absolute edate,
- struct GNUNET_TIME_Absolute refund,
- char **a,
- uint64_t nounce);
diff --git a/src/backend/taler-merchant-httpd.c b/src/backend/taler-merchant-httpd.c
index 8da6ce21..b7a914da 100644
--- a/src/backend/taler-merchant-httpd.c
+++ b/src/backend/taler-merchant-httpd.c
@@ -177,7 +177,7 @@ url_handler (void *cls,
"Hello, Customer.\n", 0,
&TMH_MHD_handler_static_response, MHD_HTTP_OK },
- { "/contract", MHD_HTTP_METHOD_GET, "application/json",
+ { "/contract", MHD_HTTP_METHOD_POST, "application/json",
NULL, 0,
&MH_handler_contract, MHD_HTTP_OK },
@@ -396,7 +396,6 @@ run (void *cls, char *const *args, const char *cfgfile,
{
unsigned int cnt;
-
mints = NULL;
keyfile = NULL;
result = GNUNET_SYSERR;
@@ -426,21 +425,22 @@ run (void *cls, char *const *args, const char *cfgfile,
EXITIF (GNUNET_SYSERR ==
GNUNET_CONFIGURATION_get_value_number (config,
"merchant",
- "port",
+ "PORT",
&port));
EXITIF (GNUNET_SYSERR ==
GNUNET_CONFIGURATION_get_value_string (config,
"merchant",
- "hostname",
+ "HOSTNAME",
&hostname));
EXITIF (GNUNET_SYSERR ==
GNUNET_CONFIGURATION_get_value_string (config,
"merchant",
- "currency",
+ "CURRENCY",
&TMH_mint_currency_string));
salt = GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_NONCE,
UINT64_MAX);
+
EXITIF (NULL == (mctx = TALER_MINT_init ()));
for (cnt = 0; cnt < nmints; cnt++)
{
diff --git a/src/backend/taler-merchant-httpd_contract.c b/src/backend/taler-merchant-httpd_contract.c
index 65ec323b..e7278c7c 100644
--- a/src/backend/taler-merchant-httpd_contract.c
+++ b/src/backend/taler-merchant-httpd_contract.c
@@ -43,14 +43,16 @@ extern PGconn *db_conn;
extern long long salt;
/**
- * Manage a contract request
- *
+ * Manage a contract request. In practical terms, it adds the fields 'mints',
+ * 'merchant_pub', and 'H_wire' to the contract 'proposition' gotten from the
+ * frontend. Finally, it adds (outside of the contract) a signature of the
+ * (hashed stringification) of this contract and the hashed stringification
+ * of this contract to the final bundle sent back to the frontend.
* @param rh context of the handler
* @param connection the MHD connection to handle
* @param[in,out] connection_cls the connection's closure (can be updated)
* @param upload_data upload data
* @param[in,out] upload_data_size number of bytes (left) in @a upload_data
- *
* @return MHD result code
*/
int
@@ -67,44 +69,24 @@ MH_handler_contract (struct TMH_RequestHandler *rh,
const struct TALER_MINT_Keys *keys;
int res;
int cnt;
- uint64_t trans_id;
- struct TALER_Amount amount;
- struct GNUNET_TIME_Absolute timestamp;
- struct GNUNET_TIME_Absolute refund;
- struct GNUNET_TIME_Absolute expiry;
- struct GNUNET_TIME_Absolute edate;
struct GNUNET_HashCode h_wire;
struct GNUNET_CRYPTO_EddsaPublicKey pubkey;
- struct TMH_PARSE_FieldSpecification spec[] =
- {
- TMH_PARSE_member_time_abs ("timestamp", &timestamp),
- TMH_PARSE_member_time_abs ("refund_deadline", &refund),
- TMH_PARSE_member_time_abs ("expiry", &expiry),
- TMH_PARSE_member_amount ("amount", &amount),
- TMH_PARSE_member_uint64 ("trans_id", &trans_id),
- TMH_PARSE_MEMBER_END
- };
-
+ struct MERCHANT_Contract contract;
+ char *contract_str;
+
res = TMH_PARSE_post_json (connection,
connection_cls,
upload_data,
upload_data_size,
&root);
-
if (GNUNET_SYSERR == res)
return MHD_NO;
/* the POST's body has to be further fetched */
if ((GNUNET_NO == res) || (NULL == root))
return MHD_YES;
- /* 1. Generate preferred mint(s) array.
+ /* Generate preferred mint(s) array. */
- The 'mint' JSON layout is as follows:
-
- { "url": "mint_base_url",
- "master_pub": "base32 mint's master public key" }
- */
-
trusted_mints = json_array ();
for (cnt = 0; cnt < nmints; cnt++)
{
@@ -121,31 +103,22 @@ MH_handler_contract (struct TMH_RequestHandler *rh,
}
}
- /* Return badly if no mints are trusted (or ready). WARNING: it
- may be possible that a mint trusted by the wallet is good, but
- still pending; that case must be handled with some "polling-style"
- routine, simply ignored, or ended with an invitation to the wallet
- to just retry later */
+ /**
+ * Return badly if no mints are trusted (or no call to /keys has still
+ * returned the expected data). WARNING: it
+ * may be possible that a mint trusted by the wallet is good, but
+ * still pending; that case must be handled with some "polling-style"
+ * routine, simply ignored, or ended with an invitation to the wallet
+ * to just retry later
+ */
if (!json_array_size (trusted_mints))
return MHD_NO;
json_object_set_new (root, "mints", trusted_mints);
- res = TMH_PARSE_json_data (connection, root, spec);
-
- if (GNUNET_SYSERR == res)
- return MHD_NO; /* hard failure */
- if (GNUNET_NO == res)
- return MHD_YES; /* failure */
-
-
- /* (indicative) deadline which the merchant wants its wire tranfer
- before */
- edate = GNUNET_TIME_absolute_add (timestamp, GNUNET_TIME_UNIT_WEEKS);
- TALER_round_abs_time (&edate);
if (NULL == (j_wire = MERCHANT_get_wire_json (wire,
salt)))
- return MHD_NO;
+ return MHD_NO;
/* hash wire objcet */
if (GNUNET_SYSERR ==
@@ -161,8 +134,8 @@ MH_handler_contract (struct TMH_RequestHandler *rh,
"merchant_pub",
TALER_json_from_data (&pubkey, sizeof (pubkey)));
- /* store relevant values for this contract, in DB */
- //res = MERCHANT_handle_contract ();
+ /* Sign */
+
return TMH_RESPONSE_reply_json (connection, root, MHD_HTTP_OK);
}
diff --git a/src/frontend/generate_taler_contract.php b/src/frontend/generate_taler_contract.php
index 1b9648bb..52e11940 100644
--- a/src/frontend/generate_taler_contract.php
+++ b/src/frontend/generate_taler_contract.php
@@ -23,10 +23,27 @@
2. generate the JSON to forward to the backend
3. forward the response with the contract from the backend to
to the wallet
-*/
-$cli_debug = true;
+
+ To test this feature from the command line, issue:
+
+ - $ curl http://merchant_url/generate_taler_contract.php?cli_debug=yes
+ if the whole "journey" to the backend is begin tested
+ - $ curl http://merchant_url/generate_taler_contract.php?backend_test=no
+ if just the frontend job is being tested
+*/
+
+$cli_debug = false;
$backend_test = true;
+if ($_GET['cli_debug'] == 'yes')
+ $cli_debug = true;
+
+if ($_GET['backend_test'] == 'no')
+{
+ $cli_debug = true;
+ $backend_test = false;
+}
+
// 1) recover the session information
session_start();
if (!$cli_debug && ((! isset($_SESSION['receiver'])) ||
@@ -84,7 +101,7 @@ $json = json_encode (array ('amount' => array ('value' => $value,
'max_fee' => array ('value' => 3,
'fraction' => 01010,
'currency' => $currency),
- 'trans_id' => $transaction_id,
+ 'transaction_id' => $transaction_id,
'products' => array (
array ('description' => $desc,
'quantity' => 1,
diff --git a/src/include/merchant.h b/src/include/merchant.h
index 1368c575..04dd253d 100644
--- a/src/include/merchant.h
+++ b/src/include/merchant.h
@@ -64,6 +64,26 @@ struct MERCHANT_Mint
};
/**
+ * The contract sent by the merchant to the wallet
+ */
+struct MERCHANT_Contract
+{
+ /**
+ * Purpose header for the signature over contract
+ */
+ struct GNUNET_CRYPTO_EccSignaturePurpose purpose;
+
+ /**
+ * Hash of the JSON contract in UTF-8 including 0-termination,
+ * using JSON_COMPACT encoding with sorted fields.
+ */
+ struct GNUNET_HashCode h_contract_details;
+
+};
+
+
+
+/**
* Parses mints from the configuration.
*
* @param cfg the configuration