feat(withdraw): type casting
This commit is contained in:
parent
63b9741c14
commit
14d61eaf56
6 changed files with 30 additions and 20 deletions
|
|
@ -58,14 +58,14 @@ def get_withdraw_link(link_id: str) -> Optional[WithdrawLink]:
|
||||||
with open_ext_db("withdraw") as db:
|
with open_ext_db("withdraw") as db:
|
||||||
row = db.fetchone("SELECT * FROM withdraw_links WHERE id = ?", (link_id,))
|
row = db.fetchone("SELECT * FROM withdraw_links WHERE id = ?", (link_id,))
|
||||||
|
|
||||||
return WithdrawLink(**row) if row else None
|
return WithdrawLink.from_row(row) if row else None
|
||||||
|
|
||||||
|
|
||||||
def get_withdraw_link_by_hash(unique_hash: str) -> Optional[WithdrawLink]:
|
def get_withdraw_link_by_hash(unique_hash: str) -> Optional[WithdrawLink]:
|
||||||
with open_ext_db("withdraw") as db:
|
with open_ext_db("withdraw") as db:
|
||||||
row = db.fetchone("SELECT * FROM withdraw_links WHERE unique_hash = ?", (unique_hash,))
|
row = db.fetchone("SELECT * FROM withdraw_links WHERE unique_hash = ?", (unique_hash,))
|
||||||
|
|
||||||
return WithdrawLink(**row) if row else None
|
return WithdrawLink.from_row(row) if row else None
|
||||||
|
|
||||||
|
|
||||||
def get_withdraw_links(wallet_ids: Union[str, List[str]]) -> List[WithdrawLink]:
|
def get_withdraw_links(wallet_ids: Union[str, List[str]]) -> List[WithdrawLink]:
|
||||||
|
|
@ -76,7 +76,7 @@ def get_withdraw_links(wallet_ids: Union[str, List[str]]) -> List[WithdrawLink]:
|
||||||
q = ",".join(["?"] * len(wallet_ids))
|
q = ",".join(["?"] * len(wallet_ids))
|
||||||
rows = db.fetchall(f"SELECT * FROM withdraw_links WHERE wallet IN ({q})", (*wallet_ids,))
|
rows = db.fetchall(f"SELECT * FROM withdraw_links WHERE wallet IN ({q})", (*wallet_ids,))
|
||||||
|
|
||||||
return [WithdrawLink(**row) for row in rows]
|
return [WithdrawLink.from_row(row) for row in rows]
|
||||||
|
|
||||||
|
|
||||||
def update_withdraw_link(link_id: str, **kwargs) -> Optional[WithdrawLink]:
|
def update_withdraw_link(link_id: str, **kwargs) -> Optional[WithdrawLink]:
|
||||||
|
|
@ -86,7 +86,7 @@ def update_withdraw_link(link_id: str, **kwargs) -> Optional[WithdrawLink]:
|
||||||
db.execute(f"UPDATE withdraw_links SET {q} WHERE id = ?", (*kwargs.values(), link_id))
|
db.execute(f"UPDATE withdraw_links SET {q} WHERE id = ?", (*kwargs.values(), link_id))
|
||||||
row = db.fetchone("SELECT * FROM withdraw_links WHERE id = ?", (link_id,))
|
row = db.fetchone("SELECT * FROM withdraw_links WHERE id = ?", (link_id,))
|
||||||
|
|
||||||
return WithdrawLink(**row) if row else None
|
return WithdrawLink.from_row(row) if row else None
|
||||||
|
|
||||||
|
|
||||||
def delete_withdraw_link(link_id: str) -> None:
|
def delete_withdraw_link(link_id: str) -> None:
|
||||||
|
|
|
||||||
|
|
@ -91,6 +91,7 @@ def m002_change_withdraw_table(db):
|
||||||
row[9], # spent
|
row[9], # spent
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
||||||
db.execute("DROP TABLE withdraws")
|
db.execute("DROP TABLE withdraws")
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
from flask import url_for
|
from flask import url_for
|
||||||
from lnurl import Lnurl, LnurlWithdrawResponse, encode as lnurl_encode
|
from lnurl import Lnurl, LnurlWithdrawResponse, encode as lnurl_encode
|
||||||
|
from sqlite3 import Row
|
||||||
from typing import NamedTuple
|
from typing import NamedTuple
|
||||||
|
|
||||||
from lnbits.settings import FORCE_HTTPS
|
from lnbits.settings import FORCE_HTTPS
|
||||||
|
|
@ -19,6 +20,12 @@ class WithdrawLink(NamedTuple):
|
||||||
open_time: int
|
open_time: int
|
||||||
used: int
|
used: int
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def from_row(cls, row: Row) -> "WithdrawLink":
|
||||||
|
data = dict(row)
|
||||||
|
data["is_unique"] = bool(data["is_unique"])
|
||||||
|
return cls(**data)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def is_spent(self) -> bool:
|
def is_spent(self) -> bool:
|
||||||
return self.used >= self.uses
|
return self.used >= self.uses
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,6 @@ Vue.component(VueQrcode.name, VueQrcode);
|
||||||
var locationPath = [window.location.protocol, '//', window.location.hostname, window.location.pathname].join('');
|
var locationPath = [window.location.protocol, '//', window.location.hostname, window.location.pathname].join('');
|
||||||
|
|
||||||
var mapWithdrawLink = function (obj) {
|
var mapWithdrawLink = function (obj) {
|
||||||
obj.is_unique = obj.is_unique == 1;
|
|
||||||
obj._data = _.clone(obj);
|
obj._data = _.clone(obj);
|
||||||
obj.date = Quasar.utils.date.formatDate(new Date(obj.time * 1000), 'YYYY-MM-DD HH:mm');
|
obj.date = Quasar.utils.date.formatDate(new Date(obj.time * 1000), 'YYYY-MM-DD HH:mm');
|
||||||
obj.min_fsat = new Intl.NumberFormat(LOCALE).format(obj.min_withdrawable);
|
obj.min_fsat = new Intl.NumberFormat(LOCALE).format(obj.min_withdrawable);
|
||||||
|
|
|
||||||
|
|
@ -8,20 +8,20 @@
|
||||||
group="api"
|
group="api"
|
||||||
dense
|
dense
|
||||||
expand-separator
|
expand-separator
|
||||||
label="List all withdraw links"
|
label="List withdraw links"
|
||||||
>
|
>
|
||||||
<q-card>
|
<q-card>
|
||||||
<q-card-section>
|
<q-card-section>
|
||||||
<code
|
<code
|
||||||
><span class="text-light-blue">GET</span> /withdraw/api/v1/links</code
|
><span class="text-blue">GET</span> /withdraw/api/v1/links</code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
||||||
<code>{"X-Api-Key": <invoice_key>}</code><br />
|
<code>{"X-Api-Key": <invoice_key>}</code><br />
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">
|
<h5 class="text-caption q-mt-sm q-mb-none">
|
||||||
Returns 201 CREATED (application/json)
|
Returns 200 OK (application/json)
|
||||||
</h5>
|
</h5>
|
||||||
<code>{"lnurl": <string>}</code>
|
<code>[<withdraw_link_object>, ...]</code>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
||||||
<code
|
<code
|
||||||
>curl -X GET {{ request.url_root }}withdraw/api/v1/links -H
|
>curl -X GET {{ request.url_root }}withdraw/api/v1/links -H
|
||||||
|
|
@ -34,13 +34,13 @@
|
||||||
group="api"
|
group="api"
|
||||||
dense
|
dense
|
||||||
expand-separator
|
expand-separator
|
||||||
label="List specific withdraw link"
|
label="Get a withdraw link"
|
||||||
>
|
>
|
||||||
<q-card>
|
<q-card>
|
||||||
<q-card-section>
|
<q-card-section>
|
||||||
<code
|
<code
|
||||||
><span class="text-light-blue">GET</span>
|
><span class="text-blue">GET</span>
|
||||||
/withdraw/api/v1/links/<LNURL_id></code
|
/withdraw/api/v1/links/<withdraw_id></code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
||||||
<code>{"X-Api-Key": <invoice_key>}</code><br />
|
<code>{"X-Api-Key": <invoice_key>}</code><br />
|
||||||
|
|
@ -52,7 +52,7 @@
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
||||||
<code
|
<code
|
||||||
>curl -X GET {{ request.url_root
|
>curl -X GET {{ request.url_root
|
||||||
}}withdraw/api/v1/links/<LNURL_id> -H "X-Api-Key: {{
|
}}withdraw/api/v1/links/<withdraw_id> -H "X-Api-Key: {{
|
||||||
g.user.wallets[0].inkey }}"
|
g.user.wallets[0].inkey }}"
|
||||||
</code>
|
</code>
|
||||||
</q-card-section>
|
</q-card-section>
|
||||||
|
|
@ -67,7 +67,7 @@
|
||||||
<q-card>
|
<q-card>
|
||||||
<q-card-section>
|
<q-card-section>
|
||||||
<code
|
<code
|
||||||
><span class="text-light-green">POST</span>
|
><span class="text-green">POST</span>
|
||||||
/withdraw/api/v1/links</code
|
/withdraw/api/v1/links</code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
||||||
|
|
@ -103,7 +103,7 @@
|
||||||
<q-card>
|
<q-card>
|
||||||
<q-card-section>
|
<q-card-section>
|
||||||
<code
|
<code
|
||||||
><span class="text-light-blue">PUT</span>
|
><span class="text-green">PUT</span>
|
||||||
/withdraw/api/v1/links/<withdraw_id></code
|
/withdraw/api/v1/links/<withdraw_id></code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
||||||
|
|
@ -115,7 +115,7 @@
|
||||||
"wait_time": <integer>, "is_unique": <boolean>}</code
|
"wait_time": <integer>, "is_unique": <boolean>}</code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">
|
<h5 class="text-caption q-mt-sm q-mb-none">
|
||||||
Returns 201 CREATED (application/json)
|
Returns 200 OK (application/json)
|
||||||
</h5>
|
</h5>
|
||||||
<code>{"lnurl": <string>}</code>
|
<code>{"lnurl": <string>}</code>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
||||||
|
|
@ -141,13 +141,13 @@
|
||||||
<q-card>
|
<q-card>
|
||||||
<q-card-section>
|
<q-card-section>
|
||||||
<code
|
<code
|
||||||
><span class="text-light-green">DELETE</span>
|
><span class="text-pink">DELETE</span>
|
||||||
/withdraw/api/v1/links/<withdraw_id></code
|
/withdraw/api/v1/links/<withdraw_id></code
|
||||||
>
|
>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
|
||||||
<code>{"X-Api-Key": <admin_key>}</code><br />
|
<code>{"X-Api-Key": <admin_key>}</code><br />
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Returns 201 NO_CONTENT</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Returns 204 NO CONTENT</h5>
|
||||||
<code>{"lnurl": <string>}</code>
|
<code></code>
|
||||||
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
|
||||||
<code
|
<code
|
||||||
>curl -X DELETE {{ request.url_root
|
>curl -X DELETE {{ request.url_root
|
||||||
|
|
|
||||||
|
|
@ -68,7 +68,10 @@ def api_link_retrieve(link_id):
|
||||||
)
|
)
|
||||||
def api_link_create_or_update(link_id=None):
|
def api_link_create_or_update(link_id=None):
|
||||||
if g.data["max_withdrawable"] < g.data["min_withdrawable"]:
|
if g.data["max_withdrawable"] < g.data["min_withdrawable"]:
|
||||||
return jsonify({"message": "`max_withdrawable` needs to be at least `min_withdrawable`."}), HTTPStatus.BAD_REQUEST
|
return (
|
||||||
|
jsonify({"message": "`max_withdrawable` needs to be at least `min_withdrawable`."}),
|
||||||
|
HTTPStatus.BAD_REQUEST,
|
||||||
|
)
|
||||||
|
|
||||||
if (g.data["max_withdrawable"] * g.data["uses"] * 1000) > g.wallet.balance_msat:
|
if (g.data["max_withdrawable"] * g.data["uses"] * 1000) > g.wallet.balance_msat:
|
||||||
return jsonify({"message": "Insufficient balance."}), HTTPStatus.FORBIDDEN
|
return jsonify({"message": "Insufficient balance."}), HTTPStatus.FORBIDDEN
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue