mirror of
https://github.com/aljazceru/cdk.git
synced 2025-12-18 21:25:09 +01:00
feat: bolt12
This commit is contained in:
@@ -101,6 +101,9 @@ pub enum Error {
|
||||
/// Invalid keyset ID
|
||||
#[error("Invalid keyset ID")]
|
||||
InvalidKeysetId,
|
||||
/// Invalid melt payment request
|
||||
#[error("Invalid melt payment request")]
|
||||
InvalidMeltPaymentRequest,
|
||||
}
|
||||
|
||||
impl From<Error> for cdk_common::database::Error {
|
||||
|
||||
@@ -44,7 +44,7 @@ pub async fn new_with_state(
|
||||
let mut tx = MintDatabase::begin_transaction(&db).await?;
|
||||
|
||||
for quote in mint_quotes {
|
||||
tx.add_or_replace_mint_quote(quote).await?;
|
||||
tx.add_mint_quote(quote).await?;
|
||||
}
|
||||
|
||||
for quote in melt_quotes {
|
||||
|
||||
@@ -21,4 +21,5 @@ pub static MIGRATIONS: &[(&str, &str)] = &[
|
||||
("20250406093755_mint_created_time_signature.sql", include_str!(r#"./migrations/20250406093755_mint_created_time_signature.sql"#)),
|
||||
("20250415093121_drop_keystore_foreign.sql", include_str!(r#"./migrations/20250415093121_drop_keystore_foreign.sql"#)),
|
||||
("20250626120251_rename_blind_message_y_to_b.sql", include_str!(r#"./migrations/20250626120251_rename_blind_message_y_to_b.sql"#)),
|
||||
("20250706101057_bolt12.sql", include_str!(r#"./migrations/20250706101057_bolt12.sql"#)),
|
||||
];
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
-- Add new columns to mint_quote table
|
||||
ALTER TABLE mint_quote ADD COLUMN amount_paid INTEGER NOT NULL DEFAULT 0;
|
||||
ALTER TABLE mint_quote ADD COLUMN amount_issued INTEGER NOT NULL DEFAULT 0;
|
||||
ALTER TABLE mint_quote ADD COLUMN payment_method TEXT NOT NULL DEFAULT 'BOLT11';
|
||||
ALTER TABLE mint_quote DROP COLUMN issued_time;
|
||||
ALTER TABLE mint_quote DROP COLUMN paid_time;
|
||||
|
||||
-- Set amount_paid equal to amount for quotes with PAID or ISSUED state
|
||||
UPDATE mint_quote SET amount_paid = amount WHERE state = 'PAID' OR state = 'ISSUED';
|
||||
|
||||
-- Set amount_issued equal to amount for quotes with ISSUED state
|
||||
UPDATE mint_quote SET amount_issued = amount WHERE state = 'ISSUED';
|
||||
|
||||
DROP INDEX IF EXISTS mint_quote_state_index;
|
||||
|
||||
-- Remove the state column from mint_quote table
|
||||
ALTER TABLE mint_quote DROP COLUMN state;
|
||||
|
||||
-- Remove NOT NULL constraint from amount column
|
||||
CREATE TABLE mint_quote_temp (
|
||||
id TEXT PRIMARY KEY,
|
||||
amount INTEGER,
|
||||
unit TEXT NOT NULL,
|
||||
request TEXT NOT NULL,
|
||||
expiry INTEGER NOT NULL,
|
||||
request_lookup_id TEXT UNIQUE,
|
||||
pubkey TEXT,
|
||||
created_time INTEGER NOT NULL DEFAULT 0,
|
||||
amount_paid INTEGER NOT NULL DEFAULT 0,
|
||||
amount_issued INTEGER NOT NULL DEFAULT 0,
|
||||
payment_method TEXT NOT NULL DEFAULT 'BOLT11'
|
||||
);
|
||||
|
||||
INSERT INTO mint_quote_temp (id, amount, unit, request, expiry, request_lookup_id, pubkey, created_time, amount_paid, amount_issued, payment_method)
|
||||
SELECT id, amount, unit, request, expiry, request_lookup_id, pubkey, created_time, amount_paid, amount_issued, payment_method
|
||||
FROM mint_quote;
|
||||
|
||||
DROP TABLE mint_quote;
|
||||
ALTER TABLE mint_quote_temp RENAME TO mint_quote;
|
||||
|
||||
ALTER TABLE mint_quote ADD COLUMN request_lookup_id_kind TEXT NOT NULL DEFAULT 'payment_hash';
|
||||
|
||||
CREATE INDEX IF NOT EXISTS idx_mint_quote_created_time ON mint_quote(created_time);
|
||||
CREATE INDEX IF NOT EXISTS idx_mint_quote_expiry ON mint_quote(expiry);
|
||||
CREATE INDEX IF NOT EXISTS idx_mint_quote_request_lookup_id ON mint_quote(request_lookup_id);
|
||||
CREATE INDEX IF NOT EXISTS idx_mint_quote_request_lookup_id_and_kind ON mint_quote(request_lookup_id, request_lookup_id_kind);
|
||||
|
||||
-- Create mint_quote_payments table
|
||||
CREATE TABLE mint_quote_payments (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
quote_id TEXT NOT NULL,
|
||||
payment_id TEXT NOT NULL UNIQUE,
|
||||
timestamp INTEGER NOT NULL,
|
||||
amount INTEGER NOT NULL,
|
||||
FOREIGN KEY (quote_id) REFERENCES mint_quote(id)
|
||||
);
|
||||
|
||||
-- Create index on payment_id for faster lookups
|
||||
CREATE INDEX idx_mint_quote_payments_payment_id ON mint_quote_payments(payment_id);
|
||||
CREATE INDEX idx_mint_quote_payments_quote_id ON mint_quote_payments(quote_id);
|
||||
|
||||
-- Create mint_quote_issued table
|
||||
CREATE TABLE mint_quote_issued (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
quote_id TEXT NOT NULL,
|
||||
amount INTEGER NOT NULL,
|
||||
timestamp INTEGER NOT NULL,
|
||||
FOREIGN KEY (quote_id) REFERENCES mint_quote(id)
|
||||
);
|
||||
|
||||
-- Create index on quote_id for faster lookups
|
||||
CREATE INDEX idx_mint_quote_issued_quote_id ON mint_quote_issued(quote_id);
|
||||
|
||||
-- Add new columns to melt_quote table
|
||||
ALTER TABLE melt_quote ADD COLUMN payment_method TEXT NOT NULL DEFAULT 'bolt11';
|
||||
ALTER TABLE melt_quote ADD COLUMN options TEXT;
|
||||
ALTER TABLE melt_quote ADD COLUMN request_lookup_id_kind TEXT NOT NULL DEFAULT 'payment_hash';
|
||||
|
||||
CREATE INDEX IF NOT EXISTS idx_melt_quote_request_lookup_id_and_kind ON mint_quote(request_lookup_id, request_lookup_id_kind);
|
||||
|
||||
ALTER TABLE melt_quote DROP COLUMN msat_to_pay;
|
||||
File diff suppressed because it is too large
Load Diff
@@ -17,4 +17,5 @@ pub static MIGRATIONS: &[(&str, &str)] = &[
|
||||
("20250323152040_wallet_dleq_proofs.sql", include_str!(r#"./migrations/20250323152040_wallet_dleq_proofs.sql"#)),
|
||||
("20250401120000_add_transactions_table.sql", include_str!(r#"./migrations/20250401120000_add_transactions_table.sql"#)),
|
||||
("20250616144830_add_keyset_expiry.sql", include_str!(r#"./migrations/20250616144830_add_keyset_expiry.sql"#)),
|
||||
("20250707093445_bolt12.sql", include_str!(r#"./migrations/20250707093445_bolt12.sql"#)),
|
||||
];
|
||||
|
||||
@@ -0,0 +1,58 @@
|
||||
ALTER TABLE mint_quote ADD COLUMN amount_paid INTEGER NOT NULL DEFAULT 0;
|
||||
ALTER TABLE mint_quote ADD COLUMN amount_minted INTEGER NOT NULL DEFAULT 0;
|
||||
ALTER TABLE mint_quote ADD COLUMN payment_method TEXT NOT NULL DEFAULT 'BOLT11';
|
||||
|
||||
-- Remove NOT NULL constraint from amount column
|
||||
PRAGMA foreign_keys=off;
|
||||
CREATE TABLE mint_quote_new (
|
||||
id TEXT PRIMARY KEY,
|
||||
mint_url TEXT NOT NULL,
|
||||
payment_method TEXT NOT NULL DEFAULT 'bolt11',
|
||||
amount INTEGER,
|
||||
unit TEXT NOT NULL,
|
||||
request TEXT NOT NULL,
|
||||
state TEXT NOT NULL,
|
||||
expiry INTEGER NOT NULL,
|
||||
amount_paid INTEGER NOT NULL DEFAULT 0,
|
||||
amount_issued INTEGER NOT NULL DEFAULT 0,
|
||||
secret_key TEXT
|
||||
);
|
||||
|
||||
-- Explicitly specify columns for proper mapping
|
||||
INSERT INTO mint_quote_new (
|
||||
id,
|
||||
mint_url,
|
||||
payment_method,
|
||||
amount,
|
||||
unit,
|
||||
request,
|
||||
state,
|
||||
expiry,
|
||||
amount_paid,
|
||||
amount_issued,
|
||||
secret_key
|
||||
)
|
||||
SELECT
|
||||
id,
|
||||
mint_url,
|
||||
'bolt11', -- Default value for the new payment_method column
|
||||
amount,
|
||||
unit,
|
||||
request,
|
||||
state,
|
||||
expiry,
|
||||
0, -- Default value for amount_paid
|
||||
0, -- Default value for amount_minted
|
||||
secret_key
|
||||
FROM mint_quote;
|
||||
|
||||
DROP TABLE mint_quote;
|
||||
ALTER TABLE mint_quote_new RENAME TO mint_quote;
|
||||
PRAGMA foreign_keys=on;
|
||||
|
||||
|
||||
-- Set amount_paid equal to amount for quotes with PAID or ISSUED state
|
||||
UPDATE mint_quote SET amount_paid = amount WHERE state = 'PAID' OR state = 'ISSUED';
|
||||
|
||||
-- Set amount_issued equal to amount for quotes with ISSUED state
|
||||
UPDATE mint_quote SET amount_issued = amount WHERE state = 'ISSUED';
|
||||
@@ -14,8 +14,8 @@ use cdk_common::nuts::{MeltQuoteState, MintQuoteState};
|
||||
use cdk_common::secret::Secret;
|
||||
use cdk_common::wallet::{self, MintQuote, Transaction, TransactionDirection, TransactionId};
|
||||
use cdk_common::{
|
||||
database, Amount, CurrencyUnit, Id, KeySet, KeySetInfo, Keys, MintInfo, Proof, ProofDleq,
|
||||
PublicKey, SecretKey, SpendingConditions, State,
|
||||
database, Amount, CurrencyUnit, Id, KeySet, KeySetInfo, Keys, MintInfo, PaymentMethod, Proof,
|
||||
ProofDleq, PublicKey, SecretKey, SpendingConditions, State,
|
||||
};
|
||||
use error::Error;
|
||||
use tracing::instrument;
|
||||
@@ -376,9 +376,9 @@ ON CONFLICT(mint_url) DO UPDATE SET
|
||||
Statement::new(
|
||||
r#"
|
||||
INSERT INTO mint_quote
|
||||
(id, mint_url, amount, unit, request, state, expiry, secret_key)
|
||||
(id, mint_url, amount, unit, request, state, expiry, secret_key, payment_method, amount_issued, amount_paid)
|
||||
VALUES
|
||||
(:id, :mint_url, :amount, :unit, :request, :state, :expiry, :secret_key)
|
||||
(:id, :mint_url, :amount, :unit, :request, :state, :expiry, :secret_key, :payment_method, :amount_issued, :amount_paid)
|
||||
ON CONFLICT(id) DO UPDATE SET
|
||||
mint_url = excluded.mint_url,
|
||||
amount = excluded.amount,
|
||||
@@ -386,18 +386,24 @@ ON CONFLICT(id) DO UPDATE SET
|
||||
request = excluded.request,
|
||||
state = excluded.state,
|
||||
expiry = excluded.expiry,
|
||||
secret_key = excluded.secret_key
|
||||
secret_key = excluded.secret_key,
|
||||
payment_method = excluded.payment_method,
|
||||
amount_issued = excluded.amount_issued,
|
||||
amount_paid = excluded.amount_paid
|
||||
;
|
||||
"#,
|
||||
)
|
||||
.bind(":id", quote.id.to_string())
|
||||
.bind(":mint_url", quote.mint_url.to_string())
|
||||
.bind(":amount", u64::from(quote.amount) as i64)
|
||||
.bind(":amount", quote.amount.map(|a| a.to_i64()))
|
||||
.bind(":unit", quote.unit.to_string())
|
||||
.bind(":request", quote.request)
|
||||
.bind(":state", quote.state.to_string())
|
||||
.bind(":expiry", quote.expiry as i64)
|
||||
.bind(":secret_key", quote.secret_key.map(|p| p.to_string()))
|
||||
.bind(":payment_method", quote.payment_method.to_string())
|
||||
.bind(":amount_issued", quote.amount_issued.to_i64())
|
||||
.bind(":amount_paid", quote.amount_paid.to_i64())
|
||||
.execute(&self.pool.get().map_err(Error::Pool)?)
|
||||
.map_err(Error::Sqlite)?;
|
||||
|
||||
@@ -416,7 +422,10 @@ ON CONFLICT(id) DO UPDATE SET
|
||||
request,
|
||||
state,
|
||||
expiry,
|
||||
secret_key
|
||||
secret_key,
|
||||
payment_method,
|
||||
amount_issued,
|
||||
amount_paid
|
||||
FROM
|
||||
mint_quote
|
||||
WHERE
|
||||
@@ -950,16 +959,24 @@ fn sqlite_row_to_mint_quote(row: Vec<Column>) -> Result<MintQuote, Error> {
|
||||
request,
|
||||
state,
|
||||
expiry,
|
||||
secret_key
|
||||
secret_key,
|
||||
row_method,
|
||||
row_amount_minted,
|
||||
row_amount_paid
|
||||
) = row
|
||||
);
|
||||
|
||||
let amount: u64 = column_as_number!(amount);
|
||||
let amount: Option<i64> = column_as_nullable_number!(amount);
|
||||
|
||||
let amount_paid: u64 = column_as_number!(row_amount_paid);
|
||||
let amount_minted: u64 = column_as_number!(row_amount_minted);
|
||||
let payment_method =
|
||||
PaymentMethod::from_str(&column_as_string!(row_method)).map_err(Error::from)?;
|
||||
|
||||
Ok(MintQuote {
|
||||
id: column_as_string!(id),
|
||||
mint_url: column_as_string!(mint_url, MintUrl::from_str),
|
||||
amount: Amount::from(amount),
|
||||
amount: amount.and_then(Amount::from_i64),
|
||||
unit: column_as_string!(unit, CurrencyUnit::from_str),
|
||||
request: column_as_string!(request),
|
||||
state: column_as_string!(state, MintQuoteState::from_str),
|
||||
@@ -967,6 +984,9 @@ fn sqlite_row_to_mint_quote(row: Vec<Column>) -> Result<MintQuote, Error> {
|
||||
secret_key: column_as_nullable_string!(secret_key)
|
||||
.map(|v| SecretKey::from_str(&v))
|
||||
.transpose()?,
|
||||
payment_method,
|
||||
amount_issued: amount_minted.into(),
|
||||
amount_paid: amount_paid.into(),
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user