2019-11-05 00:10:32 +01:00
|
|
|
package invoices
|
|
|
|
|
2019-11-19 13:33:05 +01:00
|
|
|
import (
|
2023-10-11 13:42:59 +02:00
|
|
|
"context"
|
2023-11-24 18:51:49 +01:00
|
|
|
"time"
|
2022-11-30 12:00:37 +01:00
|
|
|
|
2024-05-05 14:48:50 +02:00
|
|
|
"github.com/btcsuite/btcd/chaincfg/chainhash"
|
2022-11-30 12:00:37 +01:00
|
|
|
"github.com/lightningnetwork/lnd/channeldb/models"
|
|
|
|
"github.com/lightningnetwork/lnd/lntypes"
|
2023-11-24 18:51:49 +01:00
|
|
|
"github.com/lightningnetwork/lnd/lnwire"
|
2019-11-19 13:33:05 +01:00
|
|
|
"github.com/lightningnetwork/lnd/record"
|
|
|
|
)
|
2019-11-05 00:10:32 +01:00
|
|
|
|
2022-11-30 12:00:37 +01:00
|
|
|
// InvoiceDB is the database that stores the information about invoices.
|
|
|
|
type InvoiceDB interface {
|
|
|
|
// AddInvoice inserts the targeted invoice into the database.
|
|
|
|
// If the invoice has *any* payment hashes which already exists within
|
|
|
|
// the database, then the insertion will be aborted and rejected due to
|
|
|
|
// the strict policy banning any duplicate payment hashes.
|
|
|
|
//
|
|
|
|
// NOTE: A side effect of this function is that it sets AddIndex on
|
|
|
|
// newInvoice.
|
2023-10-11 13:42:59 +02:00
|
|
|
AddInvoice(ctx context.Context, invoice *Invoice,
|
|
|
|
paymentHash lntypes.Hash) (uint64, error)
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// InvoicesAddedSince can be used by callers to seek into the event
|
|
|
|
// time series of all the invoices added in the database. The specified
|
|
|
|
// sinceAddIndex should be the highest add index that the caller knows
|
|
|
|
// of. This method will return all invoices with an add index greater
|
|
|
|
// than the specified sinceAddIndex.
|
|
|
|
//
|
|
|
|
// NOTE: The index starts from 1, as a result. We enforce that
|
|
|
|
// specifying a value below the starting index value is a noop.
|
2023-10-11 13:42:59 +02:00
|
|
|
InvoicesAddedSince(ctx context.Context, sinceAddIndex uint64) (
|
|
|
|
[]Invoice, error)
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// LookupInvoice attempts to look up an invoice according to its 32 byte
|
|
|
|
// payment hash. If an invoice which can settle the HTLC identified by
|
|
|
|
// the passed payment hash isn't found, then an error is returned.
|
|
|
|
// Otherwise, the full invoice is returned.
|
|
|
|
// Before setting the incoming HTLC, the values SHOULD be checked to
|
|
|
|
// ensure the payer meets the agreed upon contractual terms of the
|
|
|
|
// payment.
|
2023-10-11 13:42:59 +02:00
|
|
|
LookupInvoice(ctx context.Context, ref InvoiceRef) (Invoice, error)
|
2022-11-30 12:00:37 +01:00
|
|
|
|
2023-10-10 18:41:06 +02:00
|
|
|
// FetchPendingInvoices returns all invoices that have not yet been
|
|
|
|
// settled or canceled.
|
|
|
|
FetchPendingInvoices(ctx context.Context) (map[lntypes.Hash]Invoice,
|
|
|
|
error)
|
|
|
|
|
2022-11-30 12:00:37 +01:00
|
|
|
// QueryInvoices allows a caller to query the invoice database for
|
|
|
|
// invoices within the specified add index range.
|
2023-10-11 13:42:59 +02:00
|
|
|
QueryInvoices(ctx context.Context, q InvoiceQuery) (InvoiceSlice, error)
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// UpdateInvoice attempts to update an invoice corresponding to the
|
|
|
|
// passed payment hash. If an invoice matching the passed payment hash
|
|
|
|
// doesn't exist within the database, then the action will fail with a
|
|
|
|
// "not found" error.
|
|
|
|
//
|
|
|
|
// The update is performed inside the same database transaction that
|
|
|
|
// fetches the invoice and is therefore atomic. The fields to update
|
|
|
|
// are controlled by the supplied callback.
|
|
|
|
//
|
|
|
|
// TODO(positiveblue): abstract this functionality so it makes sense for
|
|
|
|
// other backends like sql.
|
2023-10-11 13:42:59 +02:00
|
|
|
UpdateInvoice(ctx context.Context, ref InvoiceRef, setIDHint *SetID,
|
2022-11-30 12:00:37 +01:00
|
|
|
callback InvoiceUpdateCallback) (*Invoice, error)
|
|
|
|
|
|
|
|
// InvoicesSettledSince can be used by callers to catch up any settled
|
|
|
|
// invoices they missed within the settled invoice time series. We'll
|
|
|
|
// return all known settled invoice that have a settle index higher than
|
|
|
|
// the passed sinceSettleIndex.
|
|
|
|
//
|
|
|
|
// NOTE: The index starts from 1, as a result. We enforce that
|
|
|
|
// specifying a value below the starting index value is a noop.
|
2023-10-11 13:42:59 +02:00
|
|
|
InvoicesSettledSince(ctx context.Context, sinceSettleIndex uint64) (
|
|
|
|
[]Invoice, error)
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// DeleteInvoice attempts to delete the passed invoices from the
|
|
|
|
// database in one transaction. The passed delete references hold all
|
|
|
|
// keys required to delete the invoices without also needing to
|
2023-12-21 16:21:35 +01:00
|
|
|
// deserialize them.
|
2023-10-11 13:42:59 +02:00
|
|
|
DeleteInvoice(ctx context.Context,
|
|
|
|
invoicesToDelete []InvoiceDeleteRef) error
|
2023-10-10 22:23:50 +02:00
|
|
|
|
|
|
|
// DeleteCanceledInvoices removes all canceled invoices from the
|
|
|
|
// database.
|
|
|
|
DeleteCanceledInvoices(ctx context.Context) error
|
2022-11-30 12:00:37 +01:00
|
|
|
}
|
|
|
|
|
2019-11-05 00:10:32 +01:00
|
|
|
// Payload abstracts access to any additional fields provided in the final hop's
|
|
|
|
// TLV onion payload.
|
|
|
|
type Payload interface {
|
|
|
|
// MultiPath returns the record corresponding the option_mpp parsed from
|
|
|
|
// the onion payload.
|
|
|
|
MultiPath() *record.MPP
|
2019-11-19 13:33:05 +01:00
|
|
|
|
2021-03-03 18:54:11 +01:00
|
|
|
// AMPRecord returns the record corresponding to the option_amp record
|
|
|
|
// parsed from the onion payload.
|
|
|
|
AMPRecord() *record.AMP
|
|
|
|
|
2019-11-19 13:33:05 +01:00
|
|
|
// CustomRecords returns the custom tlv type records that were parsed
|
|
|
|
// from the payload.
|
2019-12-12 00:01:55 +01:00
|
|
|
CustomRecords() record.CustomSet
|
2022-01-11 14:15:23 +01:00
|
|
|
|
|
|
|
// Metadata returns the additional data that is sent along with the
|
|
|
|
// payment to the payee.
|
|
|
|
Metadata() []byte
|
2024-05-05 14:48:50 +02:00
|
|
|
|
|
|
|
// PathID returns the path ID encoded in the payload of a blinded
|
|
|
|
// payment.
|
|
|
|
PathID() *chainhash.Hash
|
|
|
|
|
|
|
|
// TotalAmtMsat returns the total amount sent to the final hop, as set
|
|
|
|
// by the payee.
|
|
|
|
TotalAmtMsat() lnwire.MilliSatoshi
|
2019-11-05 00:10:32 +01:00
|
|
|
}
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// InvoiceQuery represents a query to the invoice database. The query allows a
|
|
|
|
// caller to retrieve all invoices starting from a particular add index and
|
|
|
|
// limit the number of results returned.
|
|
|
|
type InvoiceQuery struct {
|
|
|
|
// IndexOffset is the offset within the add indices to start at. This
|
|
|
|
// can be used to start the response at a particular invoice.
|
|
|
|
IndexOffset uint64
|
|
|
|
|
|
|
|
// NumMaxInvoices is the maximum number of invoices that should be
|
|
|
|
// starting from the add index.
|
|
|
|
NumMaxInvoices uint64
|
|
|
|
|
|
|
|
// PendingOnly, if set, returns unsettled invoices starting from the
|
|
|
|
// add index.
|
|
|
|
PendingOnly bool
|
|
|
|
|
|
|
|
// Reversed, if set, indicates that the invoices returned should start
|
|
|
|
// from the IndexOffset and go backwards.
|
|
|
|
Reversed bool
|
|
|
|
|
2024-01-26 04:11:37 +01:00
|
|
|
// CreationDateStart, expressed in Unix seconds, if set, filters out
|
|
|
|
// all invoices with a creation date greater than or equal to it.
|
|
|
|
CreationDateStart int64
|
2022-11-30 12:00:37 +01:00
|
|
|
|
|
|
|
// CreationDateEnd, if set, filters out all invoices with a creation
|
2024-01-26 04:11:37 +01:00
|
|
|
// date less than or equal to it.
|
|
|
|
CreationDateEnd int64
|
2022-11-30 12:00:37 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
// InvoiceSlice is the response to a invoice query. It includes the original
|
|
|
|
// query, the set of invoices that match the query, and an integer which
|
|
|
|
// represents the offset index of the last item in the set of returned invoices.
|
|
|
|
// This integer allows callers to resume their query using this offset in the
|
|
|
|
// event that the query's response exceeds the maximum number of returnable
|
|
|
|
// invoices.
|
|
|
|
type InvoiceSlice struct {
|
|
|
|
InvoiceQuery
|
|
|
|
|
|
|
|
// Invoices is the set of invoices that matched the query above.
|
|
|
|
Invoices []Invoice
|
|
|
|
|
|
|
|
// FirstIndexOffset is the index of the first element in the set of
|
|
|
|
// returned Invoices above. Callers can use this to resume their query
|
|
|
|
// in the event that the slice has too many events to fit into a single
|
|
|
|
// response.
|
|
|
|
FirstIndexOffset uint64
|
|
|
|
|
|
|
|
// LastIndexOffset is the index of the last element in the set of
|
|
|
|
// returned Invoices above. Callers can use this to resume their query
|
|
|
|
// in the event that the slice has too many events to fit into a single
|
|
|
|
// response.
|
|
|
|
LastIndexOffset uint64
|
|
|
|
}
|
|
|
|
|
|
|
|
// CircuitKey is a tuple of channel ID and HTLC ID, used to uniquely identify
|
|
|
|
// HTLCs in a circuit.
|
|
|
|
type CircuitKey = models.CircuitKey
|
2023-11-24 18:51:49 +01:00
|
|
|
|
|
|
|
// InvoiceUpdater is an interface to abstract away the details of updating an
|
|
|
|
// invoice in the database. The methods of this interface are called during the
|
|
|
|
// in-memory update of an invoice when the database needs to be updated or the
|
|
|
|
// updated state needs to be marked as needing to be written to the database.
|
|
|
|
type InvoiceUpdater interface {
|
|
|
|
// AddHtlc adds a new htlc to the invoice.
|
|
|
|
AddHtlc(circuitKey CircuitKey, newHtlc *InvoiceHTLC) error
|
|
|
|
|
|
|
|
// ResolveHtlc marks an htlc as resolved with the given state.
|
|
|
|
ResolveHtlc(circuitKey CircuitKey, state HtlcState,
|
|
|
|
resolveTime time.Time) error
|
|
|
|
|
|
|
|
// AddAmpHtlcPreimage adds a preimage of an AMP htlc to the AMP invoice
|
|
|
|
// identified by the setID.
|
|
|
|
AddAmpHtlcPreimage(setID [32]byte, circuitKey CircuitKey,
|
|
|
|
preimage lntypes.Preimage) error
|
|
|
|
|
|
|
|
// UpdateInvoiceState updates the invoice state to the new state.
|
|
|
|
UpdateInvoiceState(newState ContractState,
|
|
|
|
preimage *lntypes.Preimage) error
|
|
|
|
|
|
|
|
// UpdateInvoiceAmtPaid updates the invoice amount paid to the new
|
|
|
|
// amount.
|
|
|
|
UpdateInvoiceAmtPaid(amtPaid lnwire.MilliSatoshi) error
|
|
|
|
|
|
|
|
// UpdateAmpState updates the state of the AMP invoice identified by
|
|
|
|
// the setID.
|
|
|
|
UpdateAmpState(setID [32]byte, newState InvoiceStateAMP,
|
|
|
|
circuitKey models.CircuitKey) error
|
|
|
|
|
|
|
|
// Finalize finalizes the update before it is written to the database.
|
|
|
|
Finalize(updateType UpdateType) error
|
|
|
|
}
|