Browse Source

Improve setup instructions and README

- README cleanups and link to documentation
- Improve dev setup instructions
- Fix js linting errors
- Move local setup instructions to installation docs
- Project link fix, closes #42
- Notes about frontend
- Clarify different LND backends
Login
Dennis Reimann 4 years ago
committed by GitHub
parent
commit
c3281399d2
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 2
      .env.example
  2. 47
      README.md
  3. 33
      docs/devs/installation.md
  4. 2
      lnbits/core/templates/core/index.html
  5. 38
      lnbits/extensions/events/templates/events/_api_docs.html
  6. 23
      lnbits/extensions/events/templates/events/index.html
  7. 37
      lnbits/extensions/lnticket/templates/lnticket/_api_docs.html
  8. 78
      lnbits/extensions/paywall/templates/paywall/_api_docs.html
  9. 17
      lnbits/extensions/paywall/templates/paywall/display.html
  10. 15
      lnbits/extensions/paywall/templates/paywall/index.html
  11. 11
      lnbits/extensions/tpos/templates/tpos/_api_docs.html
  12. 9
      lnbits/extensions/withdraw/templates/withdraw/_api_docs.html
  13. 2
      lnbits/templates/base.html
  14. 12
      package-lock.json
  15. 3
      package.json

2
.env.example

@ -9,7 +9,7 @@ LNBITS_DISABLED_EXTENSIONS="amilk,events"
LNBITS_FORCE_HTTPS=1
LNBITS_SERVICE_FEE="0.0"
# Choose from LNPayWallet, OpenNodeWallet, LntxbotWallet, LndWallet, CLightningWallet, LnbitsWallet
# Choose from LNPayWallet, OpenNodeWallet, LntxbotWallet, LndWallet (gRPC), LndRestWallet, CLightningWallet, LnbitsWallet
LNBITS_BACKEND_WALLET_CLASS=LntxbotWallet
CLIGHTNING_RPC="/home/bob/.lightning/bitcoin/lightning-rpc"

47
README.md

@ -8,9 +8,11 @@ LNbits
![Lightning network wallet](https://i.imgur.com/EHvK6Lq.png)
# LNbits v0.1 BETA, free and open-source lightning-network wallet/accounts system
https://lnbits.com, or run your own LNbits server!
Use [lnbits.com](https://lnbits.com), or run your own LNbits server!
LNbits is a very simple Python server that sits on top of any funding source, and can be used as:
* Accounts system to mitigate the risk of exposing applications to your full balance, via unique API keys for each wallet
* Extendable platform for exploring lightning-network functionality via LNbits extension framework
* Part of a development stack via LNbits API
@ -19,9 +21,11 @@ LNbits is a very simple Python server that sits on top of any funding source, an
The wallet can run on top of any lightning-network funding source, currently there is support for LND, CLightning, Lntxbot, LNpay, OpenNode, with more being added regularily.
See [lnbits.org](https://lnbits.org) for more detailed documentation.
## LNbits as an account system
LNbits is packaged with tools to help manage funds, such as a table of transactions, line chart of spending, export to csv + more to come..
LNbits is packaged with tools to help manage funds, such as a table of transactions, line chart of spending, export to csv + more to come..
![Lightning network wallet](https://i.imgur.com/w8jdGpF.png)
@ -32,10 +36,10 @@ Each wallet also comes with its own API keys, to help partition the exposure of
![lnurl ATM](https://i.imgur.com/WfCg8wY.png)
## LNbits as an LNURL-withdraw fallback
LNURL has a fallback scheme, so if scanned by a regular QR code reader it can default to a URL. LNbits exploits this to generate an instant wallet using the LNURL-withdraw.
LNURL has a fallback scheme, so if scanned by a regular QR code reader it can default to a URL. LNbits exploits this to generate an instant wallet using the [LNURL-withdraw](https://github.com/btcontract/lnurl-rfc/blob/master/lnurl-withdraw.md).
![lnurl fallback](https://i.imgur.com/CPBKHIv.png)
https://github.com/btcontract/lnurl-rfc/blob/master/spec.md
Using **lnbits.com/?lightning="LNURL-withdraw"** will trigger a withdraw that builds an LNbits wallet.
Example use would be an ATM, which utilises LNURL, if the user scans the QR with a regular QR code scanner app, they will stilll be able to access the funds.
@ -43,44 +47,19 @@ Example use would be an ATM, which utilises LNURL, if the user scans the QR with
![lnurl ATM](https://i.imgur.com/Gi6bn3L.jpg)
## LNbits as an insta-wallet
Wallets can be easily generated and given out to people at events (one click multi-wallet generation to be added soon).
"Go to this website", has a lot less friction than "Download this app".
![lnurl ATM](https://i.imgur.com/xFWDnwy.png)
# Running LNbits locally
Download this repo
LNbits uses [Flask](http://flask.pocoo.org/).
Feel free to contribute to the project.
Application dependencies
------------------------
The application uses [Pipenv][pipenv] to manage Python packages.
While in development, you will need to install all dependencies:
$ pipenv shell
$ pipenv install --dev
You will need to set the variables in .env.example, and rename the file to .env
![lnurl ATM](https://i.imgur.com/ri2zOe8.png)
Running the server
------------------
$ flask migrate
$ flask run
There is an environment variable called `FLASK_ENV` that has to be set to `development`
if you want to run Flask in debug mode with autoreload
## Running LNbits locally
[pipenv]: https://docs.pipenv.org/#install-pipenv-today
See the [development docs](docs/devs/installation.md) for details on installation and setup.
# Tip me
If you like this project and might even use or extend it, why not send some tip love!
https://lnbits.com/paywall/GAqKguK5S8f6w5VNjS9DfK
## Tip me
If you like this project and might even use or extend it, why not [send some tip love](https://lnbits.com/paywall/GAqKguK5S8f6w5VNjS9DfK)!
[github-actions]: https://github.com/lnbits/lnbits/actions
[github-actions-badge]: https://github.com/lnbits/lnbits/workflows/test%20suite/badge.svg

33
docs/devs/installation.md

@ -5,30 +5,47 @@ title: Installation
nav_order: 1
---
Installation
============
LNbits uses [Flask](http://flask.pocoo.org/).
Download this repo and install the dependencies.
Application dependencies
------------------------
The application uses [Pipenv][pipenv] to manage Python packages.
While in development, you will need to install all dependencies (includes packages like `black` and `flake8`):
While in development, you will need to install all dependencies:
```sh
$ pipenv shell
$ pipenv install --dev
```
You will need to set the variables in `.env.example`, and rename the file to `.env`.
$ pipenv shell
$ pipenv install --dev
![Files](https://i.imgur.com/ri2zOe8.png)
You might also need to install additional packages, depending on the [backend wallets](../guide/wallets.md) you configured.
E.g. when you want to use LND you have to `pipenv install lnd-grpc`.
Take a look at [Polar](https://lightningpolar.com/) for an excellent way of spinning up a Lightning Network dev environment.
Running the server
------------------
$ flask run
LNbits uses [Flask](http://flask.pocoo.org/) as an application server.
```sh
$ pipenv run flask migrate
$ pipenv run flask run
```
There is an environment variable called `FLASK_ENV` that has to be set to `development`
if you want to run Flask in debug mode with autoreload
[pipenv]: https://pipenv.pypa.io/
Frontend
--------
[pipenv]: https://docs.pipenv.org/#install-pipenv-today
The views are build using [Vue.js and Quasar](https://quasar.dev/start/how-to-use-vue).

2
lnbits/core/templates/core/index.html

@ -47,7 +47,7 @@
<div class="row q-mt-md q-gutter-sm">
<q-btn outline
color="grey"
type="a" href="https://github.com/arcbtc/lnbits" target="_blank" rel="noopener">View project in GitHub</q-btn>
type="a" href="https://github.com/lnbits/lnbits" target="_blank" rel="noopener">View project in GitHub</q-btn>
<q-btn outline
color="grey"
type="a" href="https://lnbits.com/paywall/GAqKguK5S8f6w5VNjS9DfK" target="_blank" rel="noopener">Donate</q-btn>

38
lnbits/extensions/events/templates/events/_api_docs.html

@ -1,17 +1,23 @@
<q-expansion-item
group="extras"
icon="swap_vertical_circle"
label="Info"
:content-inset-level="0.5"
>
<q-card>
<q-card-section>
<h5 class="text-subtitle1 q-my-none">Events: Sell and register ticket waves for an event</h5>
<p>Events alows you to make a wave of tickets for an event, each ticket is in the form of a unqiue QRcode, which the user presents at registration. Events comes with a shareable ticket scanner, which can be used to register attendees.<br/>
<small> Created by, <a href="https://github.com/benarc">Ben Arc</a></small></p>
</q-card>
</q-card-section>
</q-card-section>
<q-expansion-item
group="extras"
icon="swap_vertical_circle"
label="Info"
:content-inset-level="0.5"
>
<q-card>
<q-card-section>
<h5 class="text-subtitle1 q-my-none">
Events: Sell and register ticket waves for an event
</h5>
<p>
Events alows you to make a wave of tickets for an event, each ticket is
in the form of a unqiue QRcode, which the user presents at registration.
Events comes with a shareable ticket scanner, which can be used to
register attendees.<br />
<small>
Created by, <a href="https://github.com/benarc">Ben Arc</a>
</small>
</p>
</q-card-section>
</q-card>
</q-expansion-item>

23
lnbits/extensions/events/templates/events/index.html

@ -55,19 +55,16 @@
:href="props.row.displayUrl"
target="_blank"
></q-btn>
<q-btn
unelevated
dense
size="xs"
icon="how_to_reg"
:color="($q.dark.isActive) ? 'grey-7' : 'grey-5'"
type="a"
:href="'/events/register/' + props.row.id"
target="_blank"
></q-btn>
</q-td>
<q-btn
unelevated
dense
size="xs"
icon="how_to_reg"
:color="($q.dark.isActive) ? 'grey-7' : 'grey-5'"
type="a"
:href="'/events/register/' + props.row.id"
target="_blank"
></q-btn>
</q-td>
<q-td v-for="col in props.cols" :key="col.name" :props="props">
{{ col.value }}

37
lnbits/extensions/lnticket/templates/lnticket/_api_docs.html

@ -1,17 +1,22 @@
<q-expansion-item
group="extras"
icon="swap_vertical_circle"
label="Info"
:content-inset-level="0.5"
>
<q-card>
<q-card-section>
<h5 class="text-subtitle1 q-my-none">Support Tickets: Get paid sats to answer questions</h5>
<p>Charge people per word for contacting you. Possible applications incude, paid support ticketing, PAYG language services, contact spam protection.<br/>
<small> Created by, <a href="https://github.com/benarc">Ben Arc</a></small></p>
</q-card>
</q-card-section>
</q-card-section>
<q-expansion-item
group="extras"
icon="swap_vertical_circle"
label="Info"
:content-inset-level="0.5"
>
<q-card>
<q-card-section>
<h5 class="text-subtitle1 q-my-none">
Support Tickets: Get paid sats to answer questions
</h5>
<p>
Charge people per word for contacting you. Possible applications incude,
paid support ticketing, PAYG language services, contact spam
protection.<br />
<small>
Created by, <a href="https://github.com/benarc">Ben Arc</a></small
>
</p>
</q-card-section>
</q-card>
</q-expansion-item>

78
lnbits/extensions/paywall/templates/paywall/_api_docs.html

@ -7,9 +7,7 @@
<q-expansion-item group="api" dense expand-separator label="List paywalls">
<q-card>
<q-card-section>
<code
><span class="text-blue">GET</span> /paywall/api/v1/paywalls</code
>
<code><span class="text-blue">GET</span> /paywall/api/v1/paywalls</code>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;invoice_key&gt;}</code><br />
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
@ -29,37 +27,42 @@
<q-card>
<q-card-section>
<code
><span class="text-green">POST</span>
/paywall/api/v1/paywalls</code
><span class="text-green">POST</span> /paywall/api/v1/paywalls</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;admin_key&gt;}</code><br />
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
<code
>{"amount": &lt;integer&gt;, "description": &lt;string&gt;,
"memo": &lt;string&gt;, "remembers": &lt;boolean&gt;,
"url": &lt;string&gt;}</code
>{"amount": &lt;integer&gt;, "description": &lt;string&gt;, "memo":
&lt;string&gt;, "remembers": &lt;boolean&gt;, "url":
&lt;string&gt;}</code
>
<h5 class="text-caption q-mt-sm q-mb-none">
Returns 201 CREATED (application/json)
</h5>
<code>{"amount": &lt;integer&gt;, "description": &lt;string&gt;,
"id": &lt;string&gt;, "memo": &lt;string&gt;,
"remembers": &lt;boolean&gt;, "time": &lt;int&gt;,
"url": &lt;string&gt;, "wallet": &lt;string&gt;}</code>
<code
>{"amount": &lt;integer&gt;, "description": &lt;string&gt;, "id":
&lt;string&gt;, "memo": &lt;string&gt;, "remembers": &lt;boolean&gt;,
"time": &lt;int&gt;, "url": &lt;string&gt;, "wallet":
&lt;string&gt;}</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X POST {{ request.url_root }}paywall/api/v1/paywalls -d
'{"url": &lt;string&gt;, "memo": &lt;string&gt;,
"description": &lt;string&gt;, "amount": &lt;integer&gt;,
"remembers": &lt;boolean&gt;}' -H
"Content-type: application/json" -H "X-Api-Key: {{
g.user.wallets[0].adminkey }}"
'{"url": &lt;string&gt;, "memo": &lt;string&gt;, "description":
&lt;string&gt;, "amount": &lt;integer&gt;, "remembers":
&lt;boolean&gt;}' -H "Content-type: application/json" -H "X-Api-Key:
{{ g.user.wallets[0].adminkey }}"
</code>
</q-card-section>
</q-card>
</q-expansion-item>
<q-expansion-item group="api" dense expand-separator label="Create an invoice (public)">
<q-expansion-item
group="api"
dense
expand-separator
label="Create an invoice (public)"
>
<q-card>
<q-card-section>
<code
@ -67,23 +70,29 @@
/paywall/api/v1/paywalls/&lt;paywall_id&gt;/invoice</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
<code
>{"amount": &lt;integer&gt;}</code
>
<code>{"amount": &lt;integer&gt;}</code>
<h5 class="text-caption q-mt-sm q-mb-none">
Returns 201 CREATED (application/json)
</h5>
<code>{"checking_id": &lt;string&gt;, "payment_request": &lt;string&gt;}</code>
<code
>{"checking_id": &lt;string&gt;, "payment_request":
&lt;string&gt;}</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X POST {{ request.url_root }}paywall/api/v1/paywalls/&lt;paywall_id&gt;/invoice -d
'{"amount": &lt;integer&gt;}' -H
"Content-type: application/json"
>curl -X POST {{ request.url_root
}}paywall/api/v1/paywalls/&lt;paywall_id&gt;/invoice -d '{"amount":
&lt;integer&gt;}' -H "Content-type: application/json"
</code>
</q-card-section>
</q-card>
</q-expansion-item>
<q-expansion-item group="api" dense expand-separator label="Check invoice status (public)">
<q-expansion-item
group="api"
dense
expand-separator
label="Check invoice status (public)"
>
<q-card>
<q-card-section>
<code
@ -91,19 +100,20 @@
/paywall/api/v1/paywalls/&lt;paywall_id&gt;/check_invoice</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
<code
>{"checking_id": &lt;string&gt;}</code
>
<code>{"checking_id": &lt;string&gt;}</code>
<h5 class="text-caption q-mt-sm q-mb-none">
Returns 200 OK (application/json)
</h5>
<code>{"paid": false}</code><br>
<code>{"paid": true, "url": &lt;string&gt;, "remembers": &lt;boolean&gt;}</code>
<code>{"paid": false}</code><br />
<code
>{"paid": true, "url": &lt;string&gt;, "remembers":
&lt;boolean&gt;}</code
>
<h5 class="text-caption q-mt-sm q-mb-none">Curl example</h5>
<code
>curl -X POST {{ request.url_root }}paywall/api/v1/paywalls/&lt;paywall_id&gt;/check_invoice -d
'{"checking_id": &lt;string&gt;}' -H
"Content-type: application/json"
>curl -X POST {{ request.url_root
}}paywall/api/v1/paywalls/&lt;paywall_id&gt;/check_invoice -d
'{"checking_id": &lt;string&gt;}' -H "Content-type: application/json"
</code>
</q-card-section>
</q-card>

17
lnbits/extensions/paywall/templates/paywall/display.html

@ -5,7 +5,7 @@
<q-card-section class="q-pa-none">
<h5 class="text-subtitle1 q-mt-none q-mb-sm">{{ paywall.memo }}</h5>
{% if paywall.description %}
<p>{{ paywall.description }}</p>
<p>{{ paywall.description }}</p>
{% endif %}
<div v-if="!this.redirectUrl" class="q-mt-lg">
<q-form v-if="">
@ -19,7 +19,16 @@
:hint="'Minimum ' + paywallAmount + ' sat'"
>
<template v-slot:after>
<q-btn round dense flat icon="check" color="deep-purple" type="submit" @click="createInvoice" :disabled="userAmount < paywallAmount || paymentReq"></q-btn>
<q-btn
round
dense
flat
icon="check"
color="deep-purple"
type="submit"
@click="createInvoice"
:disabled="userAmount < paywallAmount || paymentReq"
></q-btn>
</template>
</q-input>
</q-form>
@ -37,7 +46,9 @@
<q-btn outline color="grey" @click="copyText(paymentReq)"
>Copy invoice</q-btn
>
<q-btn @click="cancelPayment" flat color="grey" class="q-ml-auto">Cancel</q-btn>
<q-btn @click="cancelPayment" flat color="grey" class="q-ml-auto"
>Cancel</q-btn
>
</div>
</div>
</div>

15
lnbits/extensions/paywall/templates/paywall/index.html

@ -147,11 +147,11 @@
></q-checkbox>
</q-item-section>
<q-item-section>
<q-item-label
>Remember payments</q-item-label
>
<q-item-label>Remember payments</q-item-label>
<q-item-label caption
>A succesful payment will be registered in the browser's storage, so the user doesn't need to pay again to access the URL.</q-item-label
>A succesful payment will be registered in the browser's
storage, so the user doesn't need to pay again to access the
URL.</q-item-label
>
</q-item-section>
</q-item>
@ -204,7 +204,12 @@
return rowA.amount - rowB.amount
}
},
{name: 'remembers', align: 'left', label: 'Remember', field: 'remembers'},
{
name: 'remembers',
align: 'left',
label: 'Remember',
field: 'remembers'
},
{
name: 'date',
align: 'left',

11
lnbits/extensions/tpos/templates/tpos/_api_docs.html

@ -4,12 +4,7 @@
label="API info"
:content-inset-level="0.5"
>
<q-expansion-item
group="api"
dense
expand-separator
label="List TPoS"
>
<q-expansion-item group="api" dense expand-separator label="List TPoS">
<q-card>
<q-card-section>
<code><span class="text-blue">GET</span> /tpos/api/v1/tposs</code>
@ -31,9 +26,7 @@
<q-expansion-item group="api" dense expand-separator label="Create a TPoS">
<q-card>
<q-card-section>
<code
><span class="text-green">POST</span> /tpos/api/v1/tposs</code
>
<code><span class="text-green">POST</span> /tpos/api/v1/tposs</code>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;invoice_key&gt;}</code><br />
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>

9
lnbits/extensions/withdraw/templates/withdraw/_api_docs.html

@ -12,9 +12,7 @@
>
<q-card>
<q-card-section>
<code
><span class="text-blue">GET</span> /withdraw/api/v1/links</code
>
<code><span class="text-blue">GET</span> /withdraw/api/v1/links</code>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;invoice_key&gt;}</code><br />
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>
@ -66,10 +64,7 @@
>
<q-card>
<q-card-section>
<code
><span class="text-green">POST</span>
/withdraw/api/v1/links</code
>
<code><span class="text-green">POST</span> /withdraw/api/v1/links</code>
<h5 class="text-caption q-mt-sm q-mb-none">Headers</h5>
<code>{"X-Api-Key": &lt;admin_key&gt;}</code><br />
<h5 class="text-caption q-mt-sm q-mb-none">Body (application/json)</h5>

2
lnbits/templates/base.html

@ -67,7 +67,7 @@
<strong>LN</strong>bits, free and open-source lightning wallet/accounts system
</q-toolbar-title>
<q-space></q-space>
<q-btn flat dense :color="($q.dark.isActive) ? 'white' : 'deep-purple'" icon="code" type="a" href="https://github.com/arcbtc/lnbits" target="_blank" rel="noopener">
<q-btn flat dense :color="($q.dark.isActive) ? 'white' : 'deep-purple'" icon="code" type="a" href="https://github.com/lnbits/lnbits" target="_blank" rel="noopener">
<q-tooltip>View project in GitHub</q-tooltip>
</q-btn>
</q-toolbar>

12
package-lock.json

@ -0,0 +1,12 @@
{
"requires": true,
"lockfileVersion": 1,
"dependencies": {
"prettier": {
"version": "2.0.5",
"resolved": "https://registry.npmjs.org/prettier/-/prettier-2.0.5.tgz",
"integrity": "sha512-7PtVymN48hGcO4fGjybyBSIWDsLU4H4XlvOHfq91pz9kkGlonzwTfYkaIEwiRg/dAJF9YlbsduBAgtYLi+8cFg==",
"dev": true
}
}
}

3
package.json

@ -1,5 +1,8 @@
{
"devDependencies": {
"prettier": "^2.0.5"
},
"scripts": {
"lint": "prettier --write lnbits/static/js/** lnbits/core/static/js/** lnbits/extensions/*/templates/**"
}
}

Loading…
Cancel
Save