mirror of
https://github.com/ElementsProject/lightning.git
synced 2025-01-17 19:03:42 +01:00
invoices: Semantically separate invoice details from invoice.
In preparation for removing in-memory invoice structures. Invoice details are requested rarely anyway.
This commit is contained in:
parent
fc3e6782dd
commit
9b4c6699f9
@ -19,7 +19,7 @@
|
||||
#include <sodium/randombytes.h>
|
||||
#include <wire/wire_sync.h>
|
||||
|
||||
static const char *invoice_status_str(const struct invoice *inv)
|
||||
static const char *invoice_status_str(const struct invoice_details *inv)
|
||||
{
|
||||
if (inv->state == PAID)
|
||||
return "paid";
|
||||
@ -29,7 +29,7 @@ static const char *invoice_status_str(const struct invoice *inv)
|
||||
}
|
||||
|
||||
static void json_add_invoice(struct json_result *response,
|
||||
const struct invoice *inv,
|
||||
const struct invoice_details *inv,
|
||||
bool modern)
|
||||
{
|
||||
json_object_start(response, NULL);
|
||||
@ -60,9 +60,11 @@ static void json_add_invoice(struct json_result *response,
|
||||
static void tell_waiter(struct command *cmd, const struct invoice *inv)
|
||||
{
|
||||
struct json_result *response = new_json_result(cmd);
|
||||
struct invoice_details details;
|
||||
|
||||
json_add_invoice(response, inv, true);
|
||||
if (inv->state == PAID)
|
||||
wallet_invoice_details(cmd, cmd->ld->wallet, inv, &details);
|
||||
json_add_invoice(response, &details, true);
|
||||
if (details.state == PAID)
|
||||
command_success(cmd, response);
|
||||
else
|
||||
command_fail_detailed(cmd, -2, response,
|
||||
@ -103,6 +105,7 @@ static void json_invoice(struct command *cmd,
|
||||
const char *buffer, const jsmntok_t *params)
|
||||
{
|
||||
const struct invoice *invoice;
|
||||
struct invoice_details details;
|
||||
jsmntok_t *msatoshi, *label, *desc, *exp, *fallback;
|
||||
u64 *msatoshi_val;
|
||||
const char *label_val;
|
||||
@ -199,11 +202,14 @@ static void json_invoice(struct command *cmd,
|
||||
return;
|
||||
}
|
||||
|
||||
/* Get details */
|
||||
wallet_invoice_details(cmd, cmd->ld->wallet, invoice, &details);
|
||||
|
||||
/* Construct bolt11 string. */
|
||||
b11 = new_bolt11(cmd, invoice->msatoshi);
|
||||
b11 = new_bolt11(cmd, details.msatoshi);
|
||||
b11->chain = get_chainparams(cmd->ld);
|
||||
b11->timestamp = time_now().ts.tv_sec;
|
||||
b11->payment_hash = invoice->rhash;
|
||||
b11->payment_hash = details.rhash;
|
||||
b11->receiver_id = cmd->ld->id;
|
||||
b11->min_final_cltv_expiry = cmd->ld->config.cltv_final;
|
||||
b11->expiry = expiry;
|
||||
@ -217,10 +223,10 @@ static void json_invoice(struct command *cmd,
|
||||
|
||||
json_object_start(response, NULL);
|
||||
json_add_hex(response, "payment_hash",
|
||||
&invoice->rhash, sizeof(invoice->rhash));
|
||||
&details.rhash, sizeof(details.rhash));
|
||||
if (deprecated_apis)
|
||||
json_add_u64(response, "expiry_time", invoice->expiry_time);
|
||||
json_add_u64(response, "expires_at", invoice->expiry_time);
|
||||
json_add_u64(response, "expiry_time", details.expiry_time);
|
||||
json_add_u64(response, "expires_at", details.expiry_time);
|
||||
json_add_string(response, "bolt11", b11enc);
|
||||
json_object_end(response);
|
||||
|
||||
@ -240,15 +246,17 @@ static void json_add_invoices(struct json_result *response,
|
||||
bool modern)
|
||||
{
|
||||
const struct invoice *i;
|
||||
struct invoice_details details;
|
||||
char *lbl = NULL;
|
||||
if (label)
|
||||
lbl = tal_strndup(response, &buffer[label->start], label->end - label->start);
|
||||
|
||||
i = NULL;
|
||||
while ((i = wallet_invoice_iterate(wallet, i)) != NULL) {
|
||||
if (lbl && !streq(i->label, lbl))
|
||||
wallet_invoice_details(response, wallet, i, &details);
|
||||
if (lbl && !streq(details.label, lbl))
|
||||
continue;
|
||||
json_add_invoice(response, i, modern);
|
||||
json_add_invoice(response, &details, modern);
|
||||
}
|
||||
}
|
||||
|
||||
@ -311,6 +319,7 @@ static void json_delinvoice(struct command *cmd,
|
||||
const char *buffer, const jsmntok_t *params)
|
||||
{
|
||||
const struct invoice *i;
|
||||
struct invoice_details details;
|
||||
jsmntok_t *labeltok, *statustok;
|
||||
struct json_result *response = new_json_result(cmd);
|
||||
const char *label, *status, *actual_status;
|
||||
@ -330,12 +339,13 @@ static void json_delinvoice(struct command *cmd,
|
||||
command_fail(cmd, "Unknown invoice");
|
||||
return;
|
||||
}
|
||||
wallet_invoice_details(cmd, cmd->ld->wallet, i, &details);
|
||||
|
||||
status = tal_strndup(cmd, buffer + statustok->start,
|
||||
statustok->end - statustok->start);
|
||||
/* This is time-sensitive, so only call once; otherwise error msg
|
||||
* might not make sense if it changed! */
|
||||
actual_status = invoice_status_str(i);
|
||||
actual_status = invoice_status_str(&details);
|
||||
if (!streq(actual_status, status)) {
|
||||
command_fail(cmd, "Invoice status is %s not %s",
|
||||
actual_status, status);
|
||||
@ -344,7 +354,7 @@ static void json_delinvoice(struct command *cmd,
|
||||
|
||||
/* Get invoice details before attempting to delete, as
|
||||
* otherwise the invoice will be freed. */
|
||||
json_add_invoice(response, i, true);
|
||||
json_add_invoice(response, &details, true);
|
||||
|
||||
if (!wallet_invoice_delete(wallet, i)) {
|
||||
log_broken(cmd->ld->log,
|
||||
@ -415,6 +425,7 @@ static void json_waitinvoice(struct command *cmd,
|
||||
const char *buffer, const jsmntok_t *params)
|
||||
{
|
||||
const struct invoice *i;
|
||||
struct invoice_details details;
|
||||
struct wallet *wallet = cmd->ld->wallet;
|
||||
jsmntok_t *labeltok;
|
||||
const char *label = NULL;
|
||||
@ -430,7 +441,10 @@ static void json_waitinvoice(struct command *cmd,
|
||||
if (!i) {
|
||||
command_fail(cmd, "Label not found");
|
||||
return;
|
||||
} else if (i->state == PAID || i->state == EXPIRED) {
|
||||
}
|
||||
wallet_invoice_details(cmd, cmd->ld->wallet, i, &details);
|
||||
|
||||
if (details.state == PAID || details.state == EXPIRED) {
|
||||
tell_waiter(cmd, i);
|
||||
return;
|
||||
} else {
|
||||
|
@ -230,7 +230,9 @@ static void handle_localpay(struct htlc_in *hin,
|
||||
{
|
||||
enum onion_type failcode;
|
||||
const struct invoice *invoice;
|
||||
struct invoice_details details;
|
||||
struct lightningd *ld = hin->key.channel->peer->ld;
|
||||
const tal_t *tmpctx = tal_tmpctx(ld);
|
||||
|
||||
/* BOLT #4:
|
||||
*
|
||||
@ -265,6 +267,7 @@ static void handle_localpay(struct htlc_in *hin,
|
||||
failcode = WIRE_UNKNOWN_PAYMENT_HASH;
|
||||
goto fail;
|
||||
}
|
||||
wallet_invoice_details(tmpctx, ld->wallet, invoice, &details);
|
||||
|
||||
/* BOLT #4:
|
||||
*
|
||||
@ -276,10 +279,10 @@ static void handle_localpay(struct htlc_in *hin,
|
||||
*
|
||||
* 1. type: PERM|16 (`incorrect_payment_amount`)
|
||||
*/
|
||||
if (invoice->msatoshi != NULL && hin->msatoshi < *invoice->msatoshi) {
|
||||
if (details.msatoshi != NULL && hin->msatoshi < *details.msatoshi) {
|
||||
failcode = WIRE_INCORRECT_PAYMENT_AMOUNT;
|
||||
goto fail;
|
||||
} else if (invoice->msatoshi != NULL && hin->msatoshi > *invoice->msatoshi * 2) {
|
||||
} else if (details.msatoshi != NULL && hin->msatoshi > *details.msatoshi * 2) {
|
||||
failcode = WIRE_INCORRECT_PAYMENT_AMOUNT;
|
||||
goto fail;
|
||||
}
|
||||
@ -300,17 +303,21 @@ static void handle_localpay(struct htlc_in *hin,
|
||||
}
|
||||
|
||||
log_info(ld->log, "Resolving invoice '%s' with HTLC %"PRIu64,
|
||||
invoice->label, hin->key.id);
|
||||
details.label, hin->key.id);
|
||||
log_debug(ld->log, "%s: Actual amount %"PRIu64"msat, HTLC expiry %u",
|
||||
invoice->label, hin->msatoshi, cltv_expiry);
|
||||
fulfill_htlc(hin, &invoice->r);
|
||||
details.label, hin->msatoshi, cltv_expiry);
|
||||
fulfill_htlc(hin, &details.r);
|
||||
wallet_invoice_resolve(ld->wallet, invoice, hin->msatoshi);
|
||||
|
||||
tal_free(tmpctx);
|
||||
return;
|
||||
|
||||
fail:
|
||||
/* Final hop never sends an UPDATE. */
|
||||
assert(!(failcode & UPDATE));
|
||||
local_fail_htlc(hin, failcode, NULL);
|
||||
|
||||
tal_free(tmpctx);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -42,36 +42,38 @@ static void trigger_invoice_waiter(struct invoice_waiter *w,
|
||||
w->cb(invoice, w->cbarg);
|
||||
}
|
||||
|
||||
static bool wallet_stmt2invoice(sqlite3_stmt *stmt, struct invoice *inv)
|
||||
static bool wallet_stmt2invoice_details(sqlite3_stmt *stmt,
|
||||
struct invoice *invoice,
|
||||
struct invoice_details *dtl)
|
||||
{
|
||||
inv->id = sqlite3_column_int64(stmt, 0);
|
||||
inv->state = sqlite3_column_int(stmt, 1);
|
||||
invoice->id = sqlite3_column_int64(stmt, 0);
|
||||
dtl->state = sqlite3_column_int(stmt, 1);
|
||||
|
||||
assert(sqlite3_column_bytes(stmt, 2) == sizeof(struct preimage));
|
||||
memcpy(&inv->r, sqlite3_column_blob(stmt, 2), sqlite3_column_bytes(stmt, 2));
|
||||
memcpy(&dtl->r, sqlite3_column_blob(stmt, 2), sqlite3_column_bytes(stmt, 2));
|
||||
|
||||
assert(sqlite3_column_bytes(stmt, 3) == sizeof(struct sha256));
|
||||
memcpy(&inv->rhash, sqlite3_column_blob(stmt, 3), sqlite3_column_bytes(stmt, 3));
|
||||
memcpy(&dtl->rhash, sqlite3_column_blob(stmt, 3), sqlite3_column_bytes(stmt, 3));
|
||||
|
||||
inv->label = tal_strndup(inv, sqlite3_column_blob(stmt, 4), sqlite3_column_bytes(stmt, 4));
|
||||
dtl->label = tal_strndup(dtl, sqlite3_column_blob(stmt, 4), sqlite3_column_bytes(stmt, 4));
|
||||
|
||||
if (sqlite3_column_type(stmt, 5) != SQLITE_NULL) {
|
||||
inv->msatoshi = tal(inv, u64);
|
||||
*inv->msatoshi = sqlite3_column_int64(stmt, 5);
|
||||
dtl->msatoshi = tal(dtl, u64);
|
||||
*dtl->msatoshi = sqlite3_column_int64(stmt, 5);
|
||||
} else {
|
||||
inv->msatoshi = NULL;
|
||||
dtl->msatoshi = NULL;
|
||||
}
|
||||
|
||||
inv->expiry_time = sqlite3_column_int64(stmt, 6);
|
||||
dtl->expiry_time = sqlite3_column_int64(stmt, 6);
|
||||
|
||||
if (inv->state == PAID) {
|
||||
inv->pay_index = sqlite3_column_int64(stmt, 7);
|
||||
inv->msatoshi_received = sqlite3_column_int64(stmt, 8);
|
||||
inv->paid_timestamp = sqlite3_column_int64(stmt, 9);
|
||||
if (dtl->state == PAID) {
|
||||
dtl->pay_index = sqlite3_column_int64(stmt, 7);
|
||||
dtl->msatoshi_received = sqlite3_column_int64(stmt, 8);
|
||||
dtl->paid_timestamp = sqlite3_column_int64(stmt, 9);
|
||||
}
|
||||
|
||||
list_head_init(&inv->waitone_waiters);
|
||||
inv->expiration_timer = NULL;
|
||||
list_head_init(&invoice->waitone_waiters);
|
||||
invoice->expiration_timer = NULL;
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -102,7 +104,7 @@ static void trigger_expiration(struct invoice *i)
|
||||
sqlite3_stmt *stmt;
|
||||
struct invoice_waiter *w;
|
||||
|
||||
assert(i->state == UNPAID);
|
||||
assert(i->details->state == UNPAID);
|
||||
|
||||
/* Timer already triggered, destroy the timer object. */
|
||||
i->expiration_timer = tal_free(i->expiration_timer);
|
||||
@ -111,11 +113,11 @@ static void trigger_expiration(struct invoice *i)
|
||||
* (used by the timer system) and time_now (used
|
||||
* by the expiry time measurements). So check that
|
||||
* time_now is reached. */
|
||||
if (i->expiry_time <= now) {
|
||||
if (i->details->expiry_time <= now) {
|
||||
const tal_t *tmpctx = tal_tmpctx(i);
|
||||
|
||||
/* Update in-memory and db. */
|
||||
i->state = EXPIRED;
|
||||
i->details->state = EXPIRED;
|
||||
stmt = db_prepare(invoices->db,
|
||||
"UPDATE invoices"
|
||||
" SET state = ?"
|
||||
@ -143,11 +145,11 @@ static void install_expiration_timer(struct invoices *invoices,
|
||||
struct timeabs expiry;
|
||||
struct timeabs now = time_now();
|
||||
|
||||
assert(i->state == UNPAID);
|
||||
assert(i->details->state == UNPAID);
|
||||
assert(!i->expiration_timer);
|
||||
|
||||
memset(&expiry, 0, sizeof(expiry));
|
||||
expiry.ts.tv_sec = i->expiry_time;
|
||||
expiry.ts.tv_sec = i->details->expiry_time;
|
||||
|
||||
/* now > expiry */
|
||||
if (time_after(now, expiry))
|
||||
@ -197,12 +199,13 @@ bool invoices_load(struct invoices *invoices)
|
||||
while (sqlite3_step(stmt) == SQLITE_ROW) {
|
||||
i = tal(invoices, struct invoice);
|
||||
i->owner = invoices;
|
||||
if (!wallet_stmt2invoice(stmt, i)) {
|
||||
i->details = tal(i, struct invoice_details);
|
||||
if (!wallet_stmt2invoice_details(stmt, i, i->details)) {
|
||||
log_broken(invoices->log, "Error deserializing invoice");
|
||||
sqlite3_finalize(stmt);
|
||||
return false;
|
||||
}
|
||||
if (i->state == UNPAID)
|
||||
if (i->details->state == UNPAID)
|
||||
install_expiration_timer(invoices, i);
|
||||
list_add_tail(&invoices->invlist, &i->list);
|
||||
count++;
|
||||
@ -272,12 +275,13 @@ const struct invoice *invoices_create(struct invoices *invoices,
|
||||
invoice->owner = invoices;
|
||||
|
||||
invoice->id = sqlite3_last_insert_rowid(invoices->db->sql);
|
||||
invoice->state = UNPAID;
|
||||
invoice->label = tal_strdup(invoice, label);
|
||||
invoice->msatoshi = tal_dup(invoice, u64, msatoshi); /* Works even if msatoshi == NULL. */
|
||||
memcpy(&invoice->r, &r, sizeof(invoice->r));
|
||||
memcpy(&invoice->rhash, &rhash, sizeof(invoice->rhash));
|
||||
invoice->expiry_time = expiry_time;
|
||||
invoice->details = tal(invoice, struct invoice_details);
|
||||
invoice->details->state = UNPAID;
|
||||
invoice->details->label = tal_strdup(invoice->details, label);
|
||||
invoice->details->msatoshi = tal_dup(invoice->details, u64, msatoshi); /* Works even if msatoshi == NULL. */
|
||||
memcpy(&invoice->details->r, &r, sizeof(invoice->details->r));
|
||||
memcpy(&invoice->details->rhash, &rhash, sizeof(invoice->details->rhash));
|
||||
invoice->details->expiry_time = expiry_time;
|
||||
list_head_init(&invoice->waitone_waiters);
|
||||
invoice->expiration_timer = NULL;
|
||||
|
||||
@ -298,7 +302,7 @@ const struct invoice *invoices_find_by_label(struct invoices *invoices,
|
||||
|
||||
/* FIXME: Use something better than a linear scan. */
|
||||
list_for_each(&invoices->invlist, i, list) {
|
||||
if (streq(i->label, label))
|
||||
if (streq(i->details->label, label))
|
||||
return i;
|
||||
}
|
||||
return NULL;
|
||||
@ -310,8 +314,9 @@ const struct invoice *invoices_find_unpaid(struct invoices *invoices,
|
||||
struct invoice *i;
|
||||
|
||||
list_for_each(&invoices->invlist, i, list) {
|
||||
if (structeq(rhash, &i->rhash) && i->state == UNPAID) {
|
||||
if (time_now().ts.tv_sec > i->expiry_time)
|
||||
if (structeq(rhash, &i->details->rhash) &&
|
||||
i->details->state == UNPAID) {
|
||||
if (time_now().ts.tv_sec > i->details->expiry_time)
|
||||
break;
|
||||
return i;
|
||||
}
|
||||
@ -407,10 +412,10 @@ void invoices_resolve(struct invoices *invoices,
|
||||
db_exec_prepared(invoices->db, stmt);
|
||||
|
||||
/* Update in-memory structure. */
|
||||
invoice->state = PAID;
|
||||
invoice->pay_index = pay_index;
|
||||
invoice->msatoshi_received = msatoshi_received;
|
||||
invoice->paid_timestamp = paid_timestamp;
|
||||
invoice->details->state = PAID;
|
||||
invoice->details->pay_index = pay_index;
|
||||
invoice->details->msatoshi_received = msatoshi_received;
|
||||
invoice->details->paid_timestamp = paid_timestamp;
|
||||
invoice->expiration_timer = tal_free(invoice->expiration_timer);
|
||||
|
||||
/* Tell all the waitany waiters about the new paid invoice. */
|
||||
@ -506,7 +511,7 @@ void invoices_waitone(const tal_t *ctx,
|
||||
void *cbarg)
|
||||
{
|
||||
struct invoice *invoice = (struct invoice*) cinvoice;
|
||||
if (invoice->state == PAID || invoice->state == EXPIRED) {
|
||||
if (invoice->details->state == PAID || invoice->details->state == EXPIRED) {
|
||||
cb(invoice, cbarg);
|
||||
return;
|
||||
}
|
||||
@ -514,3 +519,24 @@ void invoices_waitone(const tal_t *ctx,
|
||||
/* Not yet paid. */
|
||||
add_invoice_waiter(ctx, &invoice->waitone_waiters, cb, cbarg);
|
||||
}
|
||||
|
||||
void invoices_get_details(const tal_t *ctx,
|
||||
struct invoices *invoices,
|
||||
const struct invoice *invoice,
|
||||
struct invoice_details *dtl)
|
||||
{
|
||||
dtl->state = invoice->details->state;
|
||||
dtl->r = invoice->details->r;
|
||||
dtl->rhash = invoice->details->rhash;
|
||||
dtl->label = tal_strdup(ctx, invoice->details->label);
|
||||
dtl->msatoshi =
|
||||
invoice->details->msatoshi ?
|
||||
tal_dup(ctx, u64, invoice->details->msatoshi) :
|
||||
/*otherwise*/ NULL ;
|
||||
dtl->expiry_time = invoice->details->expiry_time;
|
||||
if (dtl->state == PAID) {
|
||||
dtl->pay_index = invoice->details->pay_index;
|
||||
dtl->msatoshi_received = invoice->details->msatoshi_received;
|
||||
dtl->paid_timestamp = invoice->details->paid_timestamp;
|
||||
}
|
||||
}
|
||||
|
@ -7,6 +7,7 @@
|
||||
|
||||
struct db;
|
||||
struct invoice;
|
||||
struct invoice_details;
|
||||
struct invoices;
|
||||
struct log;
|
||||
struct sha256;
|
||||
@ -159,4 +160,17 @@ void invoices_waitone(const tal_t *ctx,
|
||||
void (*cb)(const struct invoice *, void*),
|
||||
void *cbarg);
|
||||
|
||||
/**
|
||||
* invoices_get_details - Get the invoice_details of an invoice.
|
||||
*
|
||||
* @ctx - the owner of the label and msatoshi fields returned.
|
||||
* @invoices - the invoice handler,
|
||||
* @invoice - the invoice to get details on.
|
||||
* @details - pointer to details object to load.
|
||||
*/
|
||||
void invoices_get_details(const tal_t *ctx,
|
||||
struct invoices *invoices,
|
||||
const struct invoice *invoice,
|
||||
struct invoice_details *details);
|
||||
|
||||
#endif /* LIGHTNING_WALLET_INVOICES_H */
|
||||
|
@ -112,6 +112,12 @@ const struct invoice *invoices_find_by_label(struct invoices *invoices UNNEEDED,
|
||||
const struct invoice *invoices_find_unpaid(struct invoices *invoices UNNEEDED,
|
||||
const struct sha256 *rhash UNNEEDED)
|
||||
{ fprintf(stderr, "invoices_find_unpaid called!\n"); abort(); }
|
||||
/* Generated stub for invoices_get_details */
|
||||
void invoices_get_details(const tal_t *ctx UNNEEDED,
|
||||
struct invoices *invoices UNNEEDED,
|
||||
const struct invoice *invoice UNNEEDED,
|
||||
struct invoice_details *details UNNEEDED)
|
||||
{ fprintf(stderr, "invoices_get_details called!\n"); abort(); }
|
||||
/* Generated stub for invoices_iterate */
|
||||
const struct invoice *invoices_iterate(struct invoices *invoices UNNEEDED,
|
||||
const struct invoice *invoice UNNEEDED)
|
||||
|
@ -1314,7 +1314,13 @@ void wallet_invoice_waitone(const tal_t *ctx,
|
||||
{
|
||||
invoices_waitone(ctx, wallet->invoices, invoice, cb, cbarg);
|
||||
}
|
||||
|
||||
void wallet_invoice_details(const tal_t *ctx,
|
||||
struct wallet *wallet,
|
||||
const struct invoice *invoice,
|
||||
struct invoice_details *details)
|
||||
{
|
||||
invoices_get_details(ctx, wallet->invoices, invoice, details);
|
||||
}
|
||||
|
||||
|
||||
struct htlc_stub *wallet_htlc_stubs(const tal_t *ctx, struct wallet *wallet,
|
||||
|
@ -368,6 +368,28 @@ enum invoice_status {
|
||||
EXPIRED,
|
||||
};
|
||||
|
||||
/* The information about an invoice */
|
||||
struct invoice_details {
|
||||
/* Current invoice state */
|
||||
enum invoice_status state;
|
||||
/* Preimage for this invoice */
|
||||
struct preimage r;
|
||||
/* Hash of preimage r */
|
||||
struct sha256 rhash;
|
||||
/* Label assigned by user */
|
||||
const char *label;
|
||||
/* NULL if they specified "any" */
|
||||
u64 *msatoshi;
|
||||
/* Absolute UNIX epoch time this will expire */
|
||||
u64 expiry_time;
|
||||
/* Set if state == PAID; order to be returned by waitanyinvoice */
|
||||
u64 pay_index;
|
||||
/* Set if state == PAID; amount received */
|
||||
u64 msatoshi_received;
|
||||
/* Set if state == PAID; time paid */
|
||||
u64 paid_timestamp;
|
||||
};
|
||||
|
||||
struct invoice {
|
||||
/* Internal, rest of lightningd should not use */
|
||||
/* List off ld->wallet->invoices. Must be first or else
|
||||
@ -381,21 +403,8 @@ struct invoice {
|
||||
struct oneshot *expiration_timer;
|
||||
/* The owning invoices object. */
|
||||
struct invoices *owner;
|
||||
|
||||
/* Publicly-usable fields. */
|
||||
enum invoice_status state;
|
||||
const char *label;
|
||||
/* NULL if they specified "any" */
|
||||
u64 *msatoshi;
|
||||
/* Set if state == PAID */
|
||||
u64 msatoshi_received;
|
||||
/* Set if state == PAID */
|
||||
u64 paid_timestamp;
|
||||
struct preimage r;
|
||||
u64 expiry_time;
|
||||
struct sha256 rhash;
|
||||
/* Set if state == PAID */
|
||||
u64 pay_index;
|
||||
/* Loaded details. */
|
||||
struct invoice_details *details;
|
||||
};
|
||||
|
||||
#define INVOICE_MAX_LABEL_LEN 128
|
||||
@ -540,6 +549,18 @@ void wallet_invoice_waitone(const tal_t *ctx,
|
||||
void (*cb)(const struct invoice *, void*),
|
||||
void *cbarg);
|
||||
|
||||
/**
|
||||
* wallet_invoice_details - Get the invoice_details of an invoice.
|
||||
*
|
||||
* @ctx - the owner of the label and msatoshi fields returned.
|
||||
* @wallet - the wallet to query.
|
||||
* @invoice - the invoice to get details on.
|
||||
* @details - pointer to details object to load.
|
||||
*/
|
||||
void wallet_invoice_details(const tal_t *ctx,
|
||||
struct wallet *wallet,
|
||||
const struct invoice *invoice,
|
||||
struct invoice_details *details);
|
||||
|
||||
/**
|
||||
* wallet_htlc_stubs - Retrieve HTLC stubs for the given channel
|
||||
|
Loading…
Reference in New Issue
Block a user