Merge remote-tracking branch 'origin/main' into patch-2

This commit is contained in:
ben 2022-07-28 10:36:47 +01:00
commit 822373a763
24 changed files with 276 additions and 192 deletions

View File

@ -5,10 +5,9 @@ on: [push, pull_request]
jobs:
check:
runs-on: ubuntu-latest
if: ${{ 'false' == 'true' }} # skip mypy for now
steps:
- uses: actions/checkout@v1
- uses: jpetrucciani/mypy-check@master
with:
mypy_flags: '--install-types --non-interactive'
path: lnbits
path: 'lnbits'

12
Pipfile
View File

@ -36,9 +36,11 @@ pycryptodomex = "*"
[dev-packages]
black = "==20.8b1"
pytest = "*"
pytest-cov = "*"
mypy = "*"
pytest-asyncio = "*"
requests = "*"
mock = "*"
mypy = "*"
pytest = "*"
pytest-asyncio = "*"
pytest-cov = "*"
requests = "*"
types-mock = "*"
types-protobuf = "*"

225
Pipfile.lock generated
View File

@ -1,7 +1,7 @@
{
"_meta": {
"hash": {
"sha256": "503e9942306106e40621c59f37a3ab866b483f8c5f27b879c1c6783dca30949f"
"sha256": "08e53fc6f1fcc021b33f9b2c5ae3bd6dbde815d4b317e9341ab02cf5b625acbc"
},
"pipfile-spec": 6,
"requires": {
@ -29,6 +29,7 @@
"sha256:413adf95f93886e442aea925f3ee43baa5a765a64a0f52c6081894f9992fdd0b",
"sha256:cb29b9c70620506a9a8f87a309591713446953302d7d995344d0d7c6c0c9a7be"
],
"markers": "python_full_version >= '3.6.2'",
"version": "==3.6.1"
},
"asyncio": {
@ -46,6 +47,7 @@
"sha256:2d27e3784d7a565d36ab851fe94887c5eccd6a463168875832a1be79c82828b4",
"sha256:626ba8234211db98e869df76230a137c4c40a12d72445c45d5f5b716f076e2fd"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==21.4.0"
},
"bech32": {
@ -53,6 +55,7 @@
"sha256:7d6db8214603bd7871fcfa6c0826ef68b85b0abd90fa21c285a9c5e21d2bd899",
"sha256:990dc8e5a5e4feabbdf55207b5315fdd9b73db40be294a19b3752cde9e79d981"
],
"markers": "python_version >= '3.5'",
"version": "==1.2.0"
},
"bitstring": {
@ -76,6 +79,7 @@
"sha256:84c85a9078b11105f04f3036a9482ae10e4621616db313fe045dd24743a0820d",
"sha256:fe86415d55e84719d75f8b69414f6438ac3547d2078ab91b67e779ef69378412"
],
"markers": "python_version >= '3.6'",
"version": "==2022.6.15"
},
"cffi": {
@ -139,6 +143,7 @@
"sha256:7682dc8afb30297001674575ea00d1814d808d6a36af415a82bd481d37ba7b8e",
"sha256:bb4d8133cb15a609f44e8213d9b391b0809795062913b383c62be0ee95b1db48"
],
"markers": "python_version >= '3.7'",
"version": "==8.1.3"
},
"ecdsa": {
@ -177,6 +182,7 @@
"sha256:36a3cb8c0a032f56e2da7084577878a035d3b61d104230d4bd49c0c6b555a9c6",
"sha256:47222cb6067e4a307d535814917cd98fd0a57b6788ce715755fa2b6c28b56042"
],
"markers": "python_version >= '3.6'",
"version": "==0.12.0"
},
"httpcore": {
@ -184,6 +190,7 @@
"sha256:1105b8b73c025f23ff7c36468e4432226cbb959176eab66864b8e31c4ee27fa6",
"sha256:18b68ab86a3ccf3e7dc0f43598eaddcf472b602aba29f9aa6ab85fe2ada3980b"
],
"markers": "python_version >= '3.7'",
"version": "==0.15.0"
},
"httptools": {
@ -238,6 +245,7 @@
"sha256:84d9dd047ffa80596e0f246e2eab0b391788b0503584e8945f2368256d2735ff",
"sha256:9d643ff0a55b762d5cdb124b8eaa99c66322e2157b69160bc32796e824360e6d"
],
"markers": "python_version >= '3.5'",
"version": "==3.3"
},
"jinja2": {
@ -307,6 +315,7 @@
"sha256:f121a1420d4e173a5d96e47e9a0c0dcff965afdf1626d28de1460815f7c4ee7a",
"sha256:fc7b548b17d238737688817ab67deebb30e8073c95749d55538ed473130ec0c7"
],
"markers": "python_version >= '3.7'",
"version": "==2.1.1"
},
"marshmallow": {
@ -314,6 +323,7 @@
"sha256:00040ab5ea0c608e8787137627a8efae97fabd60552a05dc889c888f814e75eb",
"sha256:635fb65a3285a31a30f276f30e958070f5214c7196202caa5c7ecf28f5274bc7"
],
"markers": "python_version >= '3.7'",
"version": "==3.17.0"
},
"outcome": {
@ -321,6 +331,7 @@
"sha256:6f82bd3de45da303cf1f771ecafa1633750a358436a8bb60e06a1ceb745d2672",
"sha256:c4ab89a56575d6d38a05aa16daeaa333109c1f96167aba8901ab18b6b5e0f7f5"
],
"markers": "python_version >= '3.7'",
"version": "==1.2.0"
},
"packaging": {
@ -328,6 +339,7 @@
"sha256:dd47c42927d89ab911e606518907cc2d3a1f38bbd026385970643f9c5b8ecfeb",
"sha256:ef103e05f519cdc783ae24ea4e2e0f508a9c99b2d4969652eed6a2e1ea5bd522"
],
"markers": "python_version >= '3.6'",
"version": "==21.3"
},
"psycopg2-binary": {
@ -473,6 +485,7 @@
"sha256:f0f047e11febe5c3198ed346b507e1d010330d56ad615a7e0a89fae604065a0e",
"sha256:fe4670cb32ea98ffbf5a1262f14c3e102cccd92b1869df3bb09538158ba90fe6"
],
"markers": "python_full_version >= '3.6.1'",
"version": "==1.9.1"
},
"pyngrok": {
@ -487,6 +500,7 @@
"sha256:2b020ecf7d21b687f219b71ecad3631f644a47f01403fa1d1036b0c6416d70fb",
"sha256:5026bae9a10eeaefb61dab2f09052b9f4307d44aee4eda64b309723d8d206bbc"
],
"markers": "python_full_version >= '3.6.8'",
"version": "==3.0.9"
},
"pypng": {
@ -517,6 +531,7 @@
"sha256:b7e3b04a59693c42c36f9ab1cc2acc46fa5df8c78e178fc33a8d4cd05c8d498f",
"sha256:d92a187be61fe482e4fd675b6d52200e7be63a12b724abbf931a40ce4fa92938"
],
"markers": "python_version >= '3.5'",
"version": "==0.20.0"
},
"pyyaml": {
@ -562,9 +577,13 @@
"sha256:026c0de2ee8385d1255b9c2426cd4f03fe9177ac94c09979bc601946c8493aa0",
"sha256:99142650756ef1998ce0661568f54a47dac8c638fb27e3816c02536575dbba8c"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==1.6.0.post0"
},
"rfc3986": {
"extras": [
"idna2008"
],
"hashes": [
"sha256:270aaf10d87d0d4e095063c65bf3ddbc6ee3d0b226328ce21e036f946e421835",
"sha256:a86d6e1f5b1dc238b218b012df0aa79409667bb209e58da56d0b94704e712a97"
@ -600,6 +619,14 @@
"index": "pypi",
"version": "==0.14.0"
},
"setuptools": {
"hashes": [
"sha256:0d33c374d41c7863419fc8f6c10bfe25b7b498aa34164d135c622e52580c6b16",
"sha256:c04b44a57a6265fe34a4a444e965884716d34bae963119a76353434d6f18e450"
],
"markers": "python_version >= '3.7'",
"version": "==63.2.0"
},
"shortuuid": {
"hashes": [
"sha256:459f12fa1acc34ff213b1371467c0325169645a31ed989e268872339af7563d5",
@ -613,6 +640,7 @@
"sha256:1e61c37477a1626458e36f7b1d82aa5c9b094fa4802892072e49de9c60c4c926",
"sha256:8abb2f1d86890a2dfb989f9a77cfcfd3e47c2a354b01111771326f8aa26e0254"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2'",
"version": "==1.16.0"
},
"sniffio": {
@ -620,6 +648,7 @@
"sha256:471b71698eac1c2112a40ce2752bb2f4a4814c22a54a3eed3676bc0f5ca9f663",
"sha256:c4666eecec1d3f50960c6bdf61ab7bc350648da6c126e3cf6898d8cd4ddcd3de"
],
"markers": "python_version >= '3.5'",
"version": "==1.2.0"
},
"sqlalchemy": {
@ -676,17 +705,18 @@
},
"sse-starlette": {
"hashes": [
"sha256:840607fed361360cc76f8408a25f0eca887e7cab3c3ee44f9762f179428e2bd4",
"sha256:ca2de945af80b83f1efda6144df9e13db83880b3b87c660044b64f199395e8b7"
"sha256:14608559d40e3e7c6385e8c5a7b88468f7fc40c2277673a1fe8d26568e8d7c65",
"sha256:72438ed39b1612d1ea6d89a7c0af8afee6de0389dcbe2e77539001e78b5aa89c"
],
"index": "pypi",
"version": "==0.10.3"
"version": "==1.0.0"
},
"starlette": {
"hashes": [
"sha256:5a60c5c2d051f3a8eb546136aa0c9399773a689595e099e0877704d5888279bf",
"sha256:c6d21096774ecb9639acad41b86b7706e52ba3bf1dc13ea4ed9ad593d47e24c7"
],
"markers": "python_version >= '3.6'",
"version": "==0.19.1"
},
"typing-extensions": {
@ -698,6 +728,9 @@
"version": "==4.3.0"
},
"uvicorn": {
"extras": [
"standard"
],
"hashes": [
"sha256:c19a057deb1c5bb060946e2e5c262fc01590c6529c0af2c3d9ce941e89bc30e0",
"sha256:cade07c403c397f9fe275492a48c1b869efd175d5d8a692df649e6e7e2ed8f4e"
@ -815,6 +848,7 @@
"sha256:2d27e3784d7a565d36ab851fe94887c5eccd6a463168875832a1be79c82828b4",
"sha256:626ba8234211db98e869df76230a137c4c40a12d72445c45d5f5b716f076e2fd"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==21.4.0"
},
"black": {
@ -829,6 +863,7 @@
"sha256:84c85a9078b11105f04f3036a9482ae10e4621616db313fe045dd24743a0820d",
"sha256:fe86415d55e84719d75f8b69414f6438ac3547d2078ab91b67e779ef69378412"
],
"markers": "python_version >= '3.6'",
"version": "==2022.6.15"
},
"charset-normalizer": {
@ -836,6 +871,7 @@
"sha256:5189b6f22b01957427f35b6a08d9a0bc45b46d3788ef5a92e978433c7a35f8a5",
"sha256:575e708016ff3a5e3681541cb9d79312c416835686d054a23accb873b254f413"
],
"markers": "python_version >= '3.6'",
"version": "==2.1.0"
},
"click": {
@ -843,9 +879,13 @@
"sha256:7682dc8afb30297001674575ea00d1814d808d6a36af415a82bd481d37ba7b8e",
"sha256:bb4d8133cb15a609f44e8213d9b391b0809795062913b383c62be0ee95b1db48"
],
"markers": "python_version >= '3.7'",
"version": "==8.1.3"
},
"coverage": {
"extras": [
"toml"
],
"hashes": [
"sha256:0895ea6e6f7f9939166cc835df8fa4599e2d9b759b02d1521b574e13b859ac32",
"sha256:0f211df2cba951ffcae210ee00e54921ab42e2b64e0bf2c0befc977377fb09b7",
@ -889,6 +929,7 @@
"sha256:f23876b018dfa5d3e98e96f5644b109090f16a4acb22064e0f06933663005d39",
"sha256:f7bd0ffbcd03dc39490a1f40b2669cc414fae0c4e16b77bb26806a4d0b7d1452"
],
"markers": "python_version >= '3.7'",
"version": "==6.4.2"
},
"idna": {
@ -896,6 +937,7 @@
"sha256:84d9dd047ffa80596e0f246e2eab0b391788b0503584e8945f2368256d2735ff",
"sha256:9d643ff0a55b762d5cdb124b8eaa99c66322e2157b69160bc32796e824360e6d"
],
"markers": "python_version >= '3.5'",
"version": "==3.3"
},
"iniconfig": {
@ -954,6 +996,7 @@
"sha256:dd47c42927d89ab911e606518907cc2d3a1f38bbd026385970643f9c5b8ecfeb",
"sha256:ef103e05f519cdc783ae24ea4e2e0f508a9c99b2d4969652eed6a2e1ea5bd522"
],
"markers": "python_version >= '3.6'",
"version": "==21.3"
},
"pathspec": {
@ -968,6 +1011,7 @@
"sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159",
"sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"
],
"markers": "python_version >= '3.6'",
"version": "==1.0.0"
},
"py": {
@ -975,6 +1019,7 @@
"sha256:51c75c4126074b472f746a24399ad32f6053d1b34b68d2fa41e558e6f4a98719",
"sha256:607c53218732647dff4acdfcd50cb62615cedf612e72d1724fb1a0cc6405b378"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==1.11.0"
},
"pyparsing": {
@ -982,6 +1027,7 @@
"sha256:2b020ecf7d21b687f219b71ecad3631f644a47f01403fa1d1036b0c6416d70fb",
"sha256:5026bae9a10eeaefb61dab2f09052b9f4307d44aee4eda64b309723d8d206bbc"
],
"markers": "python_full_version >= '3.6.8'",
"version": "==3.0.9"
},
"pytest": {
@ -1010,82 +1056,83 @@
},
"regex": {
"hashes": [
"sha256:00d2e907d3c5e4f85197c8d2263a9cc2d34bf234a9c6236ae42a3fb0bc09b759",
"sha256:0186edcda692c38381db8ac257c2d023fd2e08818d45dc5bee4ed84212045f51",
"sha256:06c509bd7dcb7966bdb03974457d548e54d8327bad5b0c917e87248edc43e2eb",
"sha256:0a3f3f45c5902eb4d90266002ccb035531ae9b9278f6d5e8028247c34d192099",
"sha256:0c1821146b429e6fdbd13ea10f26765e48d5284bc79749468cfbfe3ceb929f0d",
"sha256:0d93167b7d7731fa9ff9fdc1bae84ec9c7133b01a35f8cc04e926d48da6ce1f7",
"sha256:0fd8c3635fa03ef79d07c7b3ed693b3f3930ccb52c0c51761c3296a7525b135c",
"sha256:119091c675e6ad19da8770f89aa1d52f4ad2a2018d631956f3e90c45882df880",
"sha256:121981ba84309dabefd5e1debd49be6d51624e54b4d44bfc184cd8d555ff1df1",
"sha256:1244e9b9b4b81c9c34e8a84273ffaeebdc78abc98a5b02dcdd49845eb3c63bd7",
"sha256:12e1404dfb4e928d3273a10e3468877fe84bdcd3c50b655a2c9613cfc5d9fe63",
"sha256:13d74951c14708f00700bb29475129ecbc40e01b4029c62ee7bfe9d1f59f31ce",
"sha256:162a5939a6fdf48658d3565eeff35acdd207e07367bf5caaff3d9ea7cb77d7a9",
"sha256:1703490c5b850fa9cef1af00c58966756042e6ca22f4fb5bb857345cd535834f",
"sha256:18e6203cfd81df42a987175aaeed7ba46bcb42130cd81763e2d5edcff0006d5d",
"sha256:192c2784833aea6fc7b004730bf1b91b8b8c6b998b30271aaf3bd8adfef20a96",
"sha256:1948d3ceac5b2d55bc93159c1e0679a256a87a54c735be5cef4543a9e692dbb9",
"sha256:206a327e628bc529d64b21ff79a5e2564f5aec7dc7abcd4b2e8a4b271ec10550",
"sha256:2e5db20412f0db8798ff72473d16da5f13ec808e975b49188badb2462f529fa9",
"sha256:2f94b0befc811fe74a972b1739fffbf74c0dc1a91102aca8e324aa4f2c6991bd",
"sha256:303676797c4c7978726e74eb8255d68f7125a3a29da71ff453448f2117290e9a",
"sha256:34ae4f35db30caa4caf85c55069fcb7a05966a3a5ba6e9e1dab5477d84fbb08a",
"sha256:3c6df8be7d1dd35a0d9a200fbc29f888c4452c8882d284f87608046152e049e6",
"sha256:402fa998c5988d11ed34585eb65740dcebd0fd11844d12eb0a6b4be178eb9c64",
"sha256:40a28759d345c0bb1f5b0ac74ac04f5d48136019522c95c0ec4b07786f67ce20",
"sha256:414ae507ba88264444baf771fec43ce0adcd4c5dbb304d3e0716f3f4d4499d2e",
"sha256:42da079e31ae9818ffa7a35cdd16ab7104e3f7eca9c0958040aede827b2e55c6",
"sha256:473a7d21932ce7c314953b33c32e63df690181860edcdf14bba1278cdf71b07f",
"sha256:49fcb45931a693b0e901972c5e077ea2cf30ec39da699645c43cb8b1542c6e14",
"sha256:4c5913cb9769038bd03e42318955c2f15a688384a6a0b807bcfc8271603d9277",
"sha256:4cfeb71095c8d8380a5df5a38ff94d27a3f483717e509130a822b4d6400b7991",
"sha256:4dc74f0171eede67d79a79c06eca0fe5b7b280dbb8c27ad1fae4ced2ad66268f",
"sha256:5b1cffff2d9f832288fe516021cb81c95c57c0067b13a82f1d2daabdbc2f4270",
"sha256:601c99ac775b6c89699a48976f3dbb000b47d3ca59362c8abc9582e6d0780d91",
"sha256:667a06bb8d72b6da3d9cf38dac4ba969688868ed2279a692e993d2c0e1c30aba",
"sha256:673549a0136c7893f567ed71ab5225ed3701c79b17c0a7faee846c645fc24010",
"sha256:67bd3bdd27db7a6460384869dd4b9c54267d805b67d70b20495bb5767f8e051c",
"sha256:727edff0a4eaff3b6d26cbb50216feac9055aba7e6290eec23c061c2fe2fab55",
"sha256:782627a1cb8fbb1c78d8e841f5b71c2c683086c038f975bebdac7cce7678a96f",
"sha256:7d462ba84655abeddae4dfc517fe1afefb5430b3b5acb0a954de12a47aea7183",
"sha256:8ab39aa445d00902c43a1e951871bedc7f18d095a21eccba153d594faac34aea",
"sha256:8e2075ed4ea2e231e2e98b16cfa5dae87e9a6045a71104525e1efc29aa8faa8e",
"sha256:9daeccb2764bf4cc280c40c6411ae176bb0876948e536590a052b3d647254c95",
"sha256:9e4006942334fa954ebd32fa0728718ec870f95f4ba7cda9edc46dd49c294f22",
"sha256:9f1c8fffd4def0b76c0947b8cb261b266e31041785dc2dc2db7569407a2f54fe",
"sha256:a00cd58a30a1041c193777cb1bc090200b05ff4b073d5935738afd1023e63069",
"sha256:a0220a7a16fd4bfc700661f920510defd31ef7830ce992d5cc51777aa8ccd724",
"sha256:a048f91823862270905cb22ef88038b08aac852ce48e0ecc4b4bf1b895ec37d9",
"sha256:a3c47c71fde0c5d584402e67546c81af9951540f1f622d821e9c20761556473a",
"sha256:a6d9ea727fd1233ee746bf44dd37e7d4320b3ed8ff09e73d7638c969b28d280f",
"sha256:ab0709daedc1099bbd4371ae17eeedd4efc1cf70fcdcfe5de1374a0944b61f80",
"sha256:ab1cb36b411f16da6e057ef8e6657dd0af36f59a667f07e0b4b617e44e53d7b2",
"sha256:ae1c5b435d44aa91d48cc710f20c3485e0584a3ad3565d5ae031d61a35f674f4",
"sha256:b279b9bb401af41130fd2a09427105100bc8c624ed45da1c81c1c0d0aa639734",
"sha256:b72a4ec79a15f6066d14ae1c472b743af4b4ecee14420e8d6e4a336b49b8f21c",
"sha256:c2cd93725911c0159d597b90c96151070ef7e0e67604637e2f2abe06c34bf079",
"sha256:c7c5f914b0eb5242c09f91058b80295525897e873b522575ab235b48db125597",
"sha256:d07d849c9e2eca80adb85d3567302a47195a603ad7b1f0a07508e253c041f954",
"sha256:d2672d68cf6c8452b6758fc3cd2d8feac966d511eed79a68182a5297b473af9c",
"sha256:d35bbcbf70d14f724e7489746cf68efe122796578addd98f91428e144d0ad266",
"sha256:d40b4447784dbe0896a6d10a178f6724598161f942c56f5a60dc0ef7fe63f7a1",
"sha256:d561dcb0fb0ab858291837d51330696a45fd3ba6912a332a4ee130e5484b9e47",
"sha256:d7f5ccfff648093152cadf6d886c7bd922047532f72024c953a79c7553aac2fe",
"sha256:dce6b2ad817e3eb107f8704782b091b0631dd3adf47f14bdc086165d05b528b0",
"sha256:e1fdda3ec7e9785065b67941693995cab95b54023a21db9bf39e54cc7b2c3526",
"sha256:e2a262ec85c595fc8e1f3162cafc654d2219125c00ea3a190c173cea70d2cc7a",
"sha256:e2fc1e3928c1189c0382c547c17717c6d9f425fffe619ef94270fe4c6c8be0a6",
"sha256:ea27acd97a752cfefa9907da935e583efecb302e6e9866f37565968c8407ad58",
"sha256:ee769a438827e443ed428e66d0aa7131c653ecd86ddc5d4644a81ed1d93af0e7",
"sha256:f32e0d1c7e7b0b9c3cac76f3d278e7ee6b99c95672d2c1c6ea625033431837c0",
"sha256:f355caec5bbce20421dc26e53787b10e32fd0df68db2b795435217210c08d69c",
"sha256:f87e9108bb532f8a1fc6bf7e69b930a35c7b0267b8fef0a3ede0bcb4c5aaa531",
"sha256:f8a2fd2f62a77536e4e3193303bec380df40d99e253b1c8f9b6eafa07eaeff67",
"sha256:fbdf4fc6adf38fab1091c579ece3fe9f493bd0f1cfc3d2c76d2e52461ca4f8a9"
"sha256:045682b6457f0224deb10c9720b8008dc798b1ad4331de9302fd4b615211e5a5",
"sha256:04e3869fc6fc24b75d38e7547797bb0a82d6cccd49e8ce6ae21a0b87aeb9fac7",
"sha256:073bd76a1f03e05a6ca0df705b6117f75b10c340af068b55becb1334fc6426c2",
"sha256:0aa48740a1385cb668ffd828a7e2c8078ce29c72d64651c8226bd2b7cb5dba0c",
"sha256:0e380ebd841201f980ab022d07033be12c9438a9b2e0f60324c9e3ba31790918",
"sha256:0f9b8ef2e46d627b2a85d3f4fe433ead283c420adcf9461906c3db10766dd3b1",
"sha256:10d3a5dda21a125cfdc31e45ae6ce6bdd1e45cb194199801248d6580be8dc337",
"sha256:11965ae779a0ccfb6d17996d531e2f522124e04d98cc65742b96bf8f50758ab9",
"sha256:1c61175730596266015c4e005c65cbfeeb1ef019ccd024870169c6593a26bdb0",
"sha256:1d1d79a87a33fbd6573e30eb53969a4190035894c4390a0787fb823e9e86b72f",
"sha256:1f0bf228c948f543876f4fb310322a4ff7e398667dd58aeb4815dc9e30bf867e",
"sha256:2026a1c108752e48577f9720076bf6e31a60aaf0c3000fffad4e2527fdffbe95",
"sha256:204705b7ec16267d39870a19e72e832b12739dc48a26d923a9cb94043660d50f",
"sha256:248b16534d1ef8f10a72cda0f97b3dfa25b3d9123a7e726d1594cb07a541bba0",
"sha256:27b5011449213dfd880e592ea6d311d00739e87d9512bad507ee18c9c92a20ac",
"sha256:2880d21e9507869ab1636e50461afb9ffb08797f1cb76f70d3ad52e7dd13a335",
"sha256:2d3f9fc885ecd8b0eb248d0e190aa7264b977cc23b6da7c08444065170c57e2e",
"sha256:2d8b50ae3cbaaa2e5ed89ed81fc025ec64b1a54c4f34e6bdaad9dc63fc2afa6b",
"sha256:3ff5b2b6a136307a5551e7821d83ab12c46f57c32bf23a27877c9c6bdb55aa61",
"sha256:40b4436466d47271fe3b4df63e55307c91a40cda0875a9ff3b7231a08394b283",
"sha256:435c94d5939a7cf4b0af1cce30d196451bae441ebe64f63d08517ab490ceb385",
"sha256:4c0b7c413d4a8a55d72df18acbeb50276eee19cec7e2f54ed3bddc46bc3b3aeb",
"sha256:4cfe87490d0a801749b42491ef7e968342e5787decbf57d5402fc2c17f7302e3",
"sha256:4f480661cd0809a1177b09581c12c9ceff9ca989e4a0c8c0f10379dffa3b4c4c",
"sha256:53370620db6058dbb464324b053fee8608518d76ff6352b2835d71e2ae8ef293",
"sha256:53eca0cece2ddb592b8dd9746f0b258d0c8a45f5a3ac8eb96833058f64778fca",
"sha256:5751bfe0d939d7110396510a39e48ee928b36b55177207c47766b093886a3945",
"sha256:5d750f99c40a7e994df1cf1295bbb3e873417ca69508664fe9f65db92e46ca40",
"sha256:6019737db5c46a24f307eae5069fced0752e3a22380398bbefbef77b068b9537",
"sha256:605ca47681c7405723a4970d66d13fa3a3a66efa6b8499d7ab7bce1ddb44a36f",
"sha256:69120a8fb1eb932b6e3ededb16448be6444eb952f9350c21dddbef947fea5690",
"sha256:72713de336b8d895f91aad34f5591f33d1d8727bd739af3ae2657411ef6e0739",
"sha256:74077b462a9b255c5fca247484f46b0f25c32676fe4645cb6b5304b2d997357a",
"sha256:74f0067495a842f7cc198b14031a2893d377bed38e19d785f35095082ab5a556",
"sha256:817a0618c149d77e493963cd98851ff49d6ab8bcab247fdbf85bb89a14dca5c3",
"sha256:869a0f6405ec569863e09909617138af575b5e2bc5181184e60f339a4c8a6d7a",
"sha256:86b0cf786efd587c27abd1d07020c555a82275bba3506d916d42aed7a3744967",
"sha256:8cbc407c44003a1cb4aaa2d48cc19b45dde07ba0ae2f541c6750ad18f8c118f5",
"sha256:90e082f262cf858cbcde330999ea5612e12918982033b716d2c5d8b1bc7a01db",
"sha256:95d8f1083ff4546ec14fb46dc41b042d372258f8c319df1e2316d8fe1bd3f085",
"sha256:97211bae1bc51f153764485a54d8d1130196cae33d02285c33732b26c5328b8d",
"sha256:98dbaf6a86991e2b09f4d8a7669b4304755bda519565971dc3b87ee00fd6eab2",
"sha256:9e297ff33172853e9a9e46dbb0c2ebf44fb38ebefce659698df4eb9dfce0a748",
"sha256:9e64492c8105312f080e25e457db70f9b0d02e6ba3c1ea14468087b0e3aa876f",
"sha256:a11241808e59deec8314792bbd8a6f0a8a7a95b742709e134c73a3216dbb26ae",
"sha256:a33c36dcc1760d66f1969d7d3dc8956f45a3d502178053074b8489f67718138f",
"sha256:a4e1e7ba8c58c1f0b828418f9a2635c0f6344bf107308b8fe65f234a13c8462a",
"sha256:a55c4d5e5076cc5ece625dd1f7015c9a0818ba1f9ad9db421b495d7ece088e56",
"sha256:a6f5cc82e1fa380eb6b8040d626df6ba9f492b6886527f53d59838b11e9caaef",
"sha256:a96826b5c9dc68417ddb29843998473f9c2c047911e6fca36a9f81a898087b01",
"sha256:acf6cbcc19d86f44e8a9d3cf1f6946a71dc55c2ec8ae374c547b1eefd83b954f",
"sha256:b4be25d3c640a35671431d8ef8cd522319254074b150147fcacad90c91ea42c2",
"sha256:b5a31abc27f9bda7a455bfa1e1bd623da50e3a343a040084c879d07394a93481",
"sha256:bb812e590e3881a93d4d291270440b3795fa4c0bc1b03ba15fe1cc88d2ea4347",
"sha256:bbd542b4afd2ed5491a480e9b15f4bca13e0170ef1895064fd15741382fdebe0",
"sha256:bf27111f56b762238bd3ce4c5e8ad34167d85dd3c077721a0c093517526a94af",
"sha256:c7a4dc9436b7a55c36daa3959e92d70337c547651ebeda685dd6bb083f0b77ab",
"sha256:c88a1068ac8e5dc579d5104903fa2c488448c1137e580a77d1438d98070c4243",
"sha256:c8cffb5040bf432355cfe51378072f20087609694066ace80710bdba04cf9ce2",
"sha256:c944921b0e77f1923dd89cda65534223ac107e24d71b1dfe174237faa5efd32a",
"sha256:ca2a7233275acf0087ecd15e5fb0eeb722a1f4de453b49bb1443edf2c2f5a997",
"sha256:cf0a3b9744f94693f3ebcca1c259354f0043c19a4ce938f80ad6d1816b8fd8f0",
"sha256:dbe2f16a66f64a00dc9ccc0db7f8b5ff014f409840e03675eb431f03b50ddffd",
"sha256:deb7b067b3b9751c60dc7f6de68476138d550c074a5016ba944cc55863fa86d1",
"sha256:df669bacbda209e9b00928f1d00432b27a16c3e051f9f7e5ea306f9b78bf3e7c",
"sha256:e2dd4ca82c2241be9582d2ae060070f2bccb0c98295b608009d5cc6e6041eaed",
"sha256:e432cf909c53506da4c8308753b2671ee37d2d8d1de8b4b54ab76e91ca7ba0b5",
"sha256:e4e7f1aba3aaf08e11d33fd5c2d8dd8cbf573049474e11256c91e3ba3d5e1642",
"sha256:e51ab7fbfe5ac3002b9aee527bcb164b17fd92f5663ebf2a4e5917dd9d577864",
"sha256:ea00c7f86405d88995e7bab5609e343fdedfe1ffc8191d3b5ed0f8c7f5eb17ec",
"sha256:f7006d7c74e25f8bc592604a5a72ba624f10ebd5c0683ab4d3e940a88ac0098c",
"sha256:f93e3e5acf82812ea92a1ccdcce690aab18c4044dd824f6b959d2b6069d84312",
"sha256:fa8a4bc81b15f49c57ede3fd636786c6619179661acf2430fcc387d75bf28d33",
"sha256:fc44c49f33dd75e58b5ff2a5ac50c96c84b6b209d36b4790c85bca08a3b9017d"
],
"version": "==2022.7.9"
"markers": "python_version >= '3.6'",
"version": "==2022.7.24"
},
"requests": {
"hashes": [
@ -1100,6 +1147,7 @@
"sha256:806143ae5bfb6a3c6e736a764057db0e6a0e05e338b5630894a5f779cabb4f9b",
"sha256:b3bda1d108d5dd99f4a20d24d9c348e91c4db7ab1b749200bded2f839ccbe68f"
],
"markers": "python_version >= '2.6' and python_version not in '3.0, 3.1, 3.2'",
"version": "==0.10.2"
},
"tomli": {
@ -1107,6 +1155,7 @@
"sha256:939de3e7a6161af0c887ef91b7d41a53e7c5a1ca976325f429cb46ea9bc30ecc",
"sha256:de526c12914f0c550d15924c62d72abc48d6fe7364aa87328337a31007fe8a4f"
],
"markers": "python_version >= '3.7'",
"version": "==2.0.1"
},
"typed-ast": {
@ -1136,8 +1185,25 @@
"sha256:ebd9d7f80ccf7a82ac5f88c521115cc55d84e35bf8b446fcd7836eb6b98929a3",
"sha256:ed855bbe3eb3715fca349c80174cfcfd699c2f9de574d40527b8429acae23a66"
],
"markers": "python_version >= '3.6'",
"version": "==1.5.4"
},
"types-mock": {
"hashes": [
"sha256:4535fbb3912b88a247d43cdb41db0c8b2e187138986f6f01a989717e56105848",
"sha256:a849bc2d966063f4946013bf404822ee2b96f77a8dccda4174b70ab61c5293fe"
],
"index": "pypi",
"version": "==4.0.15"
},
"types-protobuf": {
"hashes": [
"sha256:d291388678af91bb045fafa864f142dc4ac22f5d4cdca097c7d8d8a32fa9b3ab",
"sha256:d2b26861b0cb46a3c8669b0df507b7ef72e487da66d61f9f3576aa76ce028a83"
],
"index": "pypi",
"version": "==3.19.22"
},
"typing-extensions": {
"hashes": [
"sha256:25642c956049920a5aa49edcdd6ab1e06d7e5d467fc00e0506c44ac86fbfca02",
@ -1151,6 +1217,7 @@
"sha256:8298d6d56d39be0e3bc13c1c97d133f9b45d797169a0e11cdd0e0489d786f7ec",
"sha256:879ba4d1e89654d9769ce13121e0f94310ea32e8d2f8cf587b77c08bbcdb30d6"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4, 3.5' and python_version < '4'",
"version": "==1.26.10"
}
}

View File

@ -17,7 +17,6 @@ from loguru import logger
import lnbits.settings
from lnbits.core.tasks import register_task_listeners
from .commands import db_migrate, handle_assets
from .core import core_app
from .core.views.generic import core_html_routes
from .helpers import (
@ -93,7 +92,6 @@ def create_app(config_object="lnbits.settings") -> FastAPI:
check_funding_source(app)
register_assets(app)
register_routes(app)
# register_commands(app)
register_async_tasks(app)
register_exception_handlers(app)
@ -146,12 +144,6 @@ def register_routes(app: FastAPI) -> None:
)
def register_commands(app: FastAPI):
"""Register Click commands."""
app.cli.add_command(db_migrate)
app.cli.add_command(handle_assets)
def register_assets(app: FastAPI):
"""Serve each vendored asset separately or a bundle."""

View File

@ -113,7 +113,7 @@ async def create_wallet(
async def update_wallet(
wallet_id: str, new_name: str, conn: Optional[Connection] = None
) -> Optional[Wallet]:
await (conn or db).execute(
return await (conn or db).execute(
"""
UPDATE wallets SET
name = ?

View File

@ -106,6 +106,8 @@ class Payment(BaseModel):
@property
def tag(self) -> Optional[str]:
if self.extra is None:
return ""
return self.extra.get("tag")
@property

View File

@ -109,18 +109,15 @@ async def pay_invoice(
raise ValueError("Amount in invoice is too high.")
# put all parameters that don't change here
PaymentKwargs = TypedDict(
"PaymentKwargs",
{
"wallet_id": str,
"payment_request": str,
"payment_hash": str,
"amount": int,
"memo": str,
"extra": Optional[Dict],
},
)
payment_kwargs: PaymentKwargs = dict(
class PaymentKwargs(TypedDict):
wallet_id: str
payment_request: str
payment_hash: str
amount: int
memo: str
extra: Optional[Dict]
payment_kwargs: PaymentKwargs = PaymentKwargs(
wallet_id=wallet_id,
payment_request=payment_request,
payment_hash=invoice.payment_hash,
@ -272,6 +269,7 @@ async def perform_lnurlauth(
cb = urlparse(callback)
k1 = unhexlify(parse_qs(cb.query)["k1"][0])
key = wallet.wallet.lnurlauth_key(cb.netloc)
def int_to_bytes_suitable_der(x: int) -> bytes:

View File

@ -55,7 +55,7 @@ async def dispatch_webhook(payment: Payment):
data = payment.dict()
try:
logger.debug("sending webhook", payment.webhook)
r = await client.post(payment.webhook, json=data, timeout=40)
r = await client.post(payment.webhook, json=data, timeout=40) # type: ignore
await mark_webhook_sent(payment, r.status_code)
except (httpx.ConnectError, httpx.RequestError):
await mark_webhook_sent(payment, -1)

View File

@ -3,7 +3,7 @@ import hashlib
import json
from binascii import unhexlify
from http import HTTPStatus
from typing import Dict, List, Optional, Union
from typing import Dict, List, Optional, Tuple, Union
from urllib.parse import ParseResult, parse_qs, urlencode, urlparse, urlunparse
import httpx
@ -185,7 +185,7 @@ async def api_payments_create_invoice(data: CreateInvoiceData, wallet: Wallet):
assert (
data.lnurl_balance_check is not None
), "lnurl_balance_check is required"
save_balance_check(wallet.id, data.lnurl_balance_check)
await save_balance_check(wallet.id, data.lnurl_balance_check)
async with httpx.AsyncClient() as client:
try:
@ -248,7 +248,7 @@ async def api_payments_pay_invoice(bolt11: str, wallet: Wallet):
)
async def api_payments_create(
wallet: WalletTypeInfo = Depends(require_invoice_key),
invoiceData: CreateInvoiceData = Body(...),
invoiceData: CreateInvoiceData = Body(...), # type: ignore
):
if invoiceData.out is True and wallet.wallet_type == 0:
if not invoiceData.bolt11:
@ -291,7 +291,7 @@ async def api_payments_pay_lnurl(
timeout=40,
)
if r.is_error:
raise httpx.ConnectError
raise httpx.ConnectError("LNURL callback connection error")
except (httpx.ConnectError, httpx.RequestError):
raise HTTPException(
status_code=HTTPStatus.BAD_REQUEST,
@ -354,7 +354,7 @@ async def subscribe(request: Request, wallet: Wallet):
logger.debug("adding sse listener", payment_queue)
api_invoice_listeners.append(payment_queue)
send_queue: asyncio.Queue[tuple[str, Payment]] = asyncio.Queue(0)
send_queue: asyncio.Queue[Tuple[str, Payment]] = asyncio.Queue(0)
async def payment_received() -> None:
while True:
@ -393,16 +393,13 @@ async def api_payments_sse(
async def api_payment(payment_hash, X_Api_Key: Optional[str] = Header(None)):
# We use X_Api_Key here because we want this call to work with and without keys
# If a valid key is given, we also return the field "details", otherwise not
wallet = None
try:
if X_Api_Key.extra:
logger.warning("No key")
except:
wallet = await get_wallet_for_key(X_Api_Key)
wallet = await get_wallet_for_key(X_Api_Key) if type(X_Api_Key) == str else None
# we have to specify the wallet id here, because postgres and sqlite return internal payments in different order
# and get_standalone_payment otherwise just fetches the first one, causing unpredictable results
payment = await get_standalone_payment(
payment_hash, wallet_id=wallet.id if wallet else None
) # we have to specify the wallet id here, because postgres and sqlite return internal payments in different order
# and get_standalone_payment otherwise just fetches the first one, causing unpredictable results
)
if payment is None:
raise HTTPException(
status_code=HTTPStatus.NOT_FOUND, detail="Payment does not exist."
@ -612,8 +609,8 @@ class ConversionData(BaseModel):
async def api_fiat_as_sats(data: ConversionData):
output = {}
if data.from_ == "sat":
output["sats"] = int(data.amount)
output["BTC"] = data.amount / 100000000
output["sats"] = int(data.amount)
for currency in data.to.split(","):
output[currency.strip().upper()] = await satoshis_amount_as_fiat(
data.amount, currency.strip()

View File

@ -55,9 +55,9 @@ async def home(request: Request, lightning: str = None):
)
async def extensions(
request: Request,
user: User = Depends(check_user_exists),
enable: str = Query(None),
disable: str = Query(None),
user: User = Depends(check_user_exists), # type: ignore
enable: str = Query(None), # type: ignore
disable: str = Query(None), # type: ignore
):
extension_to_enable = enable
extension_to_disable = disable
@ -88,7 +88,7 @@ async def extensions(
# Update user as his extensions have been updated
if extension_to_enable or extension_to_disable:
user = await get_user(user.id)
user = await get_user(user.id) # type: ignore
return template_renderer().TemplateResponse(
"core/extensions.html", {"request": request, "user": user.dict()}
@ -109,10 +109,10 @@ nothing: create everything<br>
""",
)
async def wallet(
request: Request = Query(None),
nme: Optional[str] = Query(None),
usr: Optional[UUID4] = Query(None),
wal: Optional[UUID4] = Query(None),
request: Request = Query(None), # type: ignore
nme: Optional[str] = Query(None), # type: ignore
usr: Optional[UUID4] = Query(None), # type: ignore
wal: Optional[UUID4] = Query(None), # type: ignore
):
user_id = usr.hex if usr else None
wallet_id = wal.hex if wal else None
@ -121,7 +121,7 @@ async def wallet(
if not user_id:
user = await get_user((await create_account()).id)
logger.info(f"Create user {user.id}")
logger.info(f"Create user {user.id}") # type: ignore
else:
user = await get_user(user_id)
if not user:
@ -135,22 +135,22 @@ async def wallet(
if LNBITS_ADMIN_USERS and user_id in LNBITS_ADMIN_USERS:
user.admin = True
if not wallet_id:
if user.wallets and not wallet_name:
wallet = user.wallets[0]
if user.wallets and not wallet_name: # type: ignore
wallet = user.wallets[0] # type: ignore
else:
wallet = await create_wallet(user_id=user.id, wallet_name=wallet_name)
wallet = await create_wallet(user_id=user.id, wallet_name=wallet_name) # type: ignore
logger.info(
f"Created new wallet {wallet_name if wallet_name else '(no name)'} for user {user.id}"
f"Created new wallet {wallet_name if wallet_name else '(no name)'} for user {user.id}" # type: ignore
)
return RedirectResponse(
f"/wallet?usr={user.id}&wal={wallet.id}",
f"/wallet?usr={user.id}&wal={wallet.id}", # type: ignore
status_code=status.HTTP_307_TEMPORARY_REDIRECT,
)
logger.debug(f"Access wallet {wallet_name}{'of user '+ user.id if user else ''}")
wallet = user.get_wallet(wallet_id)
if not wallet:
userwallet = user.get_wallet(wallet_id) # type: ignore
if not userwallet:
return template_renderer().TemplateResponse(
"error.html", {"request": request, "err": "Wallet not found"}
)
@ -159,10 +159,10 @@ async def wallet(
"core/wallet.html",
{
"request": request,
"user": user.dict(),
"wallet": wallet.dict(),
"user": user.dict(), # type: ignore
"wallet": userwallet.dict(),
"service_fee": service_fee,
"web_manifest": f"/manifest/{user.id}.webmanifest",
"web_manifest": f"/manifest/{user.id}.webmanifest", # type: ignore
},
)
@ -216,20 +216,20 @@ async def lnurl_full_withdraw_callback(request: Request):
@core_html_routes.get("/deletewallet", response_class=RedirectResponse)
async def deletewallet(request: Request, wal: str = Query(...), usr: str = Query(...)):
async def deletewallet(request: Request, wal: str = Query(...), usr: str = Query(...)): # type: ignore
user = await get_user(usr)
user_wallet_ids = [u.id for u in user.wallets]
user_wallet_ids = [u.id for u in user.wallets] # type: ignore
if wal not in user_wallet_ids:
raise HTTPException(HTTPStatus.FORBIDDEN, "Not your wallet.")
else:
await delete_wallet(user_id=user.id, wallet_id=wal)
await delete_wallet(user_id=user.id, wallet_id=wal) # type: ignore
user_wallet_ids.remove(wal)
logger.debug("Deleted wallet {wal} of user {user.id}")
if user_wallet_ids:
return RedirectResponse(
url_for("/wallet", usr=user.id, wal=user_wallet_ids[0]),
url_for("/wallet", usr=user.id, wal=user_wallet_ids[0]), # type: ignore
status_code=status.HTTP_307_TEMPORARY_REDIRECT,
)
@ -242,7 +242,7 @@ async def deletewallet(request: Request, wal: str = Query(...), usr: str = Query
async def lnurl_balance_notify(request: Request, service: str):
bc = await get_balance_check(request.query_params.get("wal"), service)
if bc:
redeem_lnurl_withdraw(bc.wallet, bc.url)
await redeem_lnurl_withdraw(bc.wallet, bc.url)
@core_html_routes.get(
@ -252,7 +252,7 @@ async def lnurlwallet(request: Request):
async with db.connect() as conn:
account = await create_account(conn=conn)
user = await get_user(account.id, conn=conn)
wallet = await create_wallet(user_id=user.id, conn=conn)
wallet = await create_wallet(user_id=user.id, conn=conn) # type: ignore
asyncio.create_task(
redeem_lnurl_withdraw(
@ -265,7 +265,7 @@ async def lnurlwallet(request: Request):
)
return RedirectResponse(
f"/wallet?usr={user.id}&wal={wallet.id}",
f"/wallet?usr={user.id}&wal={wallet.id}", # type: ignore
status_code=status.HTTP_307_TEMPORARY_REDIRECT,
)

View File

@ -1,4 +1,5 @@
from http import HTTPStatus
from typing import Union
from cerberus import Validator # type: ignore
from fastapi import status
@ -29,20 +30,21 @@ class KeyChecker(SecurityBase):
self._key_type = "invoice"
self._api_key = api_key
if api_key:
self.model: APIKey = APIKey(
key = APIKey(
**{"in": APIKeyIn.query},
name="X-API-KEY",
description="Wallet API Key - QUERY",
)
else:
self.model: APIKey = APIKey(
key = APIKey(
**{"in": APIKeyIn.header},
name="X-API-KEY",
description="Wallet API Key - HEADER",
)
self.wallet = None
self.wallet = None # type: ignore
self.model: APIKey = key
async def __call__(self, request: Request) -> Wallet:
async def __call__(self, request: Request):
try:
key_value = (
self._api_key
@ -52,7 +54,7 @@ class KeyChecker(SecurityBase):
# FIXME: Find another way to validate the key. A fetch from DB should be avoided here.
# Also, we should not return the wallet here - thats silly.
# Possibly store it in a Redis DB
self.wallet = await get_wallet_for_key(key_value, self._key_type)
self.wallet = await get_wallet_for_key(key_value, self._key_type) # type: ignore
if not self.wallet:
raise HTTPException(
status_code=HTTPStatus.UNAUTHORIZED,
@ -120,8 +122,8 @@ api_key_query = APIKeyQuery(
async def get_key_type(
r: Request,
api_key_header: str = Security(api_key_header),
api_key_query: str = Security(api_key_query),
api_key_header: str = Security(api_key_header), # type: ignore
api_key_query: str = Security(api_key_query), # type: ignore
) -> WalletTypeInfo:
# 0: admin
# 1: invoice
@ -134,9 +136,9 @@ async def get_key_type(
token = api_key_header if api_key_header else api_key_query
try:
checker = WalletAdminKeyChecker(api_key=token)
await checker.__call__(r)
wallet = WalletTypeInfo(0, checker.wallet)
admin_checker = WalletAdminKeyChecker(api_key=token)
await admin_checker.__call__(r)
wallet = WalletTypeInfo(0, admin_checker.wallet) # type: ignore
if (LNBITS_ADMIN_USERS and wallet.wallet.user not in LNBITS_ADMIN_USERS) and (
LNBITS_ADMIN_EXTENSIONS and pathname in LNBITS_ADMIN_EXTENSIONS
):
@ -153,9 +155,9 @@ async def get_key_type(
raise
try:
checker = WalletInvoiceKeyChecker(api_key=token)
await checker.__call__(r)
wallet = WalletTypeInfo(1, checker.wallet)
invoice_checker = WalletInvoiceKeyChecker(api_key=token)
await invoice_checker.__call__(r)
wallet = WalletTypeInfo(1, invoice_checker.wallet) # type: ignore
if (LNBITS_ADMIN_USERS and wallet.wallet.user not in LNBITS_ADMIN_USERS) and (
LNBITS_ADMIN_EXTENSIONS and pathname in LNBITS_ADMIN_EXTENSIONS
):
@ -167,15 +169,16 @@ async def get_key_type(
if e.status_code == HTTPStatus.BAD_REQUEST:
raise
if e.status_code == HTTPStatus.UNAUTHORIZED:
return WalletTypeInfo(2, None)
return WalletTypeInfo(2, None) # type: ignore
except:
raise
return wallet
async def require_admin_key(
r: Request,
api_key_header: str = Security(api_key_header),
api_key_query: str = Security(api_key_query),
api_key_header: str = Security(api_key_header), # type: ignore
api_key_query: str = Security(api_key_query), # type: ignore
):
token = api_key_header if api_key_header else api_key_query
@ -193,8 +196,8 @@ async def require_admin_key(
async def require_invoice_key(
r: Request,
api_key_header: str = Security(api_key_header),
api_key_query: str = Security(api_key_query),
api_key_header: str = Security(api_key_header), # type: ignore
api_key_query: str = Security(api_key_query), # type: ignore
):
token = api_key_header if api_key_header else api_key_query

View File

@ -133,7 +133,8 @@ async def api_ticket_send_ticket(event_id, payment_hash, data: CreateTicket):
if not ticket:
raise HTTPException(
status_code=HTTPStatus.NOT_FOUND, detail=f"Event could not be fetched."
status_code=HTTPStatus.NOT_FOUND,
detail=f"Event could not be fetched.",
)
return {"paid": True, "ticket_id": ticket.id}

View File

@ -4,12 +4,7 @@
label="API info"
:content-inset-level="0.5"
>
<q-btn
flat
label="Swagger API"
type="a"
href="../docs#/lnurlpayout"
></q-btn>
<q-btn flat label="Swagger API" type="a" href="../docs#/lnurlpayout"></q-btn>
<q-expansion-item group="api" dense expand-separator label="List lnurlpayout">
<q-card>
<q-card-section>
@ -38,7 +33,6 @@
expand-separator
label="Create a lnurlpayout"
>
<q-card>
<q-card-section>
<code

View File

@ -34,7 +34,7 @@ class ExtensionManager:
@property
def extensions(self) -> List[Extension]:
output = []
output: List[Extension] = []
if "all" in self._disabled:
return output

View File

@ -66,7 +66,7 @@ async def webhook_handler():
raise HTTPException(status_code=HTTPStatus.NO_CONTENT)
internal_invoice_queue = asyncio.Queue(0)
internal_invoice_queue: asyncio.Queue = asyncio.Queue(0)
async def internal_invoice_listener():

View File

@ -1,5 +1,5 @@
import asyncio
from typing import Callable, NamedTuple
from typing import Callable, List, NamedTuple
import httpx
from loguru import logger
@ -227,10 +227,10 @@ async def btc_price(currency: str) -> float:
"TO": currency.upper(),
"to": currency.lower(),
}
rates = []
tasks = []
rates: List[float] = []
tasks: List[asyncio.Task] = []
send_channel = asyncio.Queue()
send_channel: asyncio.Queue = asyncio.Queue()
async def controller():
failures = 0

View File

@ -7,7 +7,10 @@ from typing import AsyncGenerator, Dict, Optional
import httpx
from loguru import logger
from websockets import connect
# TODO: https://github.com/lnbits/lnbits-legend/issues/764
# mypy https://github.com/aaugustin/websockets/issues/940
from websockets import connect # type: ignore
from websockets.exceptions import (
ConnectionClosed,
ConnectionClosedError,

View File

@ -28,7 +28,7 @@ class FakeWallet(Wallet):
logger.info(
"FakeWallet funding source is for using LNbits as a centralised, stand-alone payment system with brrrrrr."
)
return StatusResponse(None, float("inf"))
return StatusResponse(None, 1000000000)
async def create_invoice(
self,
@ -82,7 +82,7 @@ class FakeWallet(Wallet):
invoice = decode(bolt11)
if (
hasattr(invoice, "checking_id")
and invoice.checking_id[6:] == data["privkey"][:6]
and invoice.checking_id[6:] == data["privkey"][:6] # type: ignore
):
return PaymentResponse(True, invoice.payment_hash, 0)
else:
@ -97,7 +97,7 @@ class FakeWallet(Wallet):
return PaymentStatus(None)
async def paid_invoices_stream(self) -> AsyncGenerator[str, None]:
self.queue = asyncio.Queue(0)
self.queue: asyncio.Queue = asyncio.Queue(0)
while True:
value = await self.queue.get()
yield value

View File

@ -119,7 +119,7 @@ class LNPayWallet(Wallet):
return PaymentStatus(statuses[r.json()["settled"]])
async def paid_invoices_stream(self) -> AsyncGenerator[str, None]:
self.queue = asyncio.Queue(0)
self.queue: asyncio.Queue = asyncio.Queue(0)
while True:
value = await self.queue.get()
yield value

View File

@ -73,10 +73,10 @@ class AESCipher(object):
final_key += key
return final_key[:output]
def decrypt(self, encrypted: str) -> str:
def decrypt(self, encrypted: str) -> str: # type: ignore
"""Decrypts a string using AES-256-CBC."""
passphrase = self.passphrase
encrypted = base64.b64decode(encrypted)
encrypted = base64.b64decode(encrypted) # type: ignore
assert encrypted[0:8] == b"Salted__"
salt = encrypted[8:16]
key_iv = self.bytes_to_key(passphrase.encode(), salt, 32 + 16)
@ -84,7 +84,7 @@ class AESCipher(object):
iv = key_iv[32:]
aes = AES.new(key, AES.MODE_CBC, iv)
try:
return self.unpad(aes.decrypt(encrypted[16:])).decode()
return self.unpad(aes.decrypt(encrypted[16:])).decode() # type: ignore
except UnicodeDecodeError:
raise ValueError("Wrong passphrase")

View File

@ -127,7 +127,7 @@ class OpenNodeWallet(Wallet):
return PaymentStatus(statuses[r.json()["data"]["status"]])
async def paid_invoices_stream(self) -> AsyncGenerator[str, None]:
self.queue = asyncio.Queue(0)
self.queue: asyncio.Queue = asyncio.Queue(0)
while True:
value = await self.queue.get()
yield value

View File

@ -1,7 +1,8 @@
[mypy]
ignore_missing_imports = True
exclude = lnbits/wallets/lnd_grpc_files/
exclude = lnbits/extensions/
exclude = (?x)(
^lnbits/extensions.
| ^lnbits/wallets/lnd_grpc_files.
)
[mypy-lnbits.wallets.lnd_grpc_files.*]
follow_imports = skip

1
result Symbolic link
View File

@ -0,0 +1 @@
/nix/store/ds9c48q7hnkdmpzy3aq14kc1x9wrrszd-python3.9-lnbits-0.1.0

View File

@ -1,6 +1,7 @@
import pytest
import pytest_asyncio
from lnbits.core.crud import get_wallet
from lnbits.core.views.api import api_payment
from ...helpers import get_random_invoice_data
@ -155,3 +156,26 @@ async def test_decode_invoice(client, invoice):
)
assert response.status_code < 300
assert response.json()["payment_hash"] == invoice["payment_hash"]
# check api_payment() internal function call (NOT API): payment status
@pytest.mark.asyncio
async def test_api_payment_without_key(invoice):
# check the payment status
response = await api_payment(invoice["payment_hash"])
assert type(response) == dict
assert response["paid"] == True
# no key, that's why no "details"
assert "details" not in response
# check api_payment() internal function call (NOT API): payment status
@pytest.mark.asyncio
async def test_api_payment_with_key(invoice, inkey_headers_from):
# check the payment status
response = await api_payment(
invoice["payment_hash"], inkey_headers_from["X-Api-Key"]
)
assert type(response) == dict
assert response["paid"] == True
assert "details" in response