Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pre commit #2

Merged
merged 8 commits into from
Jun 3, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .flake8
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
[flake8]
max-line-length = 120
max-complexity = 10
ignore = E203, E266, E501, W503, E231
select = B,C,E,F,W,T4,B9
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
.vscode/
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
Expand Down
26 changes: 26 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
default_language_version:
python: python3
repos:
- repo: https://github.com/psf/black
rev: 20.8b1
hooks:
- id: black
- repo: https://gitlab.com/pycqa/flake8
rev: 3.8.4
hooks:
- id: flake8
additional_dependencies: ["flake8-bugbear"]
- repo: https://github.com/PyCQA/bandit
rev: 1.7.0
hooks:
- id: bandit
args: ["-ll"]
files: .py$
- repo: https://github.com/PyCQA/isort
rev: 5.7.0
hooks:
- id: isort
- repo: https://github.com/pre-commit/mirrors-mypy
rev: v0.800
hooks:
- id: mypy
3 changes: 0 additions & 3 deletions .vscode/settings.json

This file was deleted.

27 changes: 24 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
# lnbitsbot

starter template for running bots based off of lnbits.com or your own install.
To set up your own install fast see: https://www.youtube.com/watch?v=AzIPVmCIVAw
starter template for running bots based off of lnbits.com or your own install.
To set up your own install fast see: https://www.youtube.com/watch?v=AzIPVmCIVAw

Just my quick and dirty outline using lnbits as the backend for a python TG bot
that can:
that can:

- create a wallet on lnbits tied to a TG username
- TG users can send links to nonTG users
Expand All @@ -14,3 +14,24 @@ that can:
- instructions with easy on ramp for users who don't hold sats or bitcoin
- /tx, /log, /lnurl
- Add throttle tx size based on node top capacity

Getting Started

```
git clone https://github.com/lightningames/lnbitsbot
cd lnbitsbot
python -m venv venv
source venv/bin/activate
pip install -r requirements.txt
pip install -e .
```

Check linting and formatting
`pre-commit run -a`

Run Tests

```
TBD
TBD
```
Empty file removed __init__.py
Empty file.
41 changes: 18 additions & 23 deletions config.py
Original file line number Diff line number Diff line change
@@ -1,35 +1,32 @@
from yaml import safe_load
import os

from yaml import safe_load


class Config:
def __init__(self,
config_file: str = None,
in_key: str = None,
admin_key: str = None,
lnbits_url: str = None):

def __init__(self, config_file: str = "", in_key: str = None, admin_key: str = None, lnbits_url: str = None):

self._config_file = config_file
self._in_key = in_key
self._lnbits_url = lnbits_url
self._admin_key = admin_key

try:
if in_key or admin_key or lnbits_url is None:
path = os.getcwd()
config_file = path + '/config.yml'
path = os.getcwd()
config_file = path + "/config.yml"
print(config_file)
with open(config_file, 'rb') as f:

with open(config_file, "rb") as f:
cfile = safe_load(f)
f.close()
self._in_key = cfile['in_key']
self._lnbits_url = cfile['lnbits_url']
self._admin_key = cfile['admin_key']

self._in_key = cfile["in_key"]
self._lnbits_url = cfile["lnbits_url"]
self._admin_key = cfile["admin_key"]
except Exception as e:
print(e)


@property
def in_key(self):
return self._in_key
Expand All @@ -41,22 +38,20 @@ def admin_key(self):
@property
def lnbits_url(self):
return self._lnbits_url

def headers(self):
data = {"X-Api-Key" : self._in_key, "Content-type" : "application/json"}
data = {"X-Api-Key": self._in_key, "Content-type": "application/json"}
return data

def admin_headers(self):
data = {"X-Api-Key" : self._admin_key, "Content-type" : "application/json"}
data = {"X-Api-Key": self._admin_key, "Content-type": "application/json"}
return data


if __name__ == '__main__':
if __name__ == "__main__":
c = Config()

print(c.in_key)
print(c.lnbits_url)
print(c.headers())
print(c.admin_headers())


13 changes: 13 additions & 0 deletions docs/notes.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
[setup.py](https://stackoverflow.com/a/50194143)

[configparser](https://docs.python.org/3/library/configparser.html)

[awesome setup](https://www.laac.dev/blog/automating-convention-linting-formatting-python/)

[copy pipeline](https://github.com/CoinAlpha/hummingbot/blob/master/.github/workflows/workflow.yml)

[pre-commit hooks](https://github.com/laactech/pre-commit-config-latest)

[mypy config](https://mypy.readthedocs.io/en/stable/config_file.html#confval-disallow_untyped_calls)

[more mypy](https://breadcrumbscollector.tech/mypy-how-to-use-it-in-my-project/)
5 changes: 2 additions & 3 deletions lnbits/dj_livestream.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
'''
"""
Rest API methods for DJ Livestream

- List livestream links
- Update track
- Update fee
- Add track
- Delete a withdraw link
'''

"""
4 changes: 2 additions & 2 deletions lnbits/events.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
'''
"""
Rest API methods for LNbits Events Extension

'''
"""
4 changes: 2 additions & 2 deletions lnbits/lndhub.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
'''
"""
Rest API methods for LNbits LndHub Extension
Integrates with Blue Wallet, Zeus

'''
"""
4 changes: 2 additions & 2 deletions lnbits/lnurl_p.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
'''
"""
Rest API methods for LNbits LNURLp Pay Extension

'''
"""
4 changes: 2 additions & 2 deletions lnbits/lnurl_w.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
'''
"""
Rest API methods for LNbits LNURLw Withdraw Extension

'''
"""
23 changes: 10 additions & 13 deletions lnbits/user_manager.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
from aiohttp.client import ClientSession
import logging
from config import Config
from lnbits.utils import get_url, post_url, delete_url
import json
import logging

from aiohttp.client import ClientSession

from lnbits.utils import delete_url, get_url, post_url

'''
"""
Rest API methods for LNbits User Manager Extension

GET users
Expand All @@ -16,19 +17,17 @@
DELETE user and their wallets
DELETE wallet
POST activate extension
'''
"""

###################################
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s')
logging.getLogger('lnbot').setLevel(level=logging.WARNING)
logging.basicConfig(level=logging.INFO, format="%(asctime)s - %(name)s - %(levelname)s - %(message)s")
logging.getLogger("lnbot").setLevel(level=logging.WARNING)
logger = logging.getLogger(__name__)
###################################


class UserManager:
def __init__(self,
config: Config = None,
session: ClientSession = None):
def __init__(self, config, session: ClientSession = None):
self._config = config
self._lnbits_url = config.lnbits_url
self._headers = config.headers()
Expand Down Expand Up @@ -120,5 +119,3 @@ async def post_activate_ext(self, user_id: str, extension: str, active: int):
except Exception as e:
logger.info(e)
return e


47 changes: 18 additions & 29 deletions lnbits/user_wallet.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
from aiohttp.client import ClientSession
import logging
import json
from config import Config
import logging

from aiohttp.client import ClientSession

from lnbits.utils import get_url, post_url

'''
"""
Rest API methods for LNbits User Wallet
(lnbits page where users can enable extensions)

Expand All @@ -13,25 +14,22 @@
- Pay an invoice (outgoing)
- Check an invoice (incoming or outgoing)

'''
"""
###################################
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s')
logging.getLogger('lnbot').setLevel(level=logging.WARNING)
logging.basicConfig(level=logging.INFO, format="%(asctime)s - %(name)s - %(levelname)s - %(message)s")
logging.getLogger("lnbot").setLevel(level=logging.WARNING)
logger = logging.getLogger(__name__)
###################################


class UserWallet:
def __init__(self,
config: Config=None,
session: ClientSession = None):
def __init__(self, config, session: ClientSession = None):
self._session = session
self._config = config
self._headers = config.headers()
self._admin_headers = config.admin_headers()
self._lnbits_url = config.lnbits_url


async def get_wallet_details(self):
try:
upath = "/api/v1/wallet"
Expand All @@ -52,49 +50,40 @@ async def check_invoice(self, hash: str):
logger.info(e)
return e


async def create_invoice(self, direction: bool, amt: int, memo: str, webhook: str):
'''
curl -X POST https://bits.bitcoin.org.hk/api/v1/payments
"""
curl -X POST https://bits.bitcoin.org.hk/api/v1/payments
-d '{"out": false, "amount": 100, "memo": "poo", "webhook": "http://google.com"}'
-H "X-Api-Key: f7f740104bba47e9ac9bb3fa......." # only needs Invoice/read key
-H "Content-type: application/json"
'''
"""

try:
upath = "/api/v1/payments"
path = self._lnbits_url + upath
body = {"out": direction,
"amount": amt,
"memo": memo,
"webhook": webhook}
body = {"out": direction, "amount": amt, "memo": memo, "webhook": webhook}
j = json.dumps(body)
res = await post_url(self._session, path=path, headers=self._headers, body=j)
return res
except Exception as e:
logger.info(e)
return e


async def pay_invoice(self, direction: bool, bolt11: str):
'''
curl -X POST https://bits.bitcoin.org.hk/api/v1/payments
-d '{"out": true, "bolt11": <string>}'
"""
curl -X POST https://bits.bitcoin.org.hk/api/v1/payments
-d '{"out": true, "bolt11": <string>}'
-H "X-Api-Key: b811bd2580a0431c96d3c4......" # TODO: needs admin key!
-H "Content-type: application/json"
'''
"""
try:
upath = "/api/v1/payments"
path = self._lnbits_url + upath
body = {"out": direction, "bolt11": bolt11}
j = json.dumps(body)
print(f'body: {j}')
print(f"body: {j}")
res = await post_url(self._session, path=path, headers=self._admin_headers, body=j)
return res
except Exception as e:
logger.info(e)
return e




5 changes: 4 additions & 1 deletion lnbits/utils.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,18 @@
# utils
# utils


async def get_url(session, path, headers):
async with session.get(path, headers=headers) as resp:
res = await resp.json()
return res


async def post_url(session, path, headers, body):
async with session.post(path, headers=headers, data=body) as resp:
res = await resp.json()
return res


async def delete_url(session, path, headers):
async with session.delete(path, headers=headers) as resp:
res = await resp.text()
Expand Down
Loading