adding support for transaction history to wire plugin API (#4959)
This commit is contained in:
parent
234dbcc7b7
commit
f4df63e448
@ -22,25 +22,22 @@ DB_CONN_STR = "postgres:///talercheck"
|
||||
# Change here to enable SEPA wire transfers.
|
||||
ENABLE = NO
|
||||
|
||||
[exchange-wire-incoming-sepa]
|
||||
# Response for /wire
|
||||
SEPA_RESPONSE_FILE = "sepa.json"
|
||||
|
||||
[exchange-wire-outgoing-sepa]
|
||||
SEPA_RESPONSE_FILE = "sepa.json"
|
||||
# TBD
|
||||
|
||||
[exchange-wire-sepa]
|
||||
|
||||
[exchange-wire-test]
|
||||
# Change here to disable TEST wire transfers.
|
||||
ENABLE = YES
|
||||
|
||||
[exchange-wire-incoming-test]
|
||||
# Response for /wire
|
||||
TEST_RESPONSE_FILE = "test.json"
|
||||
|
||||
# What is the main website of the bank?
|
||||
BANK_URI = "https://bank/"
|
||||
# Into which account at the 'bank' should incoming
|
||||
# wire transfers be made?
|
||||
BANK_ACCOUNT_NUMBER = 2
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# What is the main website of the bank?
|
||||
BANK_URI = "https://bank/"
|
||||
# From which account at the 'bank' should outgoing
|
||||
# wire transfers be made?
|
||||
BANK_ACCOUNT_NUMBER = 2
|
||||
|
@ -441,36 +441,24 @@ option @cite{currency} in section @cite{[taler]}.
|
||||
@section Bank account
|
||||
|
||||
@menu
|
||||
* Wireformat::
|
||||
* Incoming::
|
||||
* Outgoing::
|
||||
|
||||
* Wiremethod-test::
|
||||
* Wiremethod-sepa::
|
||||
@end menu
|
||||
|
||||
@node Wireformat
|
||||
@subsection Wireformat
|
||||
|
||||
|
||||
The wireformat is the protocol to be used between the exchange and the
|
||||
banks. The option is @cite{wireformat}, under section
|
||||
@cite{[exchange]}. The exchange currently supports the @cite{test}
|
||||
wireformat. This wireformat is used for testing the system against a
|
||||
fictional bank.
|
||||
|
||||
@cartouche
|
||||
@quotation Note
|
||||
The SEPA wireformat is work in progress.
|
||||
@end quotation
|
||||
@end cartouche
|
||||
|
||||
@node Incoming
|
||||
@subsection Incoming
|
||||
@node Wiremethod-test
|
||||
@subsection Wiremethod-test
|
||||
|
||||
To enable the wire transfer method ``test'', you need to set
|
||||
``ENABLE=YES'' in section @cite{[exchange-wire-test]}.
|
||||
|
||||
The bank account where the exchange gets money from customers is
|
||||
configured under the section @cite{[exchange-wire-incoming-X]}, where
|
||||
@cite{X} matches the value given to the option @cite{wireformat}. This
|
||||
section contains only one option: @cite{X_response_file}, which takes
|
||||
configured under the section @cite{[exchange-wire-test]}. It must
|
||||
contain the options ``EXCHANGE_ACCOUNT_NO'' and ``BANK_URI''.
|
||||
For basic authentication, it must additionally contain the
|
||||
``USERNAME'' and ``PASSWORD'' of the exchange's account at the bank.
|
||||
|
||||
For incoming transfers, the section must additional contain the
|
||||
option: @cite{test_response_file}, which takes
|
||||
the path to a text file containing the exchange's bank account details
|
||||
in JSON format.
|
||||
|
||||
@ -483,21 +471,47 @@ $ taler-exchange-wire -j '@{"name": "The Exchange", "account_number":
|
||||
test -o exchange.json
|
||||
@end example
|
||||
|
||||
Note that the value given to option @cite{-t} must match the value in
|
||||
the JSON's field @code{"type"}.
|
||||
|
||||
The generated file will be echoed by the exchange when serving
|
||||
/wire@footnote{https://api.taler.net/api-exchange.html#wire-req}
|
||||
requests.
|
||||
|
||||
|
||||
@node Wiremethod-sepa
|
||||
@subsection Wiremethod-sepa
|
||||
|
||||
To enable the wire transfer method ``sepa'', you need to set
|
||||
``ENABLE=YES'' in section @cite{[exchange-wire-sepa]}.
|
||||
|
||||
|
||||
The bank account where the exchange gets money from customers is
|
||||
configured under the section @cite{[exchange-wire-incoming-sepa]}. This
|
||||
section contains only one option: @cite{sepa_response_file}, which takes
|
||||
the path to a text file containing the exchange's bank account details
|
||||
in JSON format.
|
||||
|
||||
The command line tool @cite{taler-exchange-wire} is used to create such a file.
|
||||
For example, the utility may be invoked as follows:
|
||||
|
||||
@example
|
||||
$ taler-exchange-wire -j '@{"name": "The Exchange", "account_number":
|
||||
10, "bank_uri": "https://bank.demo.taler.net", "type": "sepa"@}' -t
|
||||
sepa -o exchange.json
|
||||
@end example
|
||||
|
||||
Note that the value given to option @cite{-t} must match the value in the JSON's field @code{"type"}.
|
||||
|
||||
The generated file will be echoed by the exchange when serving
|
||||
/wire@footnote{https://api.taler.net/api-exchange.html#wire-req}
|
||||
requests.
|
||||
|
||||
@node Outgoing
|
||||
@subsection Outgoing
|
||||
|
||||
This exchange's bank account is used to give money to merchants, after
|
||||
This exchange's outgoing bank account is used to give money to merchants, after
|
||||
successful
|
||||
deposits@footnote{https://api.taler.net/api-exchange.html#deposit-par}
|
||||
operations. If @cite{test} is the chosen wireformat, the outcoming
|
||||
bank account is configured by the following options under
|
||||
@cite{[exchange-wire-outcoming-test]}:
|
||||
operations. The outgoing bank account is configured by the following
|
||||
options under @cite{[exchange-wire-outgoing-sepa]}: (NOT YET SUPPORTED).
|
||||
|
||||
@quotation
|
||||
|
||||
|
@ -16,7 +16,8 @@ libtalerbank_la_LDFLAGS = \
|
||||
|
||||
libtalerbank_la_SOURCES = \
|
||||
bank_api_admin.c \
|
||||
bank_api_common.c bank_api_common.h
|
||||
bank_api_common.c bank_api_common.h \
|
||||
bank_api_history.c
|
||||
|
||||
libtalerbank_la_LIBADD = \
|
||||
$(top_builddir)/src/json/libtalerjson.la \
|
||||
|
@ -64,34 +64,6 @@ struct TALER_BANK_AdminAddIncomingHandle
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Obtain the URL to use for an API request.
|
||||
*
|
||||
* @param u base URL of the bank
|
||||
* @param path Taler API path (i.e. "/reserve/withdraw")
|
||||
* @return the full URI to use with cURL
|
||||
*/
|
||||
static char *
|
||||
path_to_url (const char *u,
|
||||
const char *path)
|
||||
{
|
||||
char *url;
|
||||
|
||||
if ( ('/' == path[0]) &&
|
||||
(0 < strlen (u)) &&
|
||||
('/' == u[strlen (u) - 1]) )
|
||||
path++; /* avoid generating URL with "//" from concat */
|
||||
GNUNET_asprintf (&url,
|
||||
"%s%s",
|
||||
u,
|
||||
path);
|
||||
return url;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Function called when we're done processing the
|
||||
* HTTP /admin/add/incoming request.
|
||||
@ -195,8 +167,8 @@ TALER_BANK_admin_add_incoming (struct GNUNET_CURL_Context *ctx,
|
||||
aai = GNUNET_new (struct TALER_BANK_AdminAddIncomingHandle);
|
||||
aai->cb = res_cb;
|
||||
aai->cb_cls = res_cb_cls;
|
||||
aai->request_url = path_to_url (bank_base_url,
|
||||
"/admin/add/incoming");
|
||||
aai->request_url = TALER_BANK_path_to_url_ (bank_base_url,
|
||||
"/admin/add/incoming");
|
||||
aai->authh = TALER_BANK_make_auth_header_ (auth);
|
||||
eh = curl_easy_init ();
|
||||
GNUNET_assert (NULL != (aai->json_enc =
|
||||
|
@ -85,4 +85,32 @@ TALER_BANK_make_auth_header_ (const struct TALER_BANK_AuthenticationData *auth)
|
||||
return authh;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Obtain the URL to use for an API request.
|
||||
*
|
||||
* @param u base URL of the bank
|
||||
* @param path Taler API path (i.e. "/history")
|
||||
* @return the full URI to use with cURL
|
||||
*/
|
||||
char *
|
||||
TALER_BANK_path_to_url_ (const char *u,
|
||||
const char *path)
|
||||
{
|
||||
char *url;
|
||||
|
||||
if ( ('/' == path[0]) &&
|
||||
(0 < strlen (u)) &&
|
||||
('/' == u[strlen (u) - 1]) )
|
||||
path++; /* avoid generating URL with "//" from concat */
|
||||
GNUNET_asprintf (&url,
|
||||
"%s%s",
|
||||
u,
|
||||
path);
|
||||
return url;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* end of bank_api_common.c */
|
||||
|
@ -39,4 +39,16 @@ struct curl_slist *
|
||||
TALER_BANK_make_auth_header_ (const struct TALER_BANK_AuthenticationData *auth);
|
||||
|
||||
|
||||
/**
|
||||
* Obtain the URL to use for an API request.
|
||||
*
|
||||
* @param u base URL of the bank
|
||||
* @param path Taler API path (i.e. "/history")
|
||||
* @return the full URI to use with cURL
|
||||
*/
|
||||
char *
|
||||
TALER_BANK_path_to_url_ (const char *u,
|
||||
const char *path);
|
||||
|
||||
|
||||
#endif
|
||||
|
328
src/bank-lib/bank_api_history.c
Normal file
328
src/bank-lib/bank_api_history.c
Normal file
@ -0,0 +1,328 @@
|
||||
/*
|
||||
This file is part of TALER
|
||||
Copyright (C) 2017 GNUnet e.V. & Inria
|
||||
|
||||
TALER is free software; you can redistribute it and/or modify it under the
|
||||
terms of the GNU General Public License as published by the Free Software
|
||||
Foundation; either version 3, or (at your option) any later version.
|
||||
|
||||
TALER is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
|
||||
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along with
|
||||
TALER; see the file COPYING. If not, see
|
||||
<http://www.gnu.org/licenses/>
|
||||
*/
|
||||
/**
|
||||
* @file bank-lib/bank_api_history.c
|
||||
* @brief Implementation of the /history requests of the bank's HTTP API
|
||||
* @author Christian Grothoff
|
||||
*/
|
||||
#include "platform.h"
|
||||
#include "bank_api_common.h"
|
||||
#include <microhttpd.h> /* just for HTTP status codes */
|
||||
#include "taler_signatures.h"
|
||||
|
||||
|
||||
/**
|
||||
* @brief A /history Handle
|
||||
*/
|
||||
struct TALER_BANK_HistoryHandle
|
||||
{
|
||||
|
||||
/**
|
||||
* The url for this request.
|
||||
*/
|
||||
char *request_url;
|
||||
|
||||
/**
|
||||
* The base URL of the bank.
|
||||
*/
|
||||
char *bank_base_url;
|
||||
|
||||
/**
|
||||
* Handle for the request.
|
||||
*/
|
||||
struct GNUNET_CURL_Job *job;
|
||||
|
||||
/**
|
||||
* HTTP authentication-related headers for the request.
|
||||
*/
|
||||
struct curl_slist *authh;
|
||||
|
||||
/**
|
||||
* Function to call with the result.
|
||||
*/
|
||||
TALER_BANK_HistoryResultCallback hcb;
|
||||
|
||||
/**
|
||||
* Closure for @a cb.
|
||||
*/
|
||||
void *hcb_cls;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Parse history given in JSON format and invoke the callback on each item.
|
||||
*
|
||||
* @param hh handle to the account history request
|
||||
* @param history JSON array with the history
|
||||
* @return #GNUNET_OK if history was valid and @a rhistory and @a balance
|
||||
* were set,
|
||||
* #GNUNET_SYSERR if there was a protocol violation in @a history
|
||||
*/
|
||||
static int
|
||||
parse_account_history (struct TALER_BANK_HistoryHandle *hh,
|
||||
const json_t *history)
|
||||
{
|
||||
for (unsigned int i=0;i<json_array_size (history);i++)
|
||||
{
|
||||
struct TALER_BANK_TransferDetails td;
|
||||
const char *sign;
|
||||
uint64_t other_account;
|
||||
uint64_t serial_id;
|
||||
enum TALER_BANK_Direction direction;
|
||||
struct GNUNET_JSON_Specification hist_spec[] = {
|
||||
GNUNET_JSON_spec_string ("sign",
|
||||
&sign),
|
||||
TALER_JSON_spec_amount ("amount",
|
||||
&td.amount),
|
||||
GNUNET_JSON_spec_absolute_time ("date",
|
||||
&td.execution_date),
|
||||
GNUNET_JSON_spec_uint64 ("row_id",
|
||||
&serial_id),
|
||||
GNUNET_JSON_spec_string ("wire_subject",
|
||||
&td.wire_transfer_subject),
|
||||
GNUNET_JSON_spec_uint64 ("other_account",
|
||||
&other_account),
|
||||
GNUNET_JSON_spec_end()
|
||||
};
|
||||
json_t *transaction = json_array_get (history,
|
||||
i);
|
||||
|
||||
if (GNUNET_OK !=
|
||||
GNUNET_JSON_parse (transaction,
|
||||
hist_spec,
|
||||
NULL, NULL))
|
||||
{
|
||||
GNUNET_break_op (0);
|
||||
return GNUNET_SYSERR;
|
||||
}
|
||||
td.account_details = json_pack ("{s:s, s:s, s:I}",
|
||||
"type", "test",
|
||||
"bank_uri", hh->bank_base_url,
|
||||
"account_number", (json_int_t) other_account);
|
||||
direction = (0 == strcasecmp (sign,
|
||||
"+"))
|
||||
? TALER_BANK_DIRECTION_CREDIT
|
||||
: TALER_BANK_DIRECTION_DEBIT;
|
||||
hh->hcb (hh->hcb_cls,
|
||||
MHD_HTTP_OK,
|
||||
direction,
|
||||
serial_id,
|
||||
&td,
|
||||
transaction);
|
||||
GNUNET_JSON_parse_free (hist_spec);
|
||||
json_decref (td.account_details);
|
||||
}
|
||||
return GNUNET_OK;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Function called when we're done processing the
|
||||
* HTTP /admin/add/incoming request.
|
||||
*
|
||||
* @param cls the `struct TALER_BANK_HistoryHandle`
|
||||
* @param response_code HTTP response code, 0 on error
|
||||
* @param json parsed JSON result, NULL on error
|
||||
*/
|
||||
static void
|
||||
handle_history_finished (void *cls,
|
||||
long response_code,
|
||||
const json_t *json)
|
||||
{
|
||||
struct TALER_BANK_HistoryHandle *hh = cls;
|
||||
|
||||
hh->job = NULL;
|
||||
switch (response_code)
|
||||
{
|
||||
case 0:
|
||||
break;
|
||||
case MHD_HTTP_OK:
|
||||
if (GNUNET_OK !=
|
||||
parse_account_history (hh,
|
||||
json))
|
||||
{
|
||||
GNUNET_break_op (0);
|
||||
response_code = 0;
|
||||
break;
|
||||
}
|
||||
response_code = MHD_HTTP_NO_CONTENT; /* signal end of list */
|
||||
break;
|
||||
case MHD_HTTP_NO_CONTENT:
|
||||
break;
|
||||
case MHD_HTTP_BAD_REQUEST:
|
||||
/* This should never happen, either us or the bank is buggy
|
||||
(or API version conflict); just pass JSON reply to the application */
|
||||
break;
|
||||
case MHD_HTTP_FORBIDDEN:
|
||||
/* Access denied */
|
||||
break;
|
||||
case MHD_HTTP_UNAUTHORIZED:
|
||||
/* Nothing really to verify, bank says one of the signatures is
|
||||
invalid; as we checked them, this should never happen, we
|
||||
should pass the JSON reply to the application */
|
||||
break;
|
||||
case MHD_HTTP_NOT_FOUND:
|
||||
/* Nothing really to verify, this should never
|
||||
happen, we should pass the JSON reply to the application */
|
||||
break;
|
||||
case MHD_HTTP_INTERNAL_SERVER_ERROR:
|
||||
/* Server had an internal issue; we should retry, but this API
|
||||
leaves this to the application */
|
||||
break;
|
||||
default:
|
||||
/* unexpected response code */
|
||||
GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
|
||||
"Unexpected response code %u\n",
|
||||
(unsigned int) response_code);
|
||||
GNUNET_break (0);
|
||||
response_code = 0;
|
||||
break;
|
||||
}
|
||||
hh->hcb (hh->hcb_cls,
|
||||
response_code,
|
||||
TALER_BANK_DIRECTION_NONE,
|
||||
0LLU,
|
||||
NULL,
|
||||
json);
|
||||
TALER_BANK_history_cancel (hh);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Request the wire transfer history of a bank account.
|
||||
*
|
||||
* @param ctx curl context for the event loop
|
||||
* @param bank_base_url URL of the bank (used to execute this request)
|
||||
* @param auth authentication data to use
|
||||
* @param account_number which account number should we query
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_row from which row on do we want to get results, use UINT64_MAX for the latest; exclusive
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
* @param hres_cb the callback to call with the transaction history
|
||||
* @param hres_cb_cls closure for the above callback
|
||||
* @return NULL
|
||||
* if the inputs are invalid (i.e. zero value for @e num_results).
|
||||
* In this case, the callback is not called.
|
||||
*/
|
||||
struct TALER_BANK_HistoryHandle *
|
||||
TALER_BANK_history (struct GNUNET_CURL_Context *ctx,
|
||||
const char *bank_base_url,
|
||||
const struct TALER_BANK_AuthenticationData *auth,
|
||||
uint64_t account_number,
|
||||
enum TALER_BANK_Direction direction,
|
||||
uint64_t start_row,
|
||||
int64_t num_results,
|
||||
TALER_BANK_HistoryResultCallback hres_cb,
|
||||
void *hres_cb_cls)
|
||||
{
|
||||
struct TALER_BANK_HistoryHandle *hh;
|
||||
CURL *eh;
|
||||
char *url;
|
||||
|
||||
if (0 == num_results)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
if (TALER_BANK_DIRECTION_NONE == direction)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
if (UINT64_MAX == start_row)
|
||||
{
|
||||
if (TALER_BANK_DIRECTION_BOTH == direction)
|
||||
GNUNET_asprintf (&url,
|
||||
"/history?account_number=%llu&num_results=%lld",
|
||||
(unsigned long long) account_number,
|
||||
(long long) num_results);
|
||||
else
|
||||
GNUNET_asprintf (&url,
|
||||
"/history?account_number=%llu&num_results=%lld&direction=%s",
|
||||
(unsigned long long) account_number,
|
||||
(long long) num_results,
|
||||
(TALER_BANK_DIRECTION_CREDIT == direction) ? "credit" : "debit");
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if (TALER_BANK_DIRECTION_BOTH == direction)
|
||||
GNUNET_asprintf (&url,
|
||||
"/history?account_number=%llu&num_results=%lld&start_row=%llu",
|
||||
(unsigned long long) account_number,
|
||||
(long long) num_results,
|
||||
(unsigned long long) start_row);
|
||||
else
|
||||
GNUNET_asprintf (&url,
|
||||
"/history?account_number=%llu&num_results=%lld&start_row=%llu&direction=%s",
|
||||
(unsigned long long) account_number,
|
||||
(long long) num_results,
|
||||
(unsigned long long) start_row,
|
||||
(TALER_BANK_DIRECTION_CREDIT == direction) ? "credit" : "debit");
|
||||
}
|
||||
|
||||
hh = GNUNET_new (struct TALER_BANK_HistoryHandle);
|
||||
hh->hcb = hres_cb;
|
||||
hh->hcb_cls = hres_cb_cls;
|
||||
hh->bank_base_url = GNUNET_strdup (bank_base_url);
|
||||
hh->request_url = TALER_BANK_path_to_url_ (bank_base_url,
|
||||
url);
|
||||
GNUNET_free (url);
|
||||
hh->authh = TALER_BANK_make_auth_header_ (auth);
|
||||
eh = curl_easy_init ();
|
||||
GNUNET_assert (CURLE_OK ==
|
||||
curl_easy_setopt (eh,
|
||||
CURLOPT_HTTPHEADER,
|
||||
hh->authh));
|
||||
GNUNET_assert (CURLE_OK ==
|
||||
curl_easy_setopt (eh,
|
||||
CURLOPT_URL,
|
||||
hh->request_url));
|
||||
hh->job = GNUNET_CURL_job_add (ctx,
|
||||
eh,
|
||||
GNUNET_NO,
|
||||
&handle_history_finished,
|
||||
hh);
|
||||
return hh;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Cancel a history request. This function cannot be used on a request
|
||||
* handle if a response is already served for it.
|
||||
*
|
||||
* @param hh the history request handle
|
||||
*/
|
||||
void
|
||||
TALER_BANK_history_cancel (struct TALER_BANK_HistoryHandle *hh)
|
||||
{
|
||||
if (NULL != hh->job)
|
||||
{
|
||||
GNUNET_CURL_job_cancel (hh->job);
|
||||
hh->job = NULL;
|
||||
}
|
||||
curl_slist_free_all (hh->authh);
|
||||
GNUNET_free (hh->request_url);
|
||||
GNUNET_free (hh->bank_base_url);
|
||||
GNUNET_free (hh);
|
||||
}
|
||||
|
||||
|
||||
/* end of bank_api_history.c */
|
@ -26,14 +26,12 @@ DB_CONN_STR = "postgres:///talercheck"
|
||||
# Enable 'test' for testing of the actual coin operations.
|
||||
ENABLE = YES
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# What is the main website of the bank?
|
||||
# (Not used unless the aggregator is run.)
|
||||
BANK_URI = "http://localhost:8082/"
|
||||
# From which account at the 'bank' should outgoing wire transfers be made?
|
||||
BANK_ACCOUNT_NUMBER = 2
|
||||
|
||||
[exchange-wire-incoming-test]
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
TEST_RESPONSE_FILE = ${TALER_CONFIG_HOME}/test.json
|
||||
|
@ -30,6 +30,10 @@ DB_CONN_STR = "postgres:///talercheck"
|
||||
# Enable 'sepa' to test SEPA-specific routines.
|
||||
ENABLE = YES
|
||||
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
SEPA_RESPONSE_FILE = ${TALER_CONFIG_HOME}/sepa.json
|
||||
|
||||
# Fees for the forseeable future...
|
||||
# If you see this after 2017, update to match the next 10 years...
|
||||
WIRE-FEE-2017 = EUR:0.01
|
||||
@ -54,11 +58,6 @@ CLOSING-FEE-2024 = EUR:0.01
|
||||
CLOSING-FEE-2025 = EUR:0.01
|
||||
CLOSING-FEE-2026 = EUR:0.01
|
||||
|
||||
[exchange-wire-incoming-sepa]
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
SEPA_RESPONSE_FILE = ${TALER_CONFIG_HOME}/sepa.json
|
||||
|
||||
[exchange-wire-test]
|
||||
# Enable 'test' for testing of the actual coin operations.
|
||||
ENABLE = YES
|
||||
@ -87,17 +86,16 @@ CLOSING-FEE-2024 = EUR:0.01
|
||||
CLOSING-FEE-2025 = EUR:0.01
|
||||
CLOSING-FEE-2026 = EUR:0.01
|
||||
|
||||
[exchange-wire-incoming-test]
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
TEST_RESPONSE_FILE = ${TALER_CONFIG_HOME}/test.json
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# What is the main website of the bank?
|
||||
BANK_URI = "http://localhost:8082/"
|
||||
# From which account at the 'bank' should outgoing wire transfers be made?
|
||||
BANK_ACCOUNT_NUMBER = 2
|
||||
|
||||
|
||||
[coin_eur_ct_1]
|
||||
value = EUR:0.01
|
||||
duration_overlap = 5 minutes
|
||||
|
@ -187,21 +187,21 @@ then
|
||||
# If possible, initialize outgoing wire account details ('test' method only)
|
||||
if (test "test" = "$WMETHOD" -a ! -z "$ARG_BANK_URI")
|
||||
then
|
||||
$CS -s exchange-wire-outgoing-test -o BANK_URI -V "$ARG_BANK_URI" || exit 1
|
||||
$CS -s exchange-wire-test -o BANK_URI -V "$ARG_BANK_URI" || exit 1
|
||||
else
|
||||
echo "Skipped generating outgoing wire account details for exchange"
|
||||
echo "Skipped generating wire account details for exchange"
|
||||
fi
|
||||
if (test "test" = "$ARG_W" -a ! -z "$ARG_EXCHANGE_BANK_ACCOUNT")
|
||||
then
|
||||
$CS -s exchange-wire-outgoing-test -o BANK_ACCOUNT_NUMBER -V "$ARG_EXCHANGE_BANK_ACCOUNT" || exit 1
|
||||
$CS -s exchange-wire-test -o BANK_ACCOUNT_NUMBER -V "$ARG_EXCHANGE_BANK_ACCOUNT" || exit 1
|
||||
else
|
||||
echo "Skipped generating outgoing wire account details for exchange"
|
||||
echo "Skipped generating wire account details for exchange"
|
||||
fi
|
||||
|
||||
# If possible, initialize /wire response from JSON (with signature)
|
||||
if (test ! -z $ARG_JE)
|
||||
then
|
||||
JSONF=`$CS -s exchange-wire-incoming-${ARG_W} -o ${ARG_W}_RESPONSE_FILE -f`
|
||||
JSONF=`$CS -s exchange-wire-${ARG_W} -o ${ARG_W}_RESPONSE_FILE -f`
|
||||
# echo "Generating /wire response at $JSONF"
|
||||
mkdir -p `dirname $JSONF`
|
||||
taler-exchange-wire -c "$ARG_CONFIG" -t "$ARG_W" -j "$ARG_JE" -m "$MASTER_KEY" -o "$JSONF" || exit 1
|
||||
|
@ -207,12 +207,10 @@ TEH_json_validate_wireformat (const json_t *wire,
|
||||
* Obtain JSON of the supported wire methods for a given
|
||||
* account name prefix.
|
||||
*
|
||||
* @param prefix prefix for the account, the suffix will
|
||||
* be determined by the name of the plugin
|
||||
* @return JSON array with the supported validation methods
|
||||
*/
|
||||
json_t *
|
||||
TEH_VALIDATION_get_wire_methods (const char *prefix)
|
||||
TEH_VALIDATION_get_wire_methods ()
|
||||
{
|
||||
json_t *methods;
|
||||
char *account_name;
|
||||
@ -227,8 +225,7 @@ TEH_VALIDATION_get_wire_methods (const char *prefix)
|
||||
json_t *fees;
|
||||
|
||||
GNUNET_asprintf (&account_name,
|
||||
"%s-%s",
|
||||
prefix,
|
||||
"exchange-wire-%s",
|
||||
p->type);
|
||||
method = plugin->get_wire_details (plugin->cls,
|
||||
cfg,
|
||||
|
@ -61,12 +61,10 @@ TEH_json_validate_wireformat (const json_t *wire,
|
||||
* Obtain JSON of the supported wire methods for a given
|
||||
* account name prefix.
|
||||
*
|
||||
* @param prefix prefix for the account, the suffix will
|
||||
* be determined by the name of the plugin
|
||||
* @return JSON array with the supported validation methods
|
||||
*/
|
||||
json_t *
|
||||
TEH_VALIDATION_get_wire_methods (const char *prefix);
|
||||
TEH_VALIDATION_get_wire_methods (void);
|
||||
|
||||
|
||||
#endif
|
||||
|
@ -143,7 +143,7 @@ TEH_WIRE_handler_wire (struct TEH_RequestHandler *rh,
|
||||
int
|
||||
TEH_WIRE_init ()
|
||||
{
|
||||
wire_methods = TEH_VALIDATION_get_wire_methods ("exchange-wire-incoming");
|
||||
wire_methods = TEH_VALIDATION_get_wire_methods ();
|
||||
if ( (NULL == wire_methods) ||
|
||||
(0 == json_object_size (wire_methods)) )
|
||||
{
|
||||
|
@ -63,7 +63,6 @@ CLOSING-FEE-2025 = EUR:0.01
|
||||
CLOSING-FEE-2026 = EUR:0.01
|
||||
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# What is the main website of the bank?
|
||||
BANK_URI = "http://localhost:8082/"
|
||||
|
||||
|
@ -36,7 +36,6 @@ DB_CONN_STR = "postgres:///talercheck"
|
||||
# Enable 'test' for testing of the actual coin operations.
|
||||
ENABLE = YES
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# What is the main website of the bank?
|
||||
BANK_URI = "http://localhost:8082/"
|
||||
|
||||
|
@ -150,10 +150,15 @@ TALER_BANK_admin_add_incoming_cancel (struct TALER_BANK_AdminAddIncomingHandle *
|
||||
|
||||
|
||||
/**
|
||||
* Which types of transactions should be returned?
|
||||
* Which types of transactions should be (or is being) returned?
|
||||
*/
|
||||
enum TALER_BANK_Direction {
|
||||
|
||||
/**
|
||||
* Base case, used to indicate errors or end of list.
|
||||
*/
|
||||
TALER_BANK_DIRECTION_NONE = 0,
|
||||
|
||||
/**
|
||||
* Transactions where the bank account receives money.
|
||||
*/
|
||||
@ -192,15 +197,10 @@ struct TALER_BANK_TransferDetails
|
||||
*/
|
||||
struct GNUNET_TIME_Absolute execution_date;
|
||||
|
||||
/**
|
||||
* monotonically increasing counter corresponding to the transaction
|
||||
*/
|
||||
uint64_t serial_id;
|
||||
|
||||
/**
|
||||
* wire transfer subject
|
||||
*/
|
||||
char *wire_transfer_subject;
|
||||
const char *wire_transfer_subject;
|
||||
|
||||
/**
|
||||
* what was the other account that was involved
|
||||
@ -220,6 +220,7 @@ struct TALER_BANK_TransferDetails
|
||||
* last callback is always of this status (even if `abs(num_results)` were
|
||||
* already returned).
|
||||
* @param dir direction of the transfer
|
||||
* @param serial_id monotonically increasing counter corresponding to the transaction
|
||||
* @param details details about the wire transfer
|
||||
* @param json detailed response from the HTTPD, or NULL if reply was not in JSON
|
||||
*/
|
||||
@ -227,22 +228,20 @@ typedef void
|
||||
(*TALER_BANK_HistoryResultCallback) (void *cls,
|
||||
unsigned int http_status,
|
||||
enum TALER_BANK_Direction dir,
|
||||
uint64_t serial_id,
|
||||
const struct TALER_BANK_TransferDetails *details,
|
||||
const json_t *json);
|
||||
|
||||
|
||||
/**
|
||||
* Notify the bank that we have received an incoming transaction
|
||||
* which fills a reserve. Note that this API is an administrative
|
||||
* API and thus not accessible to typical bank clients, but only
|
||||
* to the operators of the bank.
|
||||
* Request the wire transfer history of a bank account.
|
||||
*
|
||||
* @param ctx curl context for the event loop
|
||||
* @param bank_base_url URL of the bank (used to execute this request)
|
||||
* @param auth authentication data to use
|
||||
* @param account_number which account number should we query
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_row from which row on do we want to get results, use UINT64_MAX for the latest
|
||||
* @param start_row from which row on do we want to get results, use UINT64_MAX for the latest; exclusive
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
This file is part of TALER
|
||||
Copyright (C) 2016 GNUnet e.V.
|
||||
Copyright (C) 2016, 2017 GNUnet e.V. & Inria
|
||||
|
||||
TALER is free software; you can redistribute it and/or modify it under the
|
||||
terms of the GNU General Public License as published by the Free Software
|
||||
@ -25,6 +25,7 @@
|
||||
#include <jansson.h>
|
||||
#include "taler_util.h"
|
||||
#include "taler_error_codes.h"
|
||||
#include "taler_bank_service.h" /* for `enum TALER_BANK_Direction` and `struct TALER_BANK_TransferDetails` */
|
||||
|
||||
|
||||
/**
|
||||
@ -40,17 +41,47 @@ typedef void
|
||||
size_t buf_size);
|
||||
|
||||
|
||||
/**
|
||||
* Callbacks of this type are used to serve the result of asking
|
||||
* the bank for the transaction history.
|
||||
*
|
||||
* @param cls closure
|
||||
* @param http_status HTTP response code, #MHD_HTTP_OK (200) for successful status request
|
||||
* 0 if the bank's reply is bogus (fails to follow the protocol),
|
||||
* #MHD_HTTP_NO_CONTENT if there are no more results; on success the
|
||||
* last callback is always of this status (even if `abs(num_results)` were
|
||||
* already returned).
|
||||
* @param dir direction of the transfer
|
||||
* @param row_off identification of the position at which we are querying
|
||||
* @param row_off_size number of bytes in @a row_off
|
||||
* @param details details about the wire transfer
|
||||
* @param json detailed response from the HTTPD, or NULL if reply was not in JSON
|
||||
*/
|
||||
typedef void
|
||||
(*TALER_WIRE_HistoryResultCallback) (void *cls,
|
||||
unsigned int http_status,
|
||||
enum TALER_BANK_Direction dir,
|
||||
const void *row_off,
|
||||
size_t row_off_size,
|
||||
const struct TALER_BANK_TransferDetails *details,
|
||||
const json_t *json);
|
||||
|
||||
|
||||
/**
|
||||
* Handle returned for cancelling a preparation step.
|
||||
*/
|
||||
struct TALER_WIRE_PrepareHandle;
|
||||
|
||||
|
||||
/**
|
||||
* Handle returned for cancelling an execution step.
|
||||
*/
|
||||
struct TALER_WIRE_ExecuteHandle;
|
||||
|
||||
/**
|
||||
* Handle returned for querying the transaction history.
|
||||
*/
|
||||
struct TALER_WIRE_HistoryHandle;
|
||||
|
||||
|
||||
/**
|
||||
* Function called with the result from the execute step.
|
||||
@ -217,6 +248,43 @@ struct TALER_WIRE_Plugin
|
||||
struct TALER_WIRE_ExecuteHandle *eh);
|
||||
|
||||
|
||||
/**
|
||||
* Query transfer history of an account. We use the variable-size
|
||||
* @a start_off to indicate which transfers we are interested in as
|
||||
* different banking systems may have different ways to identify
|
||||
* transfers. The @a start_off value must thus match the value of
|
||||
* a `row_off` argument previously given to the @a hres_cb. Use
|
||||
* NULL to query transfers from the beginning of time (with
|
||||
* positive @a num_results) or from the latest committed transfers
|
||||
* (with negative @a num_results).
|
||||
*
|
||||
* @param cls the @e cls of this struct with the plugin-specific state
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_off from which row on do we want to get results, use NULL for the latest; exclusive
|
||||
* @param start_off_len number of bytes in @a start_off
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
* @param hres_cb the callback to call with the transaction history
|
||||
* @param hres_cb_cls closure for the above callback
|
||||
*/
|
||||
struct TALER_WIRE_HistoryHandle *
|
||||
(*get_history) (void *cls,
|
||||
enum TALER_BANK_Direction direction,
|
||||
const void *start_off,
|
||||
size_t start_off_len,
|
||||
int64_t num_results,
|
||||
TALER_WIRE_HistoryResultCallback hres_cb,
|
||||
void *hres_cb_cls);
|
||||
|
||||
/**
|
||||
* Cancel going over the account's history.
|
||||
*
|
||||
* @param whh operation to cancel
|
||||
*/
|
||||
void
|
||||
(*get_history_cancel) (struct TALER_WIRE_HistoryHandle *whh);
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
@ -735,6 +735,52 @@ sepa_execute_wire_transfer_cancel (void *cls,
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Query transfer history of an account. We use the variable-size
|
||||
* @a start_off to indicate which transfers we are interested in as
|
||||
* different banking systems may have different ways to identify
|
||||
* transfers. The @a start_off value must thus match the value of
|
||||
* a `row_off` argument previously given to the @a hres_cb. Use
|
||||
* NULL to query transfers from the beginning of time (with
|
||||
* positive @a num_results) or from the latest committed transfers
|
||||
* (with negative @a num_results).
|
||||
*
|
||||
* @param cls the @e cls of this struct with the plugin-specific state
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_off from which row on do we want to get results, use NULL for the latest; exclusive
|
||||
* @param start_off_len number of bytes in @a start_off; must be `sizeof(uint64_t)`.
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
* @param hres_cb the callback to call with the transaction history
|
||||
* @param hres_cb_cls closure for the above callback
|
||||
*/
|
||||
static struct TALER_WIRE_HistoryHandle *
|
||||
sepa_get_history (void *cls,
|
||||
enum TALER_BANK_Direction direction,
|
||||
const void *start_off,
|
||||
size_t start_off_len,
|
||||
int64_t num_results,
|
||||
TALER_WIRE_HistoryResultCallback hres_cb,
|
||||
void *hres_cb_cls)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Cancel going over the account's history.
|
||||
*
|
||||
* @param whh operation to cancel
|
||||
*/
|
||||
static void
|
||||
sepa_get_history_cancel (struct TALER_WIRE_HistoryHandle *whh)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Initialize sepa-wire subsystem.
|
||||
*
|
||||
@ -774,6 +820,8 @@ libtaler_plugin_wire_sepa_init (void *cls)
|
||||
plugin->prepare_wire_transfer_cancel = &sepa_prepare_wire_transfer_cancel;
|
||||
plugin->execute_wire_transfer = &sepa_execute_wire_transfer;
|
||||
plugin->execute_wire_transfer_cancel = &sepa_execute_wire_transfer_cancel;
|
||||
plugin->get_history = &sepa_get_history;
|
||||
plugin->get_history_cancel = &sepa_get_history_cancel;
|
||||
return plugin;
|
||||
}
|
||||
|
||||
|
@ -219,6 +219,52 @@ template_execute_wire_transfer_cancel (void *cls,
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Query transfer history of an account. We use the variable-size
|
||||
* @a start_off to indicate which transfers we are interested in as
|
||||
* different banking systems may have different ways to identify
|
||||
* transfers. The @a start_off value must thus match the value of
|
||||
* a `row_off` argument previously given to the @a hres_cb. Use
|
||||
* NULL to query transfers from the beginning of time (with
|
||||
* positive @a num_results) or from the latest committed transfers
|
||||
* (with negative @a num_results).
|
||||
*
|
||||
* @param cls the @e cls of this struct with the plugin-specific state
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_off from which row on do we want to get results, use NULL for the latest; exclusive
|
||||
* @param start_off_len number of bytes in @a start_off; must be `sizeof(uint64_t)`.
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
* @param hres_cb the callback to call with the transaction history
|
||||
* @param hres_cb_cls closure for the above callback
|
||||
*/
|
||||
static struct TALER_WIRE_HistoryHandle *
|
||||
template_get_history (void *cls,
|
||||
enum TALER_BANK_Direction direction,
|
||||
const void *start_off,
|
||||
size_t start_off_len,
|
||||
int64_t num_results,
|
||||
TALER_WIRE_HistoryResultCallback hres_cb,
|
||||
void *hres_cb_cls)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Cancel going over the account's history.
|
||||
*
|
||||
* @param whh operation to cancel
|
||||
*/
|
||||
static void
|
||||
template_get_history_cancel (struct TALER_WIRE_HistoryHandle *whh)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Initialize template-wire subsystem.
|
||||
*
|
||||
@ -270,6 +316,8 @@ libtaler_plugin_wire_template_init (void *cls)
|
||||
plugin->prepare_wire_transfer_cancel = &template_prepare_wire_transfer_cancel;
|
||||
plugin->execute_wire_transfer = &template_execute_wire_transfer;
|
||||
plugin->execute_wire_transfer_cancel = &template_execute_wire_transfer_cancel;
|
||||
plugin->get_history = &template_get_history;
|
||||
plugin->get_history_cancel = &template_get_history_cancel;
|
||||
return plugin;
|
||||
}
|
||||
|
||||
|
@ -62,9 +62,9 @@ struct TestClosure
|
||||
|
||||
/**
|
||||
* Number of the account that the exchange has at the bank for
|
||||
* outgoing transfers.
|
||||
* transfers.
|
||||
*/
|
||||
unsigned long long exchange_account_outgoing_no;
|
||||
unsigned long long exchange_account_no;
|
||||
|
||||
};
|
||||
|
||||
@ -731,7 +731,7 @@ test_execute_wire_transfer (void *cls,
|
||||
exchange_base_url,
|
||||
&bf.wtid,
|
||||
&amount,
|
||||
(uint64_t) tc->exchange_account_outgoing_no,
|
||||
(uint64_t) tc->exchange_account_no,
|
||||
(uint64_t) account_no,
|
||||
&execute_cb,
|
||||
eh);
|
||||
@ -767,6 +767,166 @@ test_execute_wire_transfer_cancel (void *cls,
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Handle for a #test_get_history() request.
|
||||
*/
|
||||
struct TALER_WIRE_HistoryHandle
|
||||
{
|
||||
|
||||
/**
|
||||
* Function to call with results.
|
||||
*/
|
||||
TALER_WIRE_HistoryResultCallback hres_cb;
|
||||
|
||||
/**
|
||||
* Closure for @e hres_cb.
|
||||
*/
|
||||
void *hres_cb_cls;
|
||||
|
||||
/**
|
||||
* Request to the bank.
|
||||
*/
|
||||
struct TALER_BANK_HistoryHandle *hh;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Function called with results from the bank about the transaction history.
|
||||
*
|
||||
* @param cls the `struct TALER_WIRE_HistoryHandle`
|
||||
* @param http_status HTTP response code, #MHD_HTTP_OK (200) for successful status request
|
||||
* 0 if the bank's reply is bogus (fails to follow the protocol),
|
||||
* #MHD_HTTP_NO_CONTENT if there are no more results; on success the
|
||||
* last callback is always of this status (even if `abs(num_results)` were
|
||||
* already returned).
|
||||
* @param dir direction of the transfer
|
||||
* @param serial_id monotonically increasing counter corresponding to the transaction
|
||||
* @param details details about the wire transfer
|
||||
* @param json detailed response from the HTTPD, or NULL if reply was not in JSON
|
||||
*/
|
||||
static void
|
||||
bhist_cb (void *cls,
|
||||
unsigned int http_status,
|
||||
enum TALER_BANK_Direction dir,
|
||||
uint64_t serial_id,
|
||||
const struct TALER_BANK_TransferDetails *details,
|
||||
const json_t *json)
|
||||
{
|
||||
struct TALER_WIRE_HistoryHandle *whh = cls;
|
||||
uint64_t bserial_id = GNUNET_htonll (serial_id);
|
||||
|
||||
whh->hres_cb (whh->hres_cb_cls,
|
||||
http_status,
|
||||
dir,
|
||||
&bserial_id,
|
||||
sizeof (bserial_id),
|
||||
details,
|
||||
json);
|
||||
if (MHD_HTTP_OK != http_status)
|
||||
{
|
||||
whh->hh = NULL;
|
||||
GNUNET_free (whh);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Query transfer history of an account. We use the variable-size
|
||||
* @a start_off to indicate which transfers we are interested in as
|
||||
* different banking systems may have different ways to identify
|
||||
* transfers. The @a start_off value must thus match the value of
|
||||
* a `row_off` argument previously given to the @a hres_cb. Use
|
||||
* NULL to query transfers from the beginning of time (with
|
||||
* positive @a num_results) or from the latest committed transfers
|
||||
* (with negative @a num_results).
|
||||
*
|
||||
* @param cls the @e cls of this struct with the plugin-specific state
|
||||
* @param direction what kinds of wire transfers should be returned
|
||||
* @param start_off from which row on do we want to get results, use NULL for the latest; exclusive
|
||||
* @param start_off_len number of bytes in @a start_off; must be `sizeof(uint64_t)`.
|
||||
* @param num_results how many results do we want; negative numbers to go into the past,
|
||||
* positive numbers to go into the future starting at @a start_row;
|
||||
* must not be zero.
|
||||
* @param hres_cb the callback to call with the transaction history
|
||||
* @param hres_cb_cls closure for the above callback
|
||||
*/
|
||||
static struct TALER_WIRE_HistoryHandle *
|
||||
test_get_history (void *cls,
|
||||
enum TALER_BANK_Direction direction,
|
||||
const void *start_off,
|
||||
size_t start_off_len,
|
||||
int64_t num_results,
|
||||
TALER_WIRE_HistoryResultCallback hres_cb,
|
||||
void *hres_cb_cls)
|
||||
{
|
||||
struct TestClosure *tc = cls;
|
||||
struct TALER_WIRE_HistoryHandle *whh;
|
||||
const uint64_t *start_off_b64;
|
||||
uint64_t start_row;
|
||||
|
||||
if (0 == num_results)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
if (TALER_BANK_DIRECTION_NONE == direction)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
if ( (NULL != start_off) &&
|
||||
(sizeof (uint64_t) != start_off_len) )
|
||||
{
|
||||
GNUNET_break (0);
|
||||
return NULL;
|
||||
}
|
||||
if (NULL == start_off)
|
||||
{
|
||||
start_row = (num_results > 0) ? 0 : UINT64_MAX;
|
||||
}
|
||||
else
|
||||
{
|
||||
start_off_b64 = start_off;
|
||||
start_row = GNUNET_ntohll (*start_off_b64);
|
||||
}
|
||||
|
||||
whh = GNUNET_new (struct TALER_WIRE_HistoryHandle);
|
||||
whh->hres_cb = hres_cb;
|
||||
whh->hres_cb_cls = hres_cb_cls;
|
||||
whh->hh = TALER_BANK_history (tc->ctx,
|
||||
tc->bank_uri,
|
||||
&tc->auth,
|
||||
(uint64_t) tc->exchange_account_no,
|
||||
direction,
|
||||
start_row,
|
||||
num_results,
|
||||
&bhist_cb,
|
||||
whh);
|
||||
if (NULL == whh->hh)
|
||||
{
|
||||
GNUNET_break (0);
|
||||
GNUNET_free (whh);
|
||||
return NULL;
|
||||
}
|
||||
return whh;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Cancel going over the account's history.
|
||||
*
|
||||
* @param whh operation to cancel
|
||||
*/
|
||||
static void
|
||||
test_get_history_cancel (struct TALER_WIRE_HistoryHandle *whh)
|
||||
{
|
||||
TALER_BANK_history_cancel (whh->hh);
|
||||
GNUNET_free (whh);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Initialize test-wire subsystem.
|
||||
*
|
||||
@ -787,24 +947,24 @@ libtaler_plugin_wire_test_init (void *cls)
|
||||
{
|
||||
if (GNUNET_OK !=
|
||||
GNUNET_CONFIGURATION_get_value_string (cfg,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"BANK_URI",
|
||||
&tc->bank_uri))
|
||||
{
|
||||
GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"BANK_URI");
|
||||
GNUNET_free (tc);
|
||||
return NULL;
|
||||
}
|
||||
if (GNUNET_OK !=
|
||||
GNUNET_CONFIGURATION_get_value_number (cfg,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"EXCHANGE_ACCOUNT_NUMBER",
|
||||
&tc->exchange_account_outgoing_no))
|
||||
&tc->exchange_account_no))
|
||||
{
|
||||
GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"EXCHANGE_ACCOUNT_NUMBER");
|
||||
GNUNET_free (tc->bank_uri);
|
||||
GNUNET_free (tc);
|
||||
@ -825,12 +985,12 @@ libtaler_plugin_wire_test_init (void *cls)
|
||||
}
|
||||
if (GNUNET_OK !=
|
||||
GNUNET_CONFIGURATION_get_value_string (cfg,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"USERNAME",
|
||||
&user))
|
||||
{
|
||||
GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"USERNAME");
|
||||
GNUNET_free (tc->bank_uri);
|
||||
GNUNET_free (tc);
|
||||
@ -838,12 +998,12 @@ libtaler_plugin_wire_test_init (void *cls)
|
||||
}
|
||||
if (GNUNET_OK !=
|
||||
GNUNET_CONFIGURATION_get_value_string (cfg,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"PASSWORD",
|
||||
&pass))
|
||||
{
|
||||
GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR,
|
||||
"exchange-wire-outgoing-test",
|
||||
"exchange-wire-test",
|
||||
"PASSWORD");
|
||||
GNUNET_free (tc->bank_uri);
|
||||
GNUNET_free (tc);
|
||||
@ -877,6 +1037,8 @@ libtaler_plugin_wire_test_init (void *cls)
|
||||
plugin->prepare_wire_transfer_cancel = &test_prepare_wire_transfer_cancel;
|
||||
plugin->execute_wire_transfer = &test_execute_wire_transfer;
|
||||
plugin->execute_wire_transfer_cancel = &test_execute_wire_transfer_cancel;
|
||||
plugin->get_history = &test_get_history;
|
||||
plugin->get_history_cancel = &test_get_history_cancel;
|
||||
return plugin;
|
||||
}
|
||||
|
||||
|
@ -11,7 +11,7 @@ TEST_RESPONSE_FILE = test_wire_plugin_test.json
|
||||
SEPA_RESPONSE_FILE = test_wire_plugin_sepa.json
|
||||
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
[exchange-wire-test]
|
||||
# For transfers made by the exchange, we need to know
|
||||
# the URI of the bank (where the /admin/add/incoming API
|
||||
# is avaialble).
|
||||
|
@ -6,7 +6,6 @@
|
||||
# Set to "YES" to activate the 'sepa' plugin.
|
||||
ENABLE = NO
|
||||
|
||||
[exchange-wire-incoming-sepa]
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
SEPA_RESPONSE_FILE = ${TALER_CONFIG_HOME}/exchange/wire/sepa.json
|
||||
|
@ -6,19 +6,15 @@
|
||||
# Set to "YES" to activate the 'test' plugin.
|
||||
ENABLE = NO
|
||||
|
||||
[exchange-wire-incoming-test]
|
||||
# This is the response we give out for the /wire request. It provides
|
||||
# wallets with the bank information for transfers to the exchange.
|
||||
TEST_RESPONSE_FILE = ${TALER_CONFIG_HOME}/exchange/wire/test.json
|
||||
|
||||
[exchange-wire-outgoing-test]
|
||||
# For outgoing transfers, we need to know the exchange's
|
||||
# account number at the bank.
|
||||
# We need to know the exchange's account number at the bank.
|
||||
EXCHANGE_ACCOUNT_NUMBER = 2
|
||||
|
||||
# For transfers made by the exchange, we need to know
|
||||
# the URI of the bank (where the /admin/add/incoming API
|
||||
# is avaialble).
|
||||
# For accessing transfers, we need to know
|
||||
# the URI of the bank (where the /history API is available).
|
||||
# BANK_URI = https://bank.demo.taler.net/
|
||||
|
||||
# Authentication information for basic authentication
|
||||
|
Loading…
Reference in New Issue
Block a user