forked from oscar.krause/fastapi-dls
Merge branch 'dev' into debian
This commit is contained in:
commit
52faba5a1d
46
README.md
46
README.md
@ -5,6 +5,13 @@ Minimal Delegated License Service (DLS).
|
|||||||
This service can be used without internet connection.
|
This service can be used without internet connection.
|
||||||
Only the clients need a connection to this service on configured port.
|
Only the clients need a connection to this service on configured port.
|
||||||
|
|
||||||
|
## ToDo#'s
|
||||||
|
|
||||||
|
- provide `.deb` package (WIP)
|
||||||
|
- migrate from `dataset` to `sqlalchemy` (WIP)
|
||||||
|
- migrate from `fastapi` to `flask`
|
||||||
|
- Support http mode for using external https proxy
|
||||||
|
|
||||||
## Endpoints
|
## Endpoints
|
||||||
|
|
||||||
### `GET /`
|
### `GET /`
|
||||||
@ -42,7 +49,7 @@ There are some more internal api endpoints for handling authentication and lease
|
|||||||
Docker-Images are available here:
|
Docker-Images are available here:
|
||||||
|
|
||||||
- [Docker-Hub](https://hub.docker.com/repository/docker/collinwebdesigns/fastapi-dls): `collinwebdesigns/fastapi-dls:latest`
|
- [Docker-Hub](https://hub.docker.com/repository/docker/collinwebdesigns/fastapi-dls): `collinwebdesigns/fastapi-dls:latest`
|
||||||
- GitLab-Registry: `registry.git.collinwebdesigns.de/oscar.krause/fastapi-dls/main:latest`
|
- [GitLab-Registry](https://git.collinwebdesigns.de/oscar.krause/fastapi-dls/container_registry): `registry.git.collinwebdesigns.de/oscar.krause/fastapi-dls/main:latest`
|
||||||
|
|
||||||
**Run this on the Docker-Host**
|
**Run this on the Docker-Host**
|
||||||
|
|
||||||
@ -91,7 +98,7 @@ volumes:
|
|||||||
dls-db:
|
dls-db:
|
||||||
```
|
```
|
||||||
|
|
||||||
## Debian
|
## Debian/Ubuntu (manual method using `git clone`)
|
||||||
|
|
||||||
Tested on `Debian 11 (bullseye)`, Ubuntu may also work.
|
Tested on `Debian 11 (bullseye)`, Ubuntu may also work.
|
||||||
|
|
||||||
@ -112,6 +119,7 @@ python3 -m venv venv
|
|||||||
source venv/bin/activate
|
source venv/bin/activate
|
||||||
pip install -r requirements.txt
|
pip install -r requirements.txt
|
||||||
deactivate
|
deactivate
|
||||||
|
chown -R www-data:www-data $WORKING_DIR
|
||||||
```
|
```
|
||||||
|
|
||||||
**Create keypair and webserver certificate**
|
**Create keypair and webserver certificate**
|
||||||
@ -125,28 +133,27 @@ openssl genrsa -out $WORKING_DIR/instance.private.pem 2048
|
|||||||
openssl rsa -in $WORKING_DIR/instance.private.pem -outform PEM -pubout -out $WORKING_DIR/instance.public.pem
|
openssl rsa -in $WORKING_DIR/instance.private.pem -outform PEM -pubout -out $WORKING_DIR/instance.public.pem
|
||||||
# create ssl certificate for integrated webserver (uvicorn) - because clients rely on ssl
|
# create ssl certificate for integrated webserver (uvicorn) - because clients rely on ssl
|
||||||
openssl req -x509 -nodes -days 3650 -newkey rsa:2048 -keyout $WORKING_DIR/webserver.key -out $WORKING_DIR/webserver.crt
|
openssl req -x509 -nodes -days 3650 -newkey rsa:2048 -keyout $WORKING_DIR/webserver.key -out $WORKING_DIR/webserver.crt
|
||||||
|
chown -R www-data:www-data $WORKING_DIR
|
||||||
```
|
```
|
||||||
|
|
||||||
**Test Service**
|
**Test Service**
|
||||||
|
|
||||||
|
This is only to test whether the service starts successfully.
|
||||||
|
|
||||||
```shell
|
```shell
|
||||||
cd /opt/fastapi-dls/app
|
cd /opt/fastapi-dls/app
|
||||||
/opt/fastapi-dls/venv/bin/uvicorn main:app \
|
su - www-data -c "/opt/fastapi-dls/venv/bin/uvicorn main:app --app-dir=/opt/fastapi-dls/app"
|
||||||
--host 127.0.0.1 --port 443 \
|
|
||||||
--app-dir /opt/fastapi-dls/app \
|
|
||||||
--ssl-keyfile /opt/fastapi-dls/app/cert/webserver.key \
|
|
||||||
--ssl-certfile /opt/fastapi-dls/app/cert/webserver.crt \
|
|
||||||
--proxy-headers
|
|
||||||
```
|
```
|
||||||
|
|
||||||
**Create config file**
|
**Create config file**
|
||||||
|
|
||||||
```shell
|
```shell
|
||||||
cat <<EOF > /etc/fastapi-dls.env
|
cat <<EOF > /etc/fastapi-dls/env
|
||||||
DLS_URL=127.0.0.1
|
DLS_URL=127.0.0.1
|
||||||
DLS_PORT=443
|
DLS_PORT=443
|
||||||
LEASE_EXPIRE_DAYS=90
|
LEASE_EXPIRE_DAYS=90
|
||||||
DATABASE=sqlite:////opt/fastapi-dls/app/db.sqlite
|
DATABASE=sqlite:////opt/fastapi-dls/app/db.sqlite
|
||||||
|
|
||||||
EOF
|
EOF
|
||||||
```
|
```
|
||||||
|
|
||||||
@ -161,27 +168,30 @@ After=network.target
|
|||||||
[Service]
|
[Service]
|
||||||
User=www-data
|
User=www-data
|
||||||
Group=www-data
|
Group=www-data
|
||||||
|
AmbientCapabilities=CAP_NET_BIND_SERVICE
|
||||||
WorkingDirectory=/opt/fastapi-dls/app
|
WorkingDirectory=/opt/fastapi-dls/app
|
||||||
ExecStart=/opt/fastapi-dls/venv/bin/uvicorn \
|
EnvironmentFile=/etc/fastapi-dls.env
|
||||||
--host $DLS_URL --port $DLS_PORT \
|
ExecStart=/opt/fastapi-dls/venv/bin/uvicorn main:app \
|
||||||
|
--env-file /etc/fastapi-dls.env \
|
||||||
|
--host \$DLS_URL --port \$DLS_PORT \
|
||||||
--app-dir /opt/fastapi-dls/app \
|
--app-dir /opt/fastapi-dls/app \
|
||||||
--ssl-keyfile /opt/fastapi-dls/app/cert/webserver.key \
|
--ssl-keyfile /opt/fastapi-dls/app/cert/webserver.key \
|
||||||
--ssl-certfile /opt/fastapi-dls/app/cert/webserver.crt \
|
--ssl-certfile /opt/fastapi-dls/app/cert/webserver.crt \
|
||||||
--proxy-headers
|
--proxy-headers
|
||||||
EnvironmentFile=/etc/fastapi-dls.env
|
|
||||||
Restart=always
|
Restart=always
|
||||||
KillSignal=SIGQUIT
|
KillSignal=SIGQUIT
|
||||||
Type=notify
|
Type=simple
|
||||||
StandardError=syslog
|
StandardError=syslog
|
||||||
NotifyAccess=all
|
NotifyAccess=all
|
||||||
|
|
||||||
[Install]
|
[Install]
|
||||||
WantedBy=multi-user.target
|
WantedBy=multi-user.target
|
||||||
|
|
||||||
EOF
|
EOF
|
||||||
```
|
```
|
||||||
|
|
||||||
Now you have to run `systemctl daemon-reload`. After that you can start service
|
Now you have to run `systemctl daemon-reload`. After that you can start service
|
||||||
with `systemctl start fastapi-dls.service`.
|
with `systemctl start fastapi-dls.service` (and enable autostart with `systemctl enable fastapi-dls.service`).
|
||||||
|
|
||||||
# Configuration
|
# Configuration
|
||||||
|
|
||||||
@ -194,7 +204,7 @@ with `systemctl start fastapi-dls.service`.
|
|||||||
| `DATABASE` | `sqlite:///db.sqlite` | See [official dataset docs](https://dataset.readthedocs.io/en/latest/quickstart.html) |
|
| `DATABASE` | `sqlite:///db.sqlite` | See [official dataset docs](https://dataset.readthedocs.io/en/latest/quickstart.html) |
|
||||||
| `CORS_ORIGINS` | `https://{DLS_URL}` | Sets `Access-Control-Allow-Origin` header (comma separated string) |
|
| `CORS_ORIGINS` | `https://{DLS_URL}` | Sets `Access-Control-Allow-Origin` header (comma separated string) |
|
||||||
|
|
||||||
# Installation (Client)
|
# Setup (Client)
|
||||||
|
|
||||||
**The token file has to be copied! It's not enough to C&P file contents, because there can be special characters.**
|
**The token file has to be copied! It's not enough to C&P file contents, because there can be special characters.**
|
||||||
|
|
||||||
@ -235,6 +245,12 @@ Currently, there are no known issues.
|
|||||||
|
|
||||||
## Windows
|
## Windows
|
||||||
|
|
||||||
|
### Required cipher on Windows Guests (e.g. managed by domain controller with GPO)
|
||||||
|
|
||||||
|
It is required to enable `SHA1` (`TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA_P521`) in [windows cipher suite](https://learn.microsoft.com/en-us/windows-server/security/tls/manage-tls).
|
||||||
|
|
||||||
|
### Multiple Display Container LS Instances
|
||||||
|
|
||||||
On Windows on some machines there are running two or more instances of `NVIDIA Display Container LS`. This causes a
|
On Windows on some machines there are running two or more instances of `NVIDIA Display Container LS`. This causes a
|
||||||
problem on licensing flow. As you can see in the logs below, there are two lines with `NLS initialized`, each prefixed
|
problem on licensing flow. As you can see in the logs below, there are two lines with `NLS initialized`, each prefixed
|
||||||
with `<1>` and `<2>`. So it is possible, that *daemon 1* fetches a valid license through dls-service, and *daemon 2*
|
with `<1>` and `<2>`. So it is possible, that *daemon 1* fetches a valid license through dls-service, and *daemon 2*
|
||||||
|
31
app/main.py
31
app/main.py
@ -61,8 +61,8 @@ LEASE_EXPIRE_DELTA = relativedelta(days=int(getenv('LEASE_EXPIRE_DAYS', 90)))
|
|||||||
|
|
||||||
DLS_URL = str(getenv('DLS_URL', 'localhost'))
|
DLS_URL = str(getenv('DLS_URL', 'localhost'))
|
||||||
DLS_PORT = int(getenv('DLS_PORT', '443'))
|
DLS_PORT = int(getenv('DLS_PORT', '443'))
|
||||||
SITE_KEY_XID = getenv('SITE_KEY_XID', '00000000-0000-0000-0000-000000000000')
|
SITE_KEY_XID = str(getenv('SITE_KEY_XID', '00000000-0000-0000-0000-000000000000'))
|
||||||
INSTANCE_REF = '00000000-0000-0000-0000-000000000000'
|
INSTANCE_REF = str(getenv('INSTANCE_REF', '00000000-0000-0000-0000-000000000000'))
|
||||||
INSTANCE_KEY_RSA = load_key(join(dirname(__file__), 'cert/instance.private.pem'))
|
INSTANCE_KEY_RSA = load_key(join(dirname(__file__), 'cert/instance.private.pem'))
|
||||||
INSTANCE_KEY_PUB = load_key(join(dirname(__file__), 'cert/instance.public.pem'))
|
INSTANCE_KEY_PUB = load_key(join(dirname(__file__), 'cert/instance.public.pem'))
|
||||||
|
|
||||||
@ -194,6 +194,33 @@ async def auth_v1_origin(request: Request):
|
|||||||
return JSONResponse(response)
|
return JSONResponse(response)
|
||||||
|
|
||||||
|
|
||||||
|
# venv/lib/python3.9/site-packages/nls_services_auth/test/test_origins_controller.py
|
||||||
|
# { "environment" : { "guest_driver_version" : "guest_driver_version", "hostname" : "myhost", "ip_address_list" : [ "192.168.1.129" ], "os_version" : "os_version", "os_platform" : "os_platform", "fingerprint" : { "mac_address_list" : [ "e4:b9:7a:e5:7b:ff" ] }, "host_driver_version" : "host_driver_version" }, "origin_ref" : "00112233-4455-6677-8899-aabbccddeeff" }
|
||||||
|
@app.post('/auth/v1/origin/update')
|
||||||
|
async def auth_v1_origin_update(request: Request):
|
||||||
|
j, cur_time = json.loads((await request.body()).decode('utf-8')), datetime.utcnow()
|
||||||
|
|
||||||
|
origin_ref = j['origin_ref']
|
||||||
|
logging.info(f'> [ update ]: {origin_ref}: {j}')
|
||||||
|
|
||||||
|
data = dict(
|
||||||
|
origin_ref=origin_ref,
|
||||||
|
hostname=j['environment']['hostname'],
|
||||||
|
guest_driver_version=j['environment']['guest_driver_version'],
|
||||||
|
os_platform=j['environment']['os_platform'], os_version=j['environment']['os_version'],
|
||||||
|
)
|
||||||
|
|
||||||
|
db['origin'].upsert(data, ['origin_ref'])
|
||||||
|
|
||||||
|
response = {
|
||||||
|
"environment": j['environment'],
|
||||||
|
"prompts": None,
|
||||||
|
"sync_timestamp": cur_time.isoformat()
|
||||||
|
}
|
||||||
|
|
||||||
|
return JSONResponse(response)
|
||||||
|
|
||||||
|
|
||||||
# venv/lib/python3.9/site-packages/nls_services_auth/test/test_auth_controller.py
|
# venv/lib/python3.9/site-packages/nls_services_auth/test/test_auth_controller.py
|
||||||
# venv/lib/python3.9/site-packages/nls_core_auth/auth.py - CodeResponse
|
# venv/lib/python3.9/site-packages/nls_core_auth/auth.py - CodeResponse
|
||||||
# {"code_challenge":"...","origin_ref":"00112233-4455-6677-8899-aabbccddeeff"}
|
# {"code_challenge":"...","origin_ref":"00112233-4455-6677-8899-aabbccddeeff"}
|
||||||
|
Loading…
Reference in New Issue
Block a user