diff --git a/README.md b/README.md index d3b683c33fc88f7a1fd12efc5fbaeb28e030ef3a..b1b42bb661d6515f0a1cd21ab90cec964519768b 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,2 @@ -# Automatická detekce a dokumentace pĹ™ipojenĂ˝ch USB zaĹ™ĂzenĂ - Bug Thugs +# Automatic detection and documentation of connected USB devices - Bug Thugs diff --git a/server/README.md b/server/README.md index 7046460b6661868183e9e49b4a700c8a03f3c2f7..c75cf40ac3d2f97132d9bf1769bd0772865f4bb2 100644 --- a/server/README.md +++ b/server/README.md @@ -1,2 +1,37 @@ -# Automatická detekce a dokumentace pĹ™ipojenĂ˝ch USB zaĹ™ĂzenĂ - Server - Bug Thugs +# Automatic detection and documentation of connected USB devices - Server - Bug Thugs + +--- + +- [Description](#description) +- [Build](#build) +- [Execution](#execution) + +--- + +## Description + +This server application provides data via endpoints defined in **sql_app.api** package. Files in this package are divided by their respetive funcionality. File **usb_logs_web.py** provides endpoints and methods for main web view **/api/v1/logs-web**, file **usb_logs.py** provides endpoints and methods for client applications. + +**sql_app** package contains files for database communication. **models.py** and **schemas.py** provides classes for mapping objects to database table entries, **database.py** defines database communication session and **crud.py** contains methods with database queries for reading, updating and saving data from client applications and web interfaces. + + +## Build + +Server application comes with dockerFile and docker compose file so build is quite simple. In the server folder run command + +```bash +docker-compose up +``` + +And docker will create image for server application and postgresql database. Database files are stored in own folder, so saved data will be persistent even if docker daemon would unexpectedly shut down. + +## Web Views + +Data from database are easily accesibly from web browser. Main web views url is + +```bash +http://localhost:8000/api/v1/logs-web +``` + +On this page there is select box at the top of the page for accessing different views on other data in database as well as creating new ones diff --git a/server/doc/sql_app/api/devices.html b/server/doc/sql_app/api/devices.html new file mode 100644 index 0000000000000000000000000000000000000000..44cffd760e359a77429f397ab341a1f060504b65 --- /dev/null +++ b/server/doc/sql_app/api/devices.html @@ -0,0 +1,189 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.devices API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.devices</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# prefix used for all endpoints in this file +device = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@device.post("/device", response_model=schemas.Device) +def create_device(device: schemas.DeviceCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new device + """ + print(crud.create_device(db=db, device=device)) + + +@device.get("/devices", response_model=List[schemas.Device]) +def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Endpoint returns all devices in database + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + return devices + + +@device.get("/device/{device_id}", response_model=schemas.Device) +def read_device(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific device by given id + """ + db_device = crud.get_device(db, device_id=device_id) + if db_device is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_device</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.devices.create_device"><code class="name flex"> +<span>def <span class="ident">create_device</span></span>(<span>device: <a title="sql_app.schemas.DeviceCreate" href="../schemas.html#sql_app.schemas.DeviceCreate">DeviceCreate</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint used for creating new device</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device.post("/device", response_model=schemas.Device) +def create_device(device: schemas.DeviceCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new device + """ + print(crud.create_device(db=db, device=device))</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices.read_device"><code class="name flex"> +<span>def <span class="ident">read_device</span></span>(<span>device_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific device by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device.get("/device/{device_id}", response_model=schemas.Device) +def read_device(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific device by given id + """ + db_device = crud.get_device(db, device_id=device_id) + if db_device is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_device</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices.read_devices"><code class="name flex"> +<span>def <span class="ident">read_devices</span></span>(<span>skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint returns all devices in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device.get("/devices", response_model=List[schemas.Device]) +def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Endpoint returns all devices in database + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + return devices</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.devices.create_device" href="#sql_app.api.devices.create_device">create_device</a></code></li> +<li><code><a title="sql_app.api.devices.get_db" href="#sql_app.api.devices.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.devices.read_device" href="#sql_app.api.devices.read_device">read_device</a></code></li> +<li><code><a title="sql_app.api.devices.read_devices" href="#sql_app.api.devices.read_devices">read_devices</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/devices_web.html b/server/doc/sql_app/api/devices_web.html new file mode 100644 index 0000000000000000000000000000000000000000..b4028ad0a5750c49c3bf3cf4260e4f4c6823bb10 --- /dev/null +++ b/server/doc/sql_app/api/devices_web.html @@ -0,0 +1,289 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.devices_web API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.devices_web</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from datetime import datetime +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="../templates/devices") + +# prefix used for all endpoints in this file +device_web = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@device_web.get("/devices-web", response_class=HTMLResponse) +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all devices and its current states + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + # adding state for each device in list + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs)-1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses}) + + +@device_web.post("/devices-web", response_class=HTMLResponse) +async def filter_devices(request: Request, skip: int = 0, limit: int = 100, lic: str = Form("all"), + db: Session = Depends(get_db)): + """ + Endpoint used for filtering devices by license. returns html template with only + devices that has assigned license defined by user input + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + def_devices = [] + for dev in devices: + for l in dev.licenses: + if dev not in def_devices and l.licenses.name == lic: + def_devices.append(dev) + # if input was default all + if lic == "all": + def_devices = devices + statuses = [] + for i in range(0, len(def_devices)): + statuses.append(def_devices[i].logs[len(def_devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses}) + + +@device_web.get("/device-license/{device_id}", response_class=HTMLResponse) +async def connect_dev_lic(request: Request, device_id: int, db: Session = Depends(get_db)): + """ + Returns template with one device and all available licenses that can be assigned to it. + """ + device = crud.get_device(db, device_id) + licenses = crud.get_licenses(db, 0, 100) + return templates.TemplateResponse("devicelicense.html", + {"request": request, "device": device, "licenses": licenses}) + + +@device_web.post("/devices-web/{device_id}", response_class=HTMLResponse) +async def connect_post(request: Request, device_id: int, lic: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from template for connecting device with license. Adds entry to devices_licenses + table and returns template with all devices in database + """ + crud.create_device_license(db, device_id, int(lic), datetime.now()) + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + # adding state for each device in list + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.devices_web.connect_dev_lic"><code class="name flex"> +<span>async def <span class="ident">connect_dev_lic</span></span>(<span>request: starlette.requests.Request, device_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with one device and all available licenses that can be assigned to it.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device_web.get("/device-license/{device_id}", response_class=HTMLResponse) +async def connect_dev_lic(request: Request, device_id: int, db: Session = Depends(get_db)): + """ + Returns template with one device and all available licenses that can be assigned to it. + """ + device = crud.get_device(db, device_id) + licenses = crud.get_licenses(db, 0, 100) + return templates.TemplateResponse("devicelicense.html", + {"request": request, "device": device, "licenses": licenses})</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices_web.connect_post"><code class="name flex"> +<span>async def <span class="ident">connect_post</span></span>(<span>request: starlette.requests.Request, device_id: int, lic: str = Form(Ellipsis), skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from template for connecting device with license. Adds entry to devices_licenses +table and returns template with all devices in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device_web.post("/devices-web/{device_id}", response_class=HTMLResponse) +async def connect_post(request: Request, device_id: int, lic: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from template for connecting device with license. Adds entry to devices_licenses + table and returns template with all devices in database + """ + crud.create_device_license(db, device_id, int(lic), datetime.now()) + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + # adding state for each device in list + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices_web.filter_devices"><code class="name flex"> +<span>async def <span class="ident">filter_devices</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, lic: str = Form(all), db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint used for filtering devices by license. returns html template with only +devices that has assigned license defined by user input</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device_web.post("/devices-web", response_class=HTMLResponse) +async def filter_devices(request: Request, skip: int = 0, limit: int = 100, lic: str = Form("all"), + db: Session = Depends(get_db)): + """ + Endpoint used for filtering devices by license. returns html template with only + devices that has assigned license defined by user input + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + def_devices = [] + for dev in devices: + for l in dev.licenses: + if dev not in def_devices and l.licenses.name == lic: + def_devices.append(dev) + # if input was default all + if lic == "all": + def_devices = devices + statuses = [] + for i in range(0, len(def_devices)): + statuses.append(def_devices[i].logs[len(def_devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices_web.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.devices_web.read_devices"><code class="name flex"> +<span>async def <span class="ident">read_devices</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with all devices and its current states</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@device_web.get("/devices-web", response_class=HTMLResponse) +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all devices and its current states + """ + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + # adding state for each device in list + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs)-1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.devices_web.connect_dev_lic" href="#sql_app.api.devices_web.connect_dev_lic">connect_dev_lic</a></code></li> +<li><code><a title="sql_app.api.devices_web.connect_post" href="#sql_app.api.devices_web.connect_post">connect_post</a></code></li> +<li><code><a title="sql_app.api.devices_web.filter_devices" href="#sql_app.api.devices_web.filter_devices">filter_devices</a></code></li> +<li><code><a title="sql_app.api.devices_web.get_db" href="#sql_app.api.devices_web.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.devices_web.read_devices" href="#sql_app.api.devices_web.read_devices">read_devices</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/index.html b/server/doc/sql_app/api/index.html new file mode 100644 index 0000000000000000000000000000000000000000..edd858207ab477c27c10162a667e253a503ee9ee --- /dev/null +++ b/server/doc/sql_app/api/index.html @@ -0,0 +1,110 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api</code></h1> +</header> +<section id="section-intro"> +</section> +<section> +<h2 class="section-title" id="header-submodules">Sub-modules</h2> +<dl> +<dt><code class="name"><a title="sql_app.api.devices" href="devices.html">sql_app.api.devices</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.devices_web" href="devices_web.html">sql_app.api.devices_web</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.licenses" href="licenses.html">sql_app.api.licenses</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.licenses_web" href="licenses_web.html">sql_app.api.licenses_web</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.pcs" href="pcs.html">sql_app.api.pcs</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.pcs_web" href="pcs_web.html">sql_app.api.pcs_web</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.teams" href="teams.html">sql_app.api.teams</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.teams_web" href="teams_web.html">sql_app.api.teams_web</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.usb_logs" href="usb_logs.html">sql_app.api.usb_logs</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.api.usb_logs_web" href="usb_logs_web.html">sql_app.api.usb_logs_web</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="../index.html">sql_app</a></code></li> +</ul> +</li> +<li><h3><a href="#header-submodules">Sub-modules</a></h3> +<ul> +<li><code><a title="sql_app.api.devices" href="devices.html">sql_app.api.devices</a></code></li> +<li><code><a title="sql_app.api.devices_web" href="devices_web.html">sql_app.api.devices_web</a></code></li> +<li><code><a title="sql_app.api.licenses" href="licenses.html">sql_app.api.licenses</a></code></li> +<li><code><a title="sql_app.api.licenses_web" href="licenses_web.html">sql_app.api.licenses_web</a></code></li> +<li><code><a title="sql_app.api.pcs" href="pcs.html">sql_app.api.pcs</a></code></li> +<li><code><a title="sql_app.api.pcs_web" href="pcs_web.html">sql_app.api.pcs_web</a></code></li> +<li><code><a title="sql_app.api.teams" href="teams.html">sql_app.api.teams</a></code></li> +<li><code><a title="sql_app.api.teams_web" href="teams_web.html">sql_app.api.teams_web</a></code></li> +<li><code><a title="sql_app.api.usb_logs" href="usb_logs.html">sql_app.api.usb_logs</a></code></li> +<li><code><a title="sql_app.api.usb_logs_web" href="usb_logs_web.html">sql_app.api.usb_logs_web</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/licenses.html b/server/doc/sql_app/api/licenses.html new file mode 100644 index 0000000000000000000000000000000000000000..6a4aa66e9ebaaea04cc33da6de425f252c16ebae --- /dev/null +++ b/server/doc/sql_app/api/licenses.html @@ -0,0 +1,160 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.licenses API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.licenses</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from datetime import datetime +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# prefix used for all endpoints in this file +licenses = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@licenses.get("/licenses", response_model=List[schemas.License]) +def read_licenses(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all licenses currently saved in database. + """ + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return licenses + + +@licenses.post("/device-license", response_model=schemas.DeviceLicense) +def create_device_license(device_license: schemas.DeviceLicenseCreate, db: Session = Depends(get_db)): + """ + Creates entry for devices_licenses table thus connecting device with its license. + """ + print(crud.create_device_license(db=db, device=device_license.device_id, license=device_license.license_id, + time=datetime.now()))</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.licenses.create_device_license"><code class="name flex"> +<span>def <span class="ident">create_device_license</span></span>(<span>device_license: <a title="sql_app.schemas.DeviceLicenseCreate" href="../schemas.html#sql_app.schemas.DeviceLicenseCreate">DeviceLicenseCreate</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Creates entry for devices_licenses table thus connecting device with its license.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@licenses.post("/device-license", response_model=schemas.DeviceLicense) +def create_device_license(device_license: schemas.DeviceLicenseCreate, db: Session = Depends(get_db)): + """ + Creates entry for devices_licenses table thus connecting device with its license. + """ + print(crud.create_device_license(db=db, device=device_license.device_id, license=device_license.license_id, + time=datetime.now()))</code></pre> +</details> +</dd> +<dt id="sql_app.api.licenses.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.licenses.read_licenses"><code class="name flex"> +<span>def <span class="ident">read_licenses</span></span>(<span>skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all licenses currently saved in database.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@licenses.get("/licenses", response_model=List[schemas.License]) +def read_licenses(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all licenses currently saved in database. + """ + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return licenses</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.licenses.create_device_license" href="#sql_app.api.licenses.create_device_license">create_device_license</a></code></li> +<li><code><a title="sql_app.api.licenses.get_db" href="#sql_app.api.licenses.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.licenses.read_licenses" href="#sql_app.api.licenses.read_licenses">read_licenses</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/licenses_web.html b/server/doc/sql_app/api/licenses_web.html new file mode 100644 index 0000000000000000000000000000000000000000..fb9ff21c762f8fec4968166d3e3ca17a4a2ad34d --- /dev/null +++ b/server/doc/sql_app/api/licenses_web.html @@ -0,0 +1,212 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.licenses_web API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.licenses_web</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from datetime import date +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="../templates/licenses") +device_templates = Jinja2Templates(directory="../templates/devices") + +# prefix used for all endpoints in this file +licenses_web = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@licenses_web.get("/license-create", response_class=HTMLResponse) +async def licenses_create_web(request: Request): + """ + Returns template with Form for creating new license. + """ + return templates.TemplateResponse("license_create.html", {"request": request}) + + +@licenses_web.get("/licenses-web", response_class=HTMLResponse) +async def read_licenses_web(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all licenses currently saved in database + """ + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("licenses.html", {"request": request, "licenses": licenses}) + + +@licenses_web.post("/licenses-web", response_class=HTMLResponse) +def create_license(request: Request, name: str = Form(...), expdate: date = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from create license form. Creates new license and returns template with all licenses in database + """ + db_license = crud.create_license(db, name, expdate) + if db_license is None: + print("something went wrong") + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return device_templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.licenses_web.create_license"><code class="name flex"> +<span>def <span class="ident">create_license</span></span>(<span>request: starlette.requests.Request, name: str = Form(Ellipsis), expdate: datetime.date = Form(Ellipsis), skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from create license form. Creates new license and returns template with all licenses in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@licenses_web.post("/licenses-web", response_class=HTMLResponse) +def create_license(request: Request, name: str = Form(...), expdate: date = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from create license form. Creates new license and returns template with all licenses in database + """ + db_license = crud.create_license(db, name, expdate) + if db_license is None: + print("something went wrong") + devices = crud.get_devices(db, skip=skip, limit=limit) + statuses = [] + for i in range(0, len(devices)): + statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return device_templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses})</code></pre> +</details> +</dd> +<dt id="sql_app.api.licenses_web.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.licenses_web.licenses_create_web"><code class="name flex"> +<span>async def <span class="ident">licenses_create_web</span></span>(<span>request: starlette.requests.Request)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with Form for creating new license.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@licenses_web.get("/license-create", response_class=HTMLResponse) +async def licenses_create_web(request: Request): + """ + Returns template with Form for creating new license. + """ + return templates.TemplateResponse("license_create.html", {"request": request})</code></pre> +</details> +</dd> +<dt id="sql_app.api.licenses_web.read_licenses_web"><code class="name flex"> +<span>async def <span class="ident">read_licenses_web</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with all licenses currently saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@licenses_web.get("/licenses-web", response_class=HTMLResponse) +async def read_licenses_web(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all licenses currently saved in database + """ + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("licenses.html", {"request": request, "licenses": licenses})</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.licenses_web.create_license" href="#sql_app.api.licenses_web.create_license">create_license</a></code></li> +<li><code><a title="sql_app.api.licenses_web.get_db" href="#sql_app.api.licenses_web.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.licenses_web.licenses_create_web" href="#sql_app.api.licenses_web.licenses_create_web">licenses_create_web</a></code></li> +<li><code><a title="sql_app.api.licenses_web.read_licenses_web" href="#sql_app.api.licenses_web.read_licenses_web">read_licenses_web</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/pcs.html b/server/doc/sql_app/api/pcs.html new file mode 100644 index 0000000000000000000000000000000000000000..e362d480427a91db4165e05919fe22325fc54d22 --- /dev/null +++ b/server/doc/sql_app/api/pcs.html @@ -0,0 +1,188 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.pcs API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.pcs</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# prefix used for all endpoints in this file +pcs = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@pcs.post("/pc", response_model=schemas.PC) +def create_pc(pc: schemas.PCCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ + print(crud.create_pc(db=db, user=pc.username, host=pc.hostname)) + + +@pcs.get("/pcs", response_model=List[schemas.PC]) +def read_pcs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs currently saved in database + """ + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return pcs + + +@pcs.get("/pc/{pc_id}", response_model=schemas.PC) +def read_pc(pc_id: int, db: Session = Depends(get_db)): + """ + Returns one specific pc by given id + """ + db_pc = crud.get_pc(db, pc_id=pc_id) + if db_pc is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_pc</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.pcs.create_pc"><code class="name flex"> +<span>def <span class="ident">create_pc</span></span>(<span>pc: <a title="sql_app.schemas.PCCreate" href="../schemas.html#sql_app.schemas.PCCreate">PCCreate</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint used for creating new pc</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs.post("/pc", response_model=schemas.PC) +def create_pc(pc: schemas.PCCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ + print(crud.create_pc(db=db, user=pc.username, host=pc.hostname))</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs.read_pc"><code class="name flex"> +<span>def <span class="ident">read_pc</span></span>(<span>pc_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific pc by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs.get("/pc/{pc_id}", response_model=schemas.PC) +def read_pc(pc_id: int, db: Session = Depends(get_db)): + """ + Returns one specific pc by given id + """ + db_pc = crud.get_pc(db, pc_id=pc_id) + if db_pc is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_pc</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs.read_pcs"><code class="name flex"> +<span>def <span class="ident">read_pcs</span></span>(<span>skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all pcs currently saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs.get("/pcs", response_model=List[schemas.PC]) +def read_pcs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs currently saved in database + """ + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return pcs</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.pcs.create_pc" href="#sql_app.api.pcs.create_pc">create_pc</a></code></li> +<li><code><a title="sql_app.api.pcs.get_db" href="#sql_app.api.pcs.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.pcs.read_pc" href="#sql_app.api.pcs.read_pc">read_pc</a></code></li> +<li><code><a title="sql_app.api.pcs.read_pcs" href="#sql_app.api.pcs.read_pcs">read_pcs</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/pcs_web.html b/server/doc/sql_app/api/pcs_web.html new file mode 100644 index 0000000000000000000000000000000000000000..5f1198284123e5f3272e49d48dacfe61096ff93d --- /dev/null +++ b/server/doc/sql_app/api/pcs_web.html @@ -0,0 +1,201 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.pcs_web API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.pcs_web</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="../templates/pcs") + +# prefix used for all endpoints in this file +pcs_web = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@pcs_web.get("/pcs-web", response_class=HTMLResponse) +async def read_pcs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all pcs currently saved in database + """ + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs}) + + +@pcs_web.get("/pc-team/{pc_id}", response_class=HTMLResponse) +async def connect_pc_team(request: Request, pc_id: int, db: Session = Depends(get_db)): + """ + Returns template with Form for connecting pc with team + """ + pc = crud.get_pc(db, pc_id) + teams = crud.get_teams(db, 0, 100) + return templates.TemplateResponse("pcteam.html", + {"request": request, "pc": pc, "teams": teams}) + + +@pcs_web.post("/pcs-web/{pc_id}", response_class=HTMLResponse) +async def connect_post(request: Request, pc_id: int, team: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from within form for connecting pc with team. Updates certain pc with new team. + """ + old_pc = crud.update_pc(db, pc_id, team) + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs})</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.pcs_web.connect_pc_team"><code class="name flex"> +<span>async def <span class="ident">connect_pc_team</span></span>(<span>request: starlette.requests.Request, pc_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with Form for connecting pc with team</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs_web.get("/pc-team/{pc_id}", response_class=HTMLResponse) +async def connect_pc_team(request: Request, pc_id: int, db: Session = Depends(get_db)): + """ + Returns template with Form for connecting pc with team + """ + pc = crud.get_pc(db, pc_id) + teams = crud.get_teams(db, 0, 100) + return templates.TemplateResponse("pcteam.html", + {"request": request, "pc": pc, "teams": teams})</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs_web.connect_post"><code class="name flex"> +<span>async def <span class="ident">connect_post</span></span>(<span>request: starlette.requests.Request, pc_id: int, team: str = Form(Ellipsis), skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from within form for connecting pc with team. Updates certain pc with new team.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs_web.post("/pcs-web/{pc_id}", response_class=HTMLResponse) +async def connect_post(request: Request, pc_id: int, team: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from within form for connecting pc with team. Updates certain pc with new team. + """ + old_pc = crud.update_pc(db, pc_id, team) + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs})</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs_web.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.pcs_web.read_pcs"><code class="name flex"> +<span>async def <span class="ident">read_pcs</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with all pcs currently saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@pcs_web.get("/pcs-web", response_class=HTMLResponse) +async def read_pcs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all pcs currently saved in database + """ + pcs = crud.get_pcs(db, skip=skip, limit=limit) + return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs})</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.pcs_web.connect_pc_team" href="#sql_app.api.pcs_web.connect_pc_team">connect_pc_team</a></code></li> +<li><code><a title="sql_app.api.pcs_web.connect_post" href="#sql_app.api.pcs_web.connect_post">connect_post</a></code></li> +<li><code><a title="sql_app.api.pcs_web.get_db" href="#sql_app.api.pcs_web.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.pcs_web.read_pcs" href="#sql_app.api.pcs_web.read_pcs">read_pcs</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/teams.html b/server/doc/sql_app/api/teams.html new file mode 100644 index 0000000000000000000000000000000000000000..00afc9ae2a00457b59bd37c88c0391078a25c7e9 --- /dev/null +++ b/server/doc/sql_app/api/teams.html @@ -0,0 +1,188 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.teams API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.teams</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# prefix used for all endpoints in this file +teams = APIRouter(prefix="/api/v1") + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@teams.post("/team", response_model=schemas.Team) +def create_device(team: schemas.TeamCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ + print(crud.create_team(db=db, name=team.name)) + + +@teams.get("/teams", response_model=List[schemas.Device]) +def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs saved in database + """ + teams = crud.get_teams(db, skip=skip, limit=limit) + return teams + + +@teams.get("/team/{team_id}", response_model=schemas.Device) +def read_device(team_id: int, db: Session = Depends(get_db)): + """ + Returns one specific team by given id + """ + db_team = crud.get_team(db, team_id=team_id) + if db_team is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_team</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.teams.create_device"><code class="name flex"> +<span>def <span class="ident">create_device</span></span>(<span>team: <a title="sql_app.schemas.TeamCreate" href="../schemas.html#sql_app.schemas.TeamCreate">TeamCreate</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint used for creating new pc</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams.post("/team", response_model=schemas.Team) +def create_device(team: schemas.TeamCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ + print(crud.create_team(db=db, name=team.name))</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams.read_device"><code class="name flex"> +<span>def <span class="ident">read_device</span></span>(<span>team_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific team by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams.get("/team/{team_id}", response_model=schemas.Device) +def read_device(team_id: int, db: Session = Depends(get_db)): + """ + Returns one specific team by given id + """ + db_team = crud.get_team(db, team_id=team_id) + if db_team is None: + raise HTTPException(status_code=404, detail="Device not found") + return db_team</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams.read_devices"><code class="name flex"> +<span>def <span class="ident">read_devices</span></span>(<span>skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all pcs saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams.get("/teams", response_model=List[schemas.Device]) +def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs saved in database + """ + teams = crud.get_teams(db, skip=skip, limit=limit) + return teams</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.teams.create_device" href="#sql_app.api.teams.create_device">create_device</a></code></li> +<li><code><a title="sql_app.api.teams.get_db" href="#sql_app.api.teams.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.teams.read_device" href="#sql_app.api.teams.read_device">read_device</a></code></li> +<li><code><a title="sql_app.api.teams.read_devices" href="#sql_app.api.teams.read_devices">read_devices</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/teams_web.html b/server/doc/sql_app/api/teams_web.html new file mode 100644 index 0000000000000000000000000000000000000000..bee1c5d0d2cd0311057c82c1c5c7761196d61ca9 --- /dev/null +++ b/server/doc/sql_app/api/teams_web.html @@ -0,0 +1,200 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.teams_web API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.teams_web</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List + +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="../templates/teams") + +# prefix used for all endpoints in this file +teams_web = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@teams_web.get("/teams-web", response_class=HTMLResponse) +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all teams currently saved in database + """ + teams = crud.get_teams(db, skip=skip, limit=limit) + return templates.TemplateResponse("teams.html", {"request": request, "teams": teams}) + + +@teams_web.get("/team-create", response_class=HTMLResponse) +async def team_create_web(request: Request): + """ + Returns template with form for creating new team + """ + return templates.TemplateResponse("team_create.html", {"request": request}) + + +@teams_web.post("/teams-web", response_class=HTMLResponse) +def create_team(request: Request, name: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from within form for creating new team. Creates new team and returns all teams in database + """ + team = crud.create_team(db, name) + if team is None: + print("something went wrong") + teams = crud.get_teams(db, skip=skip, limit=limit) + return templates.TemplateResponse("teams.html", {"request": request, "teams": teams})</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.teams_web.create_team"><code class="name flex"> +<span>def <span class="ident">create_team</span></span>(<span>request: starlette.requests.Request, name: str = Form(Ellipsis), skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from within form for creating new team. Creates new team and returns all teams in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams_web.post("/teams-web", response_class=HTMLResponse) +def create_team(request: Request, name: str = Form(...), skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint called from within form for creating new team. Creates new team and returns all teams in database + """ + team = crud.create_team(db, name) + if team is None: + print("something went wrong") + teams = crud.get_teams(db, skip=skip, limit=limit) + return templates.TemplateResponse("teams.html", {"request": request, "teams": teams})</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams_web.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams_web.read_devices"><code class="name flex"> +<span>async def <span class="ident">read_devices</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with all teams currently saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams_web.get("/teams-web", response_class=HTMLResponse) +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all teams currently saved in database + """ + teams = crud.get_teams(db, skip=skip, limit=limit) + return templates.TemplateResponse("teams.html", {"request": request, "teams": teams})</code></pre> +</details> +</dd> +<dt id="sql_app.api.teams_web.team_create_web"><code class="name flex"> +<span>async def <span class="ident">team_create_web</span></span>(<span>request: starlette.requests.Request)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with form for creating new team</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@teams_web.get("/team-create", response_class=HTMLResponse) +async def team_create_web(request: Request): + """ + Returns template with form for creating new team + """ + return templates.TemplateResponse("team_create.html", {"request": request})</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.teams_web.create_team" href="#sql_app.api.teams_web.create_team">create_team</a></code></li> +<li><code><a title="sql_app.api.teams_web.get_db" href="#sql_app.api.teams_web.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.teams_web.read_devices" href="#sql_app.api.teams_web.read_devices">read_devices</a></code></li> +<li><code><a title="sql_app.api.teams_web.team_create_web" href="#sql_app.api.teams_web.team_create_web">team_create_web</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/usb_logs.html b/server/doc/sql_app/api/usb_logs.html new file mode 100644 index 0000000000000000000000000000000000000000..499c94e779f6a7cbd6bd50362f28787ab131babc --- /dev/null +++ b/server/doc/sql_app/api/usb_logs.html @@ -0,0 +1,265 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.usb_logs API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.usb_logs</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from datetime import datetime +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# prefix used for all endpoints in this file +usblogs = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@usblogs.post("/usb-logs", response_model=schemas.USBLog) +def create_device_logs(log: schemas.USBTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from keyman detecting client. Parses timestamp into datetime object. + Finds if device and pc defined in message already exists and creates them if necessary. + Saves log into database + """ + dev = crud.find_device(db, log.device) + dat = datetime.strptime(log.timestamp, '%Y-%m-%d %H:%M:%S') + if dev is None: + dev = crud.create_device(db=db, device=log.device) + pc = crud.find_pc(db, log.username, log.hostname) + if pc is None: + pc = crud.create_pc(db=db, user=log.username, host=log.hostname) + + print(crud.create_device_logs(db=db, item=log, dev_id=dev.id, pc_id=pc.id, date=dat)) + + +@usblogs.post("/ld-logs", response_model=schemas.LDLog) +def create_ld_logs(log: schemas.LDTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from debugger detecting client. Parses timestamp into datetime object. + Finds if head device and body device defined in message already exists and creates them if necessary. + Saves log into database + """ + head_dev = crud.find_head_device(db, log.head_device) + body_dev = crud.find_body_device(db, log.body_device) + if head_dev is None: + crud.create_head_device(db, log.head_device) + if body_dev is None: + crud.create_body_device(db, log.body_device) + + pc = crud.find_pc(db, log.username, log.hostname) + if pc is None: + pc = crud.create_pc(db=db, user=log.username, host=log.hostname) + dat = datetime.strptime(log.timestamp, '%Y-%m-%d %H:%M:%S') + print(crud.create_ld_logs(db=db, item=log, head_id=head_dev.id, body_id=body_dev.id, pc_id=pc.id, date=dat)) + + +@usblogs.get("/logs", response_model=List[schemas.USBLog]) +def read_logs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all usb logs saved in database + """ + items = crud.get_logs(db, skip=skip, limit=limit) + return items + + +@usblogs.get("/logs/{device_id}", response_model=List[schemas.USBLog]) +def read_log(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific log by given id + """ + db_log = crud.get_log(db, device_id=device_id) + if db_log is None: + raise HTTPException(status_code=404, detail="Logs not found") + return db_log</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.usb_logs.create_device_logs"><code class="name flex"> +<span>def <span class="ident">create_device_logs</span></span>(<span>log: <a title="sql_app.schemas.USBTempBase" href="../schemas.html#sql_app.schemas.USBTempBase">USBTempBase</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from keyman detecting client. Parses timestamp into datetime object. +Finds if device and pc defined in message already exists and creates them if necessary. +Saves log into database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs.post("/usb-logs", response_model=schemas.USBLog) +def create_device_logs(log: schemas.USBTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from keyman detecting client. Parses timestamp into datetime object. + Finds if device and pc defined in message already exists and creates them if necessary. + Saves log into database + """ + dev = crud.find_device(db, log.device) + dat = datetime.strptime(log.timestamp, '%Y-%m-%d %H:%M:%S') + if dev is None: + dev = crud.create_device(db=db, device=log.device) + pc = crud.find_pc(db, log.username, log.hostname) + if pc is None: + pc = crud.create_pc(db=db, user=log.username, host=log.hostname) + + print(crud.create_device_logs(db=db, item=log, dev_id=dev.id, pc_id=pc.id, date=dat))</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs.create_ld_logs"><code class="name flex"> +<span>def <span class="ident">create_ld_logs</span></span>(<span>log: <a title="sql_app.schemas.LDTempBase" href="../schemas.html#sql_app.schemas.LDTempBase">LDTempBase</a>, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint called from debugger detecting client. Parses timestamp into datetime object. +Finds if head device and body device defined in message already exists and creates them if necessary. +Saves log into database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs.post("/ld-logs", response_model=schemas.LDLog) +def create_ld_logs(log: schemas.LDTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from debugger detecting client. Parses timestamp into datetime object. + Finds if head device and body device defined in message already exists and creates them if necessary. + Saves log into database + """ + head_dev = crud.find_head_device(db, log.head_device) + body_dev = crud.find_body_device(db, log.body_device) + if head_dev is None: + crud.create_head_device(db, log.head_device) + if body_dev is None: + crud.create_body_device(db, log.body_device) + + pc = crud.find_pc(db, log.username, log.hostname) + if pc is None: + pc = crud.create_pc(db=db, user=log.username, host=log.hostname) + dat = datetime.strptime(log.timestamp, '%Y-%m-%d %H:%M:%S') + print(crud.create_ld_logs(db=db, item=log, head_id=head_dev.id, body_id=body_dev.id, pc_id=pc.id, date=dat))</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs.read_log"><code class="name flex"> +<span>def <span class="ident">read_log</span></span>(<span>device_id: int, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific log by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs.get("/logs/{device_id}", response_model=List[schemas.USBLog]) +def read_log(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific log by given id + """ + db_log = crud.get_log(db, device_id=device_id) + if db_log is None: + raise HTTPException(status_code=404, detail="Logs not found") + return db_log</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs.read_logs"><code class="name flex"> +<span>def <span class="ident">read_logs</span></span>(<span>skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all usb logs saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs.get("/logs", response_model=List[schemas.USBLog]) +def read_logs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all usb logs saved in database + """ + items = crud.get_logs(db, skip=skip, limit=limit) + return items</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.usb_logs.create_device_logs" href="#sql_app.api.usb_logs.create_device_logs">create_device_logs</a></code></li> +<li><code><a title="sql_app.api.usb_logs.create_ld_logs" href="#sql_app.api.usb_logs.create_ld_logs">create_ld_logs</a></code></li> +<li><code><a title="sql_app.api.usb_logs.get_db" href="#sql_app.api.usb_logs.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.usb_logs.read_log" href="#sql_app.api.usb_logs.read_log">read_log</a></code></li> +<li><code><a title="sql_app.api.usb_logs.read_logs" href="#sql_app.api.usb_logs.read_logs">read_logs</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/api/usb_logs_web.html b/server/doc/sql_app/api/usb_logs_web.html new file mode 100644 index 0000000000000000000000000000000000000000..fb54ab69516178af64ee9f9784f4e3b609ca27e5 --- /dev/null +++ b/server/doc/sql_app/api/usb_logs_web.html @@ -0,0 +1,202 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.api.usb_logs_web API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.api.usb_logs_web</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from datetime import datetime +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="../templates/usb-logs") + +# prefix used for all endpoints in this file +usblogs_web = APIRouter(prefix="/api/v1") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@usblogs_web.get("/logs-web", response_class=HTMLResponse) +async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all usb logs currently saved in database with its pcs, teams and licenses. + """ + logs = crud.get_logs(db, skip=skip, limit=limit) + pcs = [] + for log in logs: + if log.pc_id not in pcs: + pcs.append(log.pc_id) + pc_obj = crud.find_pcs(db, pcs) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses}) + + +@usblogs_web.post("/logs-web", response_class=HTMLResponse) +async def filter_logs(request: Request, pc: str = Form("all"), team: str = Form("all"), lic: str = Form("all"), + skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint used for filtering usb logs by user given form inputs. + """ + log = crud.get_filtered_logs(db, pc, team, lic) + logs_ids = [] + for l in log: + logs_ids.append(l[0]) + logs = crud.find_filtered_logs(db, logs_ids) + pc_obj = crud.get_pcs(db, skip=skip, limit=limit) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses})</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.api.usb_logs_web.filter_logs"><code class="name flex"> +<span>async def <span class="ident">filter_logs</span></span>(<span>request: starlette.requests.Request, pc: str = Form(all), team: str = Form(all), lic: str = Form(all), skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Endpoint used for filtering usb logs by user given form inputs.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs_web.post("/logs-web", response_class=HTMLResponse) +async def filter_logs(request: Request, pc: str = Form("all"), team: str = Form("all"), lic: str = Form("all"), + skip: int = 0, limit: int = 100, + db: Session = Depends(get_db)): + """ + Endpoint used for filtering usb logs by user given form inputs. + """ + log = crud.get_filtered_logs(db, pc, team, lic) + logs_ids = [] + for l in log: + logs_ids.append(l[0]) + logs = crud.find_filtered_logs(db, logs_ids) + pc_obj = crud.get_pcs(db, skip=skip, limit=limit) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses})</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs_web.get_db"><code class="name flex"> +<span>def <span class="ident">get_db</span></span>(<span>)</span> +</code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close()</code></pre> +</details> +</dd> +<dt id="sql_app.api.usb_logs_web.read_logs"><code class="name flex"> +<span>async def <span class="ident">read_logs</span></span>(<span>request: starlette.requests.Request, skip: int = 0, limit: int = 100, db: sqlalchemy.orm.session.Session = Depends(get_db))</span> +</code></dt> +<dd> +<div class="desc"><p>Returns template with all usb logs currently saved in database with its pcs, teams and licenses.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">@usblogs_web.get("/logs-web", response_class=HTMLResponse) +async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns template with all usb logs currently saved in database with its pcs, teams and licenses. + """ + logs = crud.get_logs(db, skip=skip, limit=limit) + pcs = [] + for log in logs: + if log.pc_id not in pcs: + pcs.append(log.pc_id) + pc_obj = crud.find_pcs(db, pcs) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses})</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app.api" href="index.html">sql_app.api</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.api.usb_logs_web.filter_logs" href="#sql_app.api.usb_logs_web.filter_logs">filter_logs</a></code></li> +<li><code><a title="sql_app.api.usb_logs_web.get_db" href="#sql_app.api.usb_logs_web.get_db">get_db</a></code></li> +<li><code><a title="sql_app.api.usb_logs_web.read_logs" href="#sql_app.api.usb_logs_web.read_logs">read_logs</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/crud.html b/server/doc/sql_app/crud.html new file mode 100644 index 0000000000000000000000000000000000000000..b6620d0a89d8401dde0eecb5cf72e0fb4d82670d --- /dev/null +++ b/server/doc/sql_app/crud.html @@ -0,0 +1,1165 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.crud API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.crud</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from datetime import datetime, date + +from sqlalchemy.orm import Session +from sqlalchemy import and_, desc +from . import models, schemas + + +def get_device(db: Session, device_id: int): + """ + returns one specific devices by given id + """ + return db.query(models.Device).filter(models.Device.id == device_id).first() + + +def get_devices(db: Session, skip: int = 0, limit: int = 100): + """ + returns all devices in database + """ + return db.query(models.Device).offset(skip).limit(limit).all() + + +def find_device(db: Session, device: schemas.DeviceBase): + """ + finds one device with product_id, vendor_id and serial_number same as in given DeviceBase object + """ + return db.query(models.Device).filter(and_(models.Device.product_id == device.product_id, + models.Device.vendor_id == device.vendor_id, + models.Device.serial_number == device.serial_number)).first() + + +def create_device(db: Session, device: schemas.DeviceBase): + """ + creates new device with data from given DeviceBase object + """ + db_device = models.Device(vendor_id=device.vendor_id, product_id=device.product_id, + serial_number=device.serial_number, assigned=False) + db.add(db_device) + db.commit() + db.refresh(db_device) + return db_device + + +def get_license(db: Session, license_id: int): + """ + returns one specific license by given id + """ + return db.query(models.License).filter(models.License.id == license_id).first() + + +def get_licenses(db: Session, skip: int = 0, limit: int = 100): + """ + returns all licenses in database + """ + return db.query(models.License).offset(skip).limit(limit).all() + + +def find_license(db: Session, name: str): + """ + finds one license by given string name + """ + return db.query(models.License).filter(models.License.name == name).first() + + +def create_license(db: Session, name: str, expdate: date): + """ + creates new license with given name and expiration date + """ + db_license = models.License(name=name, expiration_date=expdate) + db.add(db_license) + db.commit() + db.refresh(db_license) + return db_license + + +def get_license_devices(db: Session, license_id: int): + """ + returns all entries in devices_licenses table + """ + return db.query(models.DeviceLicense).filter(models.DeviceLicense.license_id == license_id).all() + + +def create_device_license(db: Session, device: int, license: int, time: datetime): + """ + creates new entry in devices_licenses table with device id, license id and time. + """ + db_device_license = models.DeviceLicense(device_id=device, license_id=license, + assigned_datetime=time) + db.add(db_device_license) + db.commit() + db.refresh(db_device_license) + return db_device_license + + +def find_pc_by_username(db: Session, name: str): + """ + Finds one pc by given username + """ + return db.query(models.PC).filter(models.PC.username == name).first() + + +def get_pc(db: Session, pc_id: int): + """ + returns one specific pc by given id + """ + return db.query(models.PC).filter(models.PC.id == pc_id).first() + + +def update_pc(db: Session, pc_id: int, team: str): + """ + Function updates team of one specific pc + """ + old_pc = get_pc(db, pc_id) + team = get_team(db, int(team)) + new = {'id': old_pc.id, 'username': old_pc.username, 'hostname': old_pc.hostname, 'assigned': True, + 'team_id': team.id} + for key, value in new.items(): + setattr(old_pc, key, value) + db.commit() + db.refresh(old_pc) + return old_pc + + +def get_pcs(db: Session, skip: int = 0, limit: int = 100): + """ + returns all pcs in database + """ + return db.query(models.PC).offset(skip).limit(limit).all() + + +def find_pc(db: Session, username: str, hostname: str): + """ + Finds one pc with given username and hostname + """ + return db.query(models.PC).filter(and_(models.PC.username == username, + models.PC.hostname == hostname)).first() + + +def find_pc_by_name(db: Session, username: str): + """ + Finds one pc by its username + """ + return db.query(models.PC).filter(models.PC.username == username).first() + + +def find_pc_by_name_all(db: Session, username: str): + """ + Finds all pcs with same username + """ + return db.query(models.PC).filter(models.PC.username == username).offset(0).limit(100).all() + + +def find_pcs(db: Session, pcs: []): + """ + Finds all pcs with ids in given id array + """ + return db.query(models.PC).filter(models.PC.id.in_(pcs)).all() + + +def get_pcs_by_team(db: Session, team_id: int): + """ + returns all pcs in given team by team id + """ + return db.query(models.PC).filter(models.PC.team_id == team_id).all() + + +def create_pc(db: Session, user: str, host: str): + """ + creates new pc with given username and hostname + """ + db_pc = models.PC(username=user, hostname=host, assigned=False) + db.add(db_pc) + db.commit() + db.refresh(db_pc) + return db_pc + + +def get_team(db: Session, team_id: int): + """ + returns one specific team wit given id + """ + return db.query(models.Team).filter(models.Team.id == team_id).first() + + +def get_teams(db: Session, skip: int = 0, limit: int = 100): + """ + returns all teams currently saved in database + """ + return db.query(models.Team).offset(skip).limit(limit).all() + + +def find_team(db: Session, name: str): + """ + Finds one specific team by its name + """ + return db.query(models.Team).filter(models.Team.name == name).first() + + +def create_team(db: Session, name: str): + """ + Creates new team with given name + """ + db_team = models.Team(name=name) + db.add(db_team) + db.commit() + db.refresh(db_team) + return db_team + + +def get_head_device(db: Session, head_id: int): + """ + Returns one specific head device by given id + """ + return db.query(models.HeadDevice).filter(models.HeadDevice.id == head_id).first() + + +def get_head_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all head devices saved in database + """ + return db.query(models.HeadDevice).offset(skip).limit(limit).all() + + +def find_head_device(db: Session, serial: schemas.HeadDeviceBase): + """ + Finds one head device by its serial number + """ + return db.query(models.HeadDevice).filter(models.HeadDevice.serial_number == serial.serial_number).first() + + +def create_head_device(db: Session, log: schemas.HeadDeviceBase): + """ + Creates new head device + """ + db_head = models.HeadDevice(serial_number=log.serial_number) + db.add(db_head) + db.commit() + db.refresh(db_head) + return db_head + + +def get_body_device(db: Session, body_id: int): + """ + Returns one specific body device by given id + """ + return db.query(models.BodyDevice).filter(models.BodyDevice.id == body_id).first() + + +def get_body_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all body devices saved in database + """ + return db.query(models.BodyDevice).offset(skip).limit(limit).all() + + +def find_body_device(db: Session, serial: schemas.BodyDeviceBase): + """ + Finds one body device by its serial number + """ + return db.query(models.BodyDevice).filter(models.BodyDevice.serial_number == serial.serial_number).first() + + +def create_body_device(db: Session, log: schemas.BodyDeviceBase): + """ + Creates new Body device + """ + db_body = models.BodyDevice(serial_number=log.serial_number) + db.add(db_body) + db.commit() + db.refresh(db_body) + return db_body + + +def get_ld_logs(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all ld debugger logs in database + """ + return db.query(models.LDLog).offset(skip).limit(limit).all() + + +def create_ld_logs(db: Session, item: schemas.LDTempBase, head_id: int, body_id: int, pc_id: int, date: datetime): + """ + Creates new ld log for ld_logs database table + """ + db_ld = models.LDLog(pc_id=pc_id, timestamp=date, status=item.status, head_id=head_id, body_id=body_id) + db.add(db_ld) + db.commit() + db.refresh(db_ld) + return db_ld + + +def get_logs(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database ordered by timestamp + """ + return db.query(models.USBLog).order_by(desc(models.USBLog.timestamp)).offset(skip).limit(limit).all() + + +def get_log(db: Session, device_id: int, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database sorted by id + """ + return db.query(models.USBLog).filter(models.USBLog.device_id == device_id).offset(skip).limit(limit).all() + + +def find_filtered_logs(db: Session, logs: []): + """ + Returns all usb logs with ids in given id array. + """ + return db.query(models.USBLog).filter(models.USBLog.id.in_(logs)).order_by(desc(models.USBLog.timestamp)).all() + + +def get_filtered_logs(db: Session, pc: str, tema: str, lic: str): + """ + Function creates query string used for filtering by pc username, team name and license name. + Depending on selected filters assembles query string for database + """ + execute_string = "SELECT * FROM usb_logs AS logs" + if pc != "all": + pcs = find_pc_by_username(db, pc) + execute_string += " WHERE logs.pc_id = " + str(pcs.id) + if tema != "all": + team = find_team(db, tema) + pcs = get_pcs_by_team(db, team.id) + pc_ids = "(" + for p in pcs: + pc_ids += str(p.id) + ", " + def_pc_ids = pc_ids[:-2] + ")" + if pc != "all": + execute_string += " AND logs.pc_id IN " + def_pc_ids + else: + execute_string += " WHERE logs.pc_id IN " + def_pc_ids + if lic != "all": + license = find_license(db, lic) + device_licenses = get_license_devices(db, license.id) + dev_ids = "(" + for dev in device_licenses: + dev_ids += str(dev.device_id) + ", " + defin_ids = dev_ids[:-2] + ")" + if pc != "all" or tema != "all": + execute_string += " AND logs.device_id IN " + defin_ids + else: + execute_string += " WHERE logs.device_id IN " + defin_ids + + # executing assembled query string + result = db.execute(execute_string) + return result + + +def create_device_logs(db: Session, item: schemas.USBTempBase, dev_id: int, pc_id: int, date: datetime): + """ + Creates new USB log for usb_logs database table + """ + db_log = models.USBLog(pc_id=pc_id, timestamp=date, status=item.status, device_id=dev_id) + db.add(db_log) + db.commit() + db.refresh(db_log) + return db_log</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-functions">Functions</h2> +<dl> +<dt id="sql_app.crud.create_body_device"><code class="name flex"> +<span>def <span class="ident">create_body_device</span></span>(<span>db: sqlalchemy.orm.session.Session, log: <a title="sql_app.schemas.BodyDeviceBase" href="schemas.html#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>Creates new Body device</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_body_device(db: Session, log: schemas.BodyDeviceBase): + """ + Creates new Body device + """ + db_body = models.BodyDevice(serial_number=log.serial_number) + db.add(db_body) + db.commit() + db.refresh(db_body) + return db_body</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_device"><code class="name flex"> +<span>def <span class="ident">create_device</span></span>(<span>db: sqlalchemy.orm.session.Session, device: <a title="sql_app.schemas.DeviceBase" href="schemas.html#sql_app.schemas.DeviceBase">DeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>creates new device with data from given DeviceBase object</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_device(db: Session, device: schemas.DeviceBase): + """ + creates new device with data from given DeviceBase object + """ + db_device = models.Device(vendor_id=device.vendor_id, product_id=device.product_id, + serial_number=device.serial_number, assigned=False) + db.add(db_device) + db.commit() + db.refresh(db_device) + return db_device</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_device_license"><code class="name flex"> +<span>def <span class="ident">create_device_license</span></span>(<span>db: sqlalchemy.orm.session.Session, device: int, license: int, time: datetime.datetime)</span> +</code></dt> +<dd> +<div class="desc"><p>creates new entry in devices_licenses table with device id, license id and time.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_device_license(db: Session, device: int, license: int, time: datetime): + """ + creates new entry in devices_licenses table with device id, license id and time. + """ + db_device_license = models.DeviceLicense(device_id=device, license_id=license, + assigned_datetime=time) + db.add(db_device_license) + db.commit() + db.refresh(db_device_license) + return db_device_license</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_device_logs"><code class="name flex"> +<span>def <span class="ident">create_device_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, item: <a title="sql_app.schemas.USBTempBase" href="schemas.html#sql_app.schemas.USBTempBase">USBTempBase</a>, dev_id: int, pc_id: int, date: datetime.datetime)</span> +</code></dt> +<dd> +<div class="desc"><p>Creates new USB log for usb_logs database table</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_device_logs(db: Session, item: schemas.USBTempBase, dev_id: int, pc_id: int, date: datetime): + """ + Creates new USB log for usb_logs database table + """ + db_log = models.USBLog(pc_id=pc_id, timestamp=date, status=item.status, device_id=dev_id) + db.add(db_log) + db.commit() + db.refresh(db_log) + return db_log</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_head_device"><code class="name flex"> +<span>def <span class="ident">create_head_device</span></span>(<span>db: sqlalchemy.orm.session.Session, log: <a title="sql_app.schemas.HeadDeviceBase" href="schemas.html#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>Creates new head device</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_head_device(db: Session, log: schemas.HeadDeviceBase): + """ + Creates new head device + """ + db_head = models.HeadDevice(serial_number=log.serial_number) + db.add(db_head) + db.commit() + db.refresh(db_head) + return db_head</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_ld_logs"><code class="name flex"> +<span>def <span class="ident">create_ld_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, item: <a title="sql_app.schemas.LDTempBase" href="schemas.html#sql_app.schemas.LDTempBase">LDTempBase</a>, head_id: int, body_id: int, pc_id: int, date: datetime.datetime)</span> +</code></dt> +<dd> +<div class="desc"><p>Creates new ld log for ld_logs database table</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_ld_logs(db: Session, item: schemas.LDTempBase, head_id: int, body_id: int, pc_id: int, date: datetime): + """ + Creates new ld log for ld_logs database table + """ + db_ld = models.LDLog(pc_id=pc_id, timestamp=date, status=item.status, head_id=head_id, body_id=body_id) + db.add(db_ld) + db.commit() + db.refresh(db_ld) + return db_ld</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_license"><code class="name flex"> +<span>def <span class="ident">create_license</span></span>(<span>db: sqlalchemy.orm.session.Session, name: str, expdate: datetime.date)</span> +</code></dt> +<dd> +<div class="desc"><p>creates new license with given name and expiration date</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_license(db: Session, name: str, expdate: date): + """ + creates new license with given name and expiration date + """ + db_license = models.License(name=name, expiration_date=expdate) + db.add(db_license) + db.commit() + db.refresh(db_license) + return db_license</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_pc"><code class="name flex"> +<span>def <span class="ident">create_pc</span></span>(<span>db: sqlalchemy.orm.session.Session, user: str, host: str)</span> +</code></dt> +<dd> +<div class="desc"><p>creates new pc with given username and hostname</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_pc(db: Session, user: str, host: str): + """ + creates new pc with given username and hostname + """ + db_pc = models.PC(username=user, hostname=host, assigned=False) + db.add(db_pc) + db.commit() + db.refresh(db_pc) + return db_pc</code></pre> +</details> +</dd> +<dt id="sql_app.crud.create_team"><code class="name flex"> +<span>def <span class="ident">create_team</span></span>(<span>db: sqlalchemy.orm.session.Session, name: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Creates new team with given name</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def create_team(db: Session, name: str): + """ + Creates new team with given name + """ + db_team = models.Team(name=name) + db.add(db_team) + db.commit() + db.refresh(db_team) + return db_team</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_body_device"><code class="name flex"> +<span>def <span class="ident">find_body_device</span></span>(<span>db: sqlalchemy.orm.session.Session, serial: <a title="sql_app.schemas.BodyDeviceBase" href="schemas.html#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one body device by its serial number</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_body_device(db: Session, serial: schemas.BodyDeviceBase): + """ + Finds one body device by its serial number + """ + return db.query(models.BodyDevice).filter(models.BodyDevice.serial_number == serial.serial_number).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_device"><code class="name flex"> +<span>def <span class="ident">find_device</span></span>(<span>db: sqlalchemy.orm.session.Session, device: <a title="sql_app.schemas.DeviceBase" href="schemas.html#sql_app.schemas.DeviceBase">DeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>finds one device with product_id, vendor_id and serial_number same as in given DeviceBase object</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_device(db: Session, device: schemas.DeviceBase): + """ + finds one device with product_id, vendor_id and serial_number same as in given DeviceBase object + """ + return db.query(models.Device).filter(and_(models.Device.product_id == device.product_id, + models.Device.vendor_id == device.vendor_id, + models.Device.serial_number == device.serial_number)).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_filtered_logs"><code class="name flex"> +<span>def <span class="ident">find_filtered_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, logs: [])</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all usb logs with ids in given id array.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_filtered_logs(db: Session, logs: []): + """ + Returns all usb logs with ids in given id array. + """ + return db.query(models.USBLog).filter(models.USBLog.id.in_(logs)).order_by(desc(models.USBLog.timestamp)).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_head_device"><code class="name flex"> +<span>def <span class="ident">find_head_device</span></span>(<span>db: sqlalchemy.orm.session.Session, serial: <a title="sql_app.schemas.HeadDeviceBase" href="schemas.html#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a>)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one head device by its serial number</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_head_device(db: Session, serial: schemas.HeadDeviceBase): + """ + Finds one head device by its serial number + """ + return db.query(models.HeadDevice).filter(models.HeadDevice.serial_number == serial.serial_number).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_license"><code class="name flex"> +<span>def <span class="ident">find_license</span></span>(<span>db: sqlalchemy.orm.session.Session, name: str)</span> +</code></dt> +<dd> +<div class="desc"><p>finds one license by given string name</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_license(db: Session, name: str): + """ + finds one license by given string name + """ + return db.query(models.License).filter(models.License.name == name).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_pc"><code class="name flex"> +<span>def <span class="ident">find_pc</span></span>(<span>db: sqlalchemy.orm.session.Session, username: str, hostname: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one pc with given username and hostname</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_pc(db: Session, username: str, hostname: str): + """ + Finds one pc with given username and hostname + """ + return db.query(models.PC).filter(and_(models.PC.username == username, + models.PC.hostname == hostname)).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_pc_by_name"><code class="name flex"> +<span>def <span class="ident">find_pc_by_name</span></span>(<span>db: sqlalchemy.orm.session.Session, username: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one pc by its username</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_pc_by_name(db: Session, username: str): + """ + Finds one pc by its username + """ + return db.query(models.PC).filter(models.PC.username == username).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_pc_by_name_all"><code class="name flex"> +<span>def <span class="ident">find_pc_by_name_all</span></span>(<span>db: sqlalchemy.orm.session.Session, username: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds all pcs with same username</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_pc_by_name_all(db: Session, username: str): + """ + Finds all pcs with same username + """ + return db.query(models.PC).filter(models.PC.username == username).offset(0).limit(100).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_pc_by_username"><code class="name flex"> +<span>def <span class="ident">find_pc_by_username</span></span>(<span>db: sqlalchemy.orm.session.Session, name: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one pc by given username</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_pc_by_username(db: Session, name: str): + """ + Finds one pc by given username + """ + return db.query(models.PC).filter(models.PC.username == name).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_pcs"><code class="name flex"> +<span>def <span class="ident">find_pcs</span></span>(<span>db: sqlalchemy.orm.session.Session, pcs: [])</span> +</code></dt> +<dd> +<div class="desc"><p>Finds all pcs with ids in given id array</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_pcs(db: Session, pcs: []): + """ + Finds all pcs with ids in given id array + """ + return db.query(models.PC).filter(models.PC.id.in_(pcs)).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.find_team"><code class="name flex"> +<span>def <span class="ident">find_team</span></span>(<span>db: sqlalchemy.orm.session.Session, name: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Finds one specific team by its name</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def find_team(db: Session, name: str): + """ + Finds one specific team by its name + """ + return db.query(models.Team).filter(models.Team.name == name).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_body_device"><code class="name flex"> +<span>def <span class="ident">get_body_device</span></span>(<span>db: sqlalchemy.orm.session.Session, body_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific body device by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_body_device(db: Session, body_id: int): + """ + Returns one specific body device by given id + """ + return db.query(models.BodyDevice).filter(models.BodyDevice.id == body_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_body_devices"><code class="name flex"> +<span>def <span class="ident">get_body_devices</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all body devices saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_body_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all body devices saved in database + """ + return db.query(models.BodyDevice).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_device"><code class="name flex"> +<span>def <span class="ident">get_device</span></span>(<span>db: sqlalchemy.orm.session.Session, device_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns one specific devices by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_device(db: Session, device_id: int): + """ + returns one specific devices by given id + """ + return db.query(models.Device).filter(models.Device.id == device_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_devices"><code class="name flex"> +<span>def <span class="ident">get_devices</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all devices in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_devices(db: Session, skip: int = 0, limit: int = 100): + """ + returns all devices in database + """ + return db.query(models.Device).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_filtered_logs"><code class="name flex"> +<span>def <span class="ident">get_filtered_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, pc: str, tema: str, lic: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Function creates query string used for filtering by pc username, team name and license name. +Depending on selected filters assembles query string for database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_filtered_logs(db: Session, pc: str, tema: str, lic: str): + """ + Function creates query string used for filtering by pc username, team name and license name. + Depending on selected filters assembles query string for database + """ + execute_string = "SELECT * FROM usb_logs AS logs" + if pc != "all": + pcs = find_pc_by_username(db, pc) + execute_string += " WHERE logs.pc_id = " + str(pcs.id) + if tema != "all": + team = find_team(db, tema) + pcs = get_pcs_by_team(db, team.id) + pc_ids = "(" + for p in pcs: + pc_ids += str(p.id) + ", " + def_pc_ids = pc_ids[:-2] + ")" + if pc != "all": + execute_string += " AND logs.pc_id IN " + def_pc_ids + else: + execute_string += " WHERE logs.pc_id IN " + def_pc_ids + if lic != "all": + license = find_license(db, lic) + device_licenses = get_license_devices(db, license.id) + dev_ids = "(" + for dev in device_licenses: + dev_ids += str(dev.device_id) + ", " + defin_ids = dev_ids[:-2] + ")" + if pc != "all" or tema != "all": + execute_string += " AND logs.device_id IN " + defin_ids + else: + execute_string += " WHERE logs.device_id IN " + defin_ids + + # executing assembled query string + result = db.execute(execute_string) + return result</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_head_device"><code class="name flex"> +<span>def <span class="ident">get_head_device</span></span>(<span>db: sqlalchemy.orm.session.Session, head_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns one specific head device by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_head_device(db: Session, head_id: int): + """ + Returns one specific head device by given id + """ + return db.query(models.HeadDevice).filter(models.HeadDevice.id == head_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_head_devices"><code class="name flex"> +<span>def <span class="ident">get_head_devices</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all head devices saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_head_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all head devices saved in database + """ + return db.query(models.HeadDevice).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_ld_logs"><code class="name flex"> +<span>def <span class="ident">get_ld_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all ld debugger logs in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_ld_logs(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all ld debugger logs in database + """ + return db.query(models.LDLog).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_license"><code class="name flex"> +<span>def <span class="ident">get_license</span></span>(<span>db: sqlalchemy.orm.session.Session, license_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns one specific license by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_license(db: Session, license_id: int): + """ + returns one specific license by given id + """ + return db.query(models.License).filter(models.License.id == license_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_license_devices"><code class="name flex"> +<span>def <span class="ident">get_license_devices</span></span>(<span>db: sqlalchemy.orm.session.Session, license_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all entries in devices_licenses table</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_license_devices(db: Session, license_id: int): + """ + returns all entries in devices_licenses table + """ + return db.query(models.DeviceLicense).filter(models.DeviceLicense.license_id == license_id).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_licenses"><code class="name flex"> +<span>def <span class="ident">get_licenses</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all licenses in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_licenses(db: Session, skip: int = 0, limit: int = 100): + """ + returns all licenses in database + """ + return db.query(models.License).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_log"><code class="name flex"> +<span>def <span class="ident">get_log</span></span>(<span>db: sqlalchemy.orm.session.Session, device_id: int, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all usb logs in database sorted by id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_log(db: Session, device_id: int, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database sorted by id + """ + return db.query(models.USBLog).filter(models.USBLog.device_id == device_id).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_logs"><code class="name flex"> +<span>def <span class="ident">get_logs</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>Returns all usb logs in database ordered by timestamp</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_logs(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database ordered by timestamp + """ + return db.query(models.USBLog).order_by(desc(models.USBLog.timestamp)).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_pc"><code class="name flex"> +<span>def <span class="ident">get_pc</span></span>(<span>db: sqlalchemy.orm.session.Session, pc_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns one specific pc by given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_pc(db: Session, pc_id: int): + """ + returns one specific pc by given id + """ + return db.query(models.PC).filter(models.PC.id == pc_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_pcs"><code class="name flex"> +<span>def <span class="ident">get_pcs</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all pcs in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_pcs(db: Session, skip: int = 0, limit: int = 100): + """ + returns all pcs in database + """ + return db.query(models.PC).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_pcs_by_team"><code class="name flex"> +<span>def <span class="ident">get_pcs_by_team</span></span>(<span>db: sqlalchemy.orm.session.Session, team_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all pcs in given team by team id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_pcs_by_team(db: Session, team_id: int): + """ + returns all pcs in given team by team id + """ + return db.query(models.PC).filter(models.PC.team_id == team_id).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_team"><code class="name flex"> +<span>def <span class="ident">get_team</span></span>(<span>db: sqlalchemy.orm.session.Session, team_id: int)</span> +</code></dt> +<dd> +<div class="desc"><p>returns one specific team wit given id</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_team(db: Session, team_id: int): + """ + returns one specific team wit given id + """ + return db.query(models.Team).filter(models.Team.id == team_id).first()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.get_teams"><code class="name flex"> +<span>def <span class="ident">get_teams</span></span>(<span>db: sqlalchemy.orm.session.Session, skip: int = 0, limit: int = 100)</span> +</code></dt> +<dd> +<div class="desc"><p>returns all teams currently saved in database</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def get_teams(db: Session, skip: int = 0, limit: int = 100): + """ + returns all teams currently saved in database + """ + return db.query(models.Team).offset(skip).limit(limit).all()</code></pre> +</details> +</dd> +<dt id="sql_app.crud.update_pc"><code class="name flex"> +<span>def <span class="ident">update_pc</span></span>(<span>db: sqlalchemy.orm.session.Session, pc_id: int, team: str)</span> +</code></dt> +<dd> +<div class="desc"><p>Function updates team of one specific pc</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def update_pc(db: Session, pc_id: int, team: str): + """ + Function updates team of one specific pc + """ + old_pc = get_pc(db, pc_id) + team = get_team(db, int(team)) + new = {'id': old_pc.id, 'username': old_pc.username, 'hostname': old_pc.hostname, 'assigned': True, + 'team_id': team.id} + for key, value in new.items(): + setattr(old_pc, key, value) + db.commit() + db.refresh(old_pc) + return old_pc</code></pre> +</details> +</dd> +</dl> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="index.html">sql_app</a></code></li> +</ul> +</li> +<li><h3><a href="#header-functions">Functions</a></h3> +<ul class=""> +<li><code><a title="sql_app.crud.create_body_device" href="#sql_app.crud.create_body_device">create_body_device</a></code></li> +<li><code><a title="sql_app.crud.create_device" href="#sql_app.crud.create_device">create_device</a></code></li> +<li><code><a title="sql_app.crud.create_device_license" href="#sql_app.crud.create_device_license">create_device_license</a></code></li> +<li><code><a title="sql_app.crud.create_device_logs" href="#sql_app.crud.create_device_logs">create_device_logs</a></code></li> +<li><code><a title="sql_app.crud.create_head_device" href="#sql_app.crud.create_head_device">create_head_device</a></code></li> +<li><code><a title="sql_app.crud.create_ld_logs" href="#sql_app.crud.create_ld_logs">create_ld_logs</a></code></li> +<li><code><a title="sql_app.crud.create_license" href="#sql_app.crud.create_license">create_license</a></code></li> +<li><code><a title="sql_app.crud.create_pc" href="#sql_app.crud.create_pc">create_pc</a></code></li> +<li><code><a title="sql_app.crud.create_team" href="#sql_app.crud.create_team">create_team</a></code></li> +<li><code><a title="sql_app.crud.find_body_device" href="#sql_app.crud.find_body_device">find_body_device</a></code></li> +<li><code><a title="sql_app.crud.find_device" href="#sql_app.crud.find_device">find_device</a></code></li> +<li><code><a title="sql_app.crud.find_filtered_logs" href="#sql_app.crud.find_filtered_logs">find_filtered_logs</a></code></li> +<li><code><a title="sql_app.crud.find_head_device" href="#sql_app.crud.find_head_device">find_head_device</a></code></li> +<li><code><a title="sql_app.crud.find_license" href="#sql_app.crud.find_license">find_license</a></code></li> +<li><code><a title="sql_app.crud.find_pc" href="#sql_app.crud.find_pc">find_pc</a></code></li> +<li><code><a title="sql_app.crud.find_pc_by_name" href="#sql_app.crud.find_pc_by_name">find_pc_by_name</a></code></li> +<li><code><a title="sql_app.crud.find_pc_by_name_all" href="#sql_app.crud.find_pc_by_name_all">find_pc_by_name_all</a></code></li> +<li><code><a title="sql_app.crud.find_pc_by_username" href="#sql_app.crud.find_pc_by_username">find_pc_by_username</a></code></li> +<li><code><a title="sql_app.crud.find_pcs" href="#sql_app.crud.find_pcs">find_pcs</a></code></li> +<li><code><a title="sql_app.crud.find_team" href="#sql_app.crud.find_team">find_team</a></code></li> +<li><code><a title="sql_app.crud.get_body_device" href="#sql_app.crud.get_body_device">get_body_device</a></code></li> +<li><code><a title="sql_app.crud.get_body_devices" href="#sql_app.crud.get_body_devices">get_body_devices</a></code></li> +<li><code><a title="sql_app.crud.get_device" href="#sql_app.crud.get_device">get_device</a></code></li> +<li><code><a title="sql_app.crud.get_devices" href="#sql_app.crud.get_devices">get_devices</a></code></li> +<li><code><a title="sql_app.crud.get_filtered_logs" href="#sql_app.crud.get_filtered_logs">get_filtered_logs</a></code></li> +<li><code><a title="sql_app.crud.get_head_device" href="#sql_app.crud.get_head_device">get_head_device</a></code></li> +<li><code><a title="sql_app.crud.get_head_devices" href="#sql_app.crud.get_head_devices">get_head_devices</a></code></li> +<li><code><a title="sql_app.crud.get_ld_logs" href="#sql_app.crud.get_ld_logs">get_ld_logs</a></code></li> +<li><code><a title="sql_app.crud.get_license" href="#sql_app.crud.get_license">get_license</a></code></li> +<li><code><a title="sql_app.crud.get_license_devices" href="#sql_app.crud.get_license_devices">get_license_devices</a></code></li> +<li><code><a title="sql_app.crud.get_licenses" href="#sql_app.crud.get_licenses">get_licenses</a></code></li> +<li><code><a title="sql_app.crud.get_log" href="#sql_app.crud.get_log">get_log</a></code></li> +<li><code><a title="sql_app.crud.get_logs" href="#sql_app.crud.get_logs">get_logs</a></code></li> +<li><code><a title="sql_app.crud.get_pc" href="#sql_app.crud.get_pc">get_pc</a></code></li> +<li><code><a title="sql_app.crud.get_pcs" href="#sql_app.crud.get_pcs">get_pcs</a></code></li> +<li><code><a title="sql_app.crud.get_pcs_by_team" href="#sql_app.crud.get_pcs_by_team">get_pcs_by_team</a></code></li> +<li><code><a title="sql_app.crud.get_team" href="#sql_app.crud.get_team">get_team</a></code></li> +<li><code><a title="sql_app.crud.get_teams" href="#sql_app.crud.get_teams">get_teams</a></code></li> +<li><code><a title="sql_app.crud.update_pc" href="#sql_app.crud.update_pc">update_pc</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/database.html b/server/doc/sql_app/database.html new file mode 100644 index 0000000000000000000000000000000000000000..fc8a9c79d3081fa343081cf9076d9b631d7cdda7 --- /dev/null +++ b/server/doc/sql_app/database.html @@ -0,0 +1,100 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.database API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.database</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from sqlalchemy import create_engine +from sqlalchemy.ext.declarative import declarative_base +from sqlalchemy.orm import sessionmaker + + + +# used mainly for testing purposes. Creates local sqllite data file +SQLALCHEMY_DATABASE_URL = "sqlite:///./sql_app.db" +engine = create_engine( + SQLALCHEMY_DATABASE_URL, connect_args={"check_same_thread": False} +) +''' + +# Defining connection url with postgresql database +SQLALCHEMY_DATABASE_URL = "postgresql://postgres:postgres@10.5.0.5:5432/usb_api_db" + +# Creating engine for database communication +engine = create_engine( + SQLALCHEMY_DATABASE_URL +) +''' +# Session maker for data transmissions +SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine) + +Base = declarative_base()</code></pre> +</details> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-variables">Global variables</h2> +<dl> +<dt id="sql_app.database.engine"><code class="name">var <span class="ident">engine</span></code></dt> +<dd> +<div class="desc"><h1 id="defining-connection-url-with-postgresql-database">Defining connection url with postgresql database</h1> +<p>SQLALCHEMY_DATABASE_URL = "postgresql://postgres:postgres@10.5.0.5:5432/usb_api_db"</p> +<h1 id="creating-engine-for-database-communication">Creating engine for database communication</h1> +<p>engine = create_engine( +SQLALCHEMY_DATABASE_URL +)</p></div> +</dd> +</dl> +</section> +<section> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="index.html">sql_app</a></code></li> +</ul> +</li> +<li><h3><a href="#header-variables">Global variables</a></h3> +<ul class=""> +<li><code><a title="sql_app.database.engine" href="#sql_app.database.engine">engine</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/documentation.html b/server/doc/sql_app/documentation.html new file mode 100644 index 0000000000000000000000000000000000000000..3807832987eb877544f6cbf8f0ac58cfcac90020 --- /dev/null +++ b/server/doc/sql_app/documentation.html @@ -0,0 +1,85 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Package <code>sql_app</code></h1> +</header> +<section id="section-intro"> +</section> +<section> +<h2 class="section-title" id="header-submodules">Sub-modules</h2> +<dl> +<dt><code class="name"><a title="sql_app.api" href="api/index.html">sql_app.api</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.crud" href="crud.html">sql_app.crud</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.database" href="database.html">sql_app.database</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.main" href="main.html">sql_app.main</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.models" href="models.html">sql_app.models</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt><code class="name"><a title="sql_app.schemas" href="schemas.html">sql_app.schemas</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3><a href="#header-submodules">Sub-modules</a></h3> +<ul> +<li><code><a title="sql_app.api" href="api/index.html">sql_app.api</a></code></li> +<li><code><a title="sql_app.crud" href="crud.html">sql_app.crud</a></code></li> +<li><code><a title="sql_app.database" href="database.html">sql_app.database</a></code></li> +<li><code><a title="sql_app.main" href="main.html">sql_app.main</a></code></li> +<li><code><a title="sql_app.models" href="models.html">sql_app.models</a></code></li> +<li><code><a title="sql_app.schemas" href="schemas.html">sql_app.schemas</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/main.html b/server/doc/sql_app/main.html new file mode 100644 index 0000000000000000000000000000000000000000..fabf34b096043ef2accea2959a0069bd6910def2 --- /dev/null +++ b/server/doc/sql_app/main.html @@ -0,0 +1,91 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.main API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.main</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">import uvicorn +from sql_app.api.devices import device +from sql_app.api.devices_web import device_web +from sql_app.api.licenses import licenses +from sql_app.api.licenses_web import licenses_web +from sql_app.api.pcs import pcs +from sql_app.api.pcs_web import pcs_web +from sql_app.api.usb_logs import usblogs +from sql_app.api.usb_logs_web import usblogs_web +from sql_app.api.teams import teams +from sql_app.api.teams_web import teams_web +from fastapi import FastAPI + + +app = FastAPI() + +# including routers for endpoints used by clients +app.include_router(device) +app.include_router(licenses) +app.include_router(pcs) +app.include_router(usblogs) +app.include_router(teams) + +# including routers for endpoints called from web +app.include_router(device_web) +app.include_router(licenses_web) +app.include_router(pcs_web) +app.include_router(teams_web) +app.include_router(usblogs_web) + + +if __name__ == "__main__": + uvicorn.run(app, host="192.168.0.22", port=8000)</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="index.html">sql_app</a></code></li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/models.html b/server/doc/sql_app/models.html new file mode 100644 index 0000000000000000000000000000000000000000..6cc705a63a85b343fa0a624ea3d7623955fac395 --- /dev/null +++ b/server/doc/sql_app/models.html @@ -0,0 +1,1911 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.models API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.models</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from sqlalchemy import Boolean, Column, ForeignKey, Integer, String, DateTime +from sqlalchemy.orm import relationship +from sqlalchemy.sql import func +from .database import Base + + +class Device(Base): + """ + Class defining database table devices + """ + __tablename__ = "devices" + + id = Column(Integer, primary_key=True, index=True) + vendor_id = Column(String, index=True, nullable=False) + product_id = Column(String, index=True, nullable=False) + serial_number = Column(String, index=True, nullable=False) + assigned = Column(Boolean, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with usb_logs and licenses + # tables + logs = relationship("USBLog", back_populates="device") + licenses = relationship("DeviceLicense", back_populates="device_lic") + + +class USBLog(Base): + """ + Class defining database table usb_logs + """ + __tablename__ = "usb_logs" + + id = Column(Integer, primary_key=True, index=True) + pc_id = Column(Integer, ForeignKey("pc.id")) + timestamp = Column(DateTime(timezone=True), server_default=func.now()) + status = Column(String, index=True, nullable=False) + device_id = Column(Integer, ForeignKey("devices.id")) + + # relationships for foreign keys, thus connecting table with devices and pc + # tables + device = relationship("Device", back_populates="logs") + pc = relationship("PC", back_populates="logs_pc") + + +class License(Base): + """ + Class defining database table licenses + """ + __tablename__ = "licenses" + + id = Column(Integer, primary_key=True, index=True) + name = Column(String, index=True, nullable=False) + expiration_date = Column(DateTime(timezone=True), server_default=func.now()) + + # relationships for foreign keys, thus connecting table with devices table + devices = relationship("DeviceLicense", back_populates="licenses") + + +class DeviceLicense(Base): + """ + Class defining database table devices_licenses + """ + __tablename__ = "devices_licenses" + + id = Column(Integer, primary_key=True, index=True) + device_id = Column(Integer, ForeignKey("devices.id")) + license_id = Column(Integer, ForeignKey("licenses.id")) + assigned_datetime = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with devices and licenses + # tables + device_lic = relationship("Device", back_populates="licenses") + licenses = relationship("License", back_populates="devices") + + +class PC(Base): + """ + Class defining database table pc + """ + __tablename__ = "pc" + + id = Column(Integer, primary_key=True, index=True) + username = Column(String, index=True, nullable=False) + hostname = Column(String, index=True, nullable=False) + assigned = Column(Boolean, index=True, nullable=False) + team_id = Column(Integer, ForeignKey("teams.id")) + + # relationships for foreign keys, thus connecting table with teams, usb_logs and ld_logs + # tables + team = relationship("Team", back_populates="pcs") + logs_pc = relationship("USBLog", back_populates="pc") + ld_pc = relationship("LDLog", back_populates="ldpc") + + +class Team(Base): + """ + Class defining database table teams + """ + __tablename__ = "teams" + + id = Column(Integer, primary_key=True, index=True) + name = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with pc table + pcs = relationship("PC", back_populates="team") + + +class HeadDevice(Base): + """ + Class defining database table head_devices + """ + __tablename__ = "head_devices" + + id = Column(Integer, primary_key=True, index=True) + serial_number = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with ld_logs table + h_logs = relationship("LDLog", back_populates="head_device") + + +class BodyDevice(Base): + """ + Class defining database table body_devices + """ + __tablename__ = "body_devices" + + id = Column(Integer, primary_key=True, index=True) + serial_number = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with ld_logs table + b_logs = relationship("LDLog", back_populates="body_device") + + +class LDLog(Base): + """ + Class defining database table ld_logs + """ + __tablename__ = "ld_logs" + + id = Column(Integer, primary_key=True, index=True) + pc_id = Column(Integer, ForeignKey("pc.id")) + timestamp = Column(DateTime(timezone=True), server_default=func.now()) + status = Column(String, index=True, nullable=False) + head_id = Column(Integer, ForeignKey("head_devices.id")) + body_id = Column(Integer, ForeignKey("body_devices.id")) + + # relationships for foreign keys, thus connecting table with pc, head_devices and body_devices + # tables + ldpc = relationship("PC", back_populates="ld_pc") + head_device = relationship("HeadDevice", back_populates="h_logs") + body_device = relationship("BodyDevice", back_populates="b_logs")</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-classes">Classes</h2> +<dl> +<dt id="sql_app.models.BodyDevice"><code class="flex name class"> +<span>class <span class="ident">BodyDevice</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table body_devices</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class BodyDevice(Base): + """ + Class defining database table body_devices + """ + __tablename__ = "body_devices" + + id = Column(Integer, primary_key=True, index=True) + serial_number = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with ld_logs table + b_logs = relationship("LDLog", back_populates="body_device")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.BodyDevice.b_logs"><code class="name">var <span class="ident">b_logs</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.BodyDevice.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.BodyDevice.serial_number"><code class="name">var <span class="ident">serial_number</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.Device"><code class="flex name class"> +<span>class <span class="ident">Device</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table devices</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class Device(Base): + """ + Class defining database table devices + """ + __tablename__ = "devices" + + id = Column(Integer, primary_key=True, index=True) + vendor_id = Column(String, index=True, nullable=False) + product_id = Column(String, index=True, nullable=False) + serial_number = Column(String, index=True, nullable=False) + assigned = Column(Boolean, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with usb_logs and licenses + # tables + logs = relationship("USBLog", back_populates="device") + licenses = relationship("DeviceLicense", back_populates="device_lic")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.Device.assigned"><code class="name">var <span class="ident">assigned</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.licenses"><code class="name">var <span class="ident">licenses</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.logs"><code class="name">var <span class="ident">logs</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.product_id"><code class="name">var <span class="ident">product_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.serial_number"><code class="name">var <span class="ident">serial_number</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Device.vendor_id"><code class="name">var <span class="ident">vendor_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.DeviceLicense"><code class="flex name class"> +<span>class <span class="ident">DeviceLicense</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table devices_licenses</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceLicense(Base): + """ + Class defining database table devices_licenses + """ + __tablename__ = "devices_licenses" + + id = Column(Integer, primary_key=True, index=True) + device_id = Column(Integer, ForeignKey("devices.id")) + license_id = Column(Integer, ForeignKey("licenses.id")) + assigned_datetime = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with devices and licenses + # tables + device_lic = relationship("Device", back_populates="licenses") + licenses = relationship("License", back_populates="devices")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.DeviceLicense.assigned_datetime"><code class="name">var <span class="ident">assigned_datetime</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.DeviceLicense.device_id"><code class="name">var <span class="ident">device_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.DeviceLicense.device_lic"><code class="name">var <span class="ident">device_lic</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.DeviceLicense.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.DeviceLicense.license_id"><code class="name">var <span class="ident">license_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.DeviceLicense.licenses"><code class="name">var <span class="ident">licenses</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.HeadDevice"><code class="flex name class"> +<span>class <span class="ident">HeadDevice</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table head_devices</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class HeadDevice(Base): + """ + Class defining database table head_devices + """ + __tablename__ = "head_devices" + + id = Column(Integer, primary_key=True, index=True) + serial_number = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with ld_logs table + h_logs = relationship("LDLog", back_populates="head_device")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.HeadDevice.h_logs"><code class="name">var <span class="ident">h_logs</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.HeadDevice.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.HeadDevice.serial_number"><code class="name">var <span class="ident">serial_number</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.LDLog"><code class="flex name class"> +<span>class <span class="ident">LDLog</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table ld_logs</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDLog(Base): + """ + Class defining database table ld_logs + """ + __tablename__ = "ld_logs" + + id = Column(Integer, primary_key=True, index=True) + pc_id = Column(Integer, ForeignKey("pc.id")) + timestamp = Column(DateTime(timezone=True), server_default=func.now()) + status = Column(String, index=True, nullable=False) + head_id = Column(Integer, ForeignKey("head_devices.id")) + body_id = Column(Integer, ForeignKey("body_devices.id")) + + # relationships for foreign keys, thus connecting table with pc, head_devices and body_devices + # tables + ldpc = relationship("PC", back_populates="ld_pc") + head_device = relationship("HeadDevice", back_populates="h_logs") + body_device = relationship("BodyDevice", back_populates="b_logs")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.LDLog.body_device"><code class="name">var <span class="ident">body_device</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.body_id"><code class="name">var <span class="ident">body_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.head_device"><code class="name">var <span class="ident">head_device</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.head_id"><code class="name">var <span class="ident">head_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.ldpc"><code class="name">var <span class="ident">ldpc</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.pc_id"><code class="name">var <span class="ident">pc_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.status"><code class="name">var <span class="ident">status</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.LDLog.timestamp"><code class="name">var <span class="ident">timestamp</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.License"><code class="flex name class"> +<span>class <span class="ident">License</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table licenses</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class License(Base): + """ + Class defining database table licenses + """ + __tablename__ = "licenses" + + id = Column(Integer, primary_key=True, index=True) + name = Column(String, index=True, nullable=False) + expiration_date = Column(DateTime(timezone=True), server_default=func.now()) + + # relationships for foreign keys, thus connecting table with devices table + devices = relationship("DeviceLicense", back_populates="licenses")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.License.devices"><code class="name">var <span class="ident">devices</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.License.expiration_date"><code class="name">var <span class="ident">expiration_date</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.License.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.License.name"><code class="name">var <span class="ident">name</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.PC"><code class="flex name class"> +<span>class <span class="ident">PC</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table pc</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class PC(Base): + """ + Class defining database table pc + """ + __tablename__ = "pc" + + id = Column(Integer, primary_key=True, index=True) + username = Column(String, index=True, nullable=False) + hostname = Column(String, index=True, nullable=False) + assigned = Column(Boolean, index=True, nullable=False) + team_id = Column(Integer, ForeignKey("teams.id")) + + # relationships for foreign keys, thus connecting table with teams, usb_logs and ld_logs + # tables + team = relationship("Team", back_populates="pcs") + logs_pc = relationship("USBLog", back_populates="pc") + ld_pc = relationship("LDLog", back_populates="ldpc")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.PC.assigned"><code class="name">var <span class="ident">assigned</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.hostname"><code class="name">var <span class="ident">hostname</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.ld_pc"><code class="name">var <span class="ident">ld_pc</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.logs_pc"><code class="name">var <span class="ident">logs_pc</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.team"><code class="name">var <span class="ident">team</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.team_id"><code class="name">var <span class="ident">team_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.PC.username"><code class="name">var <span class="ident">username</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.Team"><code class="flex name class"> +<span>class <span class="ident">Team</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table teams</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class Team(Base): + """ + Class defining database table teams + """ + __tablename__ = "teams" + + id = Column(Integer, primary_key=True, index=True) + name = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with pc table + pcs = relationship("PC", back_populates="team")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.Team.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Team.name"><code class="name">var <span class="ident">name</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.Team.pcs"><code class="name">var <span class="ident">pcs</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +<dt id="sql_app.models.USBLog"><code class="flex name class"> +<span>class <span class="ident">USBLog</span></span> +<span>(</span><span>**kwargs)</span> +</code></dt> +<dd> +<div class="desc"><p>Class defining database table usb_logs</p> +<p>A simple constructor that allows initialization from kwargs.</p> +<p>Sets attributes on the constructed instance using the names and +values in <code>kwargs</code>.</p> +<p>Only keys that are present as +attributes of the instance's class are allowed. These could be, +for example, any mapped columns or relationships.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBLog(Base): + """ + Class defining database table usb_logs + """ + __tablename__ = "usb_logs" + + id = Column(Integer, primary_key=True, index=True) + pc_id = Column(Integer, ForeignKey("pc.id")) + timestamp = Column(DateTime(timezone=True), server_default=func.now()) + status = Column(String, index=True, nullable=False) + device_id = Column(Integer, ForeignKey("devices.id")) + + # relationships for foreign keys, thus connecting table with devices and pc + # tables + device = relationship("Device", back_populates="logs") + pc = relationship("PC", back_populates="logs_pc")</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>sqlalchemy.orm.decl_api.Base</li> +</ul> +<h3>Instance variables</h3> +<dl> +<dt id="sql_app.models.USBLog.device"><code class="name">var <span class="ident">device</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.device_id"><code class="name">var <span class="ident">device_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.id"><code class="name">var <span class="ident">id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.pc"><code class="name">var <span class="ident">pc</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.pc_id"><code class="name">var <span class="ident">pc_id</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.status"><code class="name">var <span class="ident">status</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +<dt id="sql_app.models.USBLog.timestamp"><code class="name">var <span class="ident">timestamp</span></code></dt> +<dd> +<div class="desc"></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">def __get__(self, instance, owner): + if instance is None: + return self + + dict_ = instance_dict(instance) + if self._supports_population and self.key in dict_: + return dict_[self.key] + else: + try: + state = instance_state(instance) + except AttributeError as err: + util.raise_( + orm_exc.UnmappedInstanceError(instance), + replace_context=err, + ) + return self.impl.get(state, dict_)</code></pre> +</details> +</dd> +</dl> +</dd> +</dl> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="index.html">sql_app</a></code></li> +</ul> +</li> +<li><h3><a href="#header-classes">Classes</a></h3> +<ul> +<li> +<h4><code><a title="sql_app.models.BodyDevice" href="#sql_app.models.BodyDevice">BodyDevice</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.models.BodyDevice.b_logs" href="#sql_app.models.BodyDevice.b_logs">b_logs</a></code></li> +<li><code><a title="sql_app.models.BodyDevice.id" href="#sql_app.models.BodyDevice.id">id</a></code></li> +<li><code><a title="sql_app.models.BodyDevice.serial_number" href="#sql_app.models.BodyDevice.serial_number">serial_number</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.Device" href="#sql_app.models.Device">Device</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.models.Device.assigned" href="#sql_app.models.Device.assigned">assigned</a></code></li> +<li><code><a title="sql_app.models.Device.id" href="#sql_app.models.Device.id">id</a></code></li> +<li><code><a title="sql_app.models.Device.licenses" href="#sql_app.models.Device.licenses">licenses</a></code></li> +<li><code><a title="sql_app.models.Device.logs" href="#sql_app.models.Device.logs">logs</a></code></li> +<li><code><a title="sql_app.models.Device.product_id" href="#sql_app.models.Device.product_id">product_id</a></code></li> +<li><code><a title="sql_app.models.Device.serial_number" href="#sql_app.models.Device.serial_number">serial_number</a></code></li> +<li><code><a title="sql_app.models.Device.vendor_id" href="#sql_app.models.Device.vendor_id">vendor_id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.DeviceLicense" href="#sql_app.models.DeviceLicense">DeviceLicense</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.models.DeviceLicense.assigned_datetime" href="#sql_app.models.DeviceLicense.assigned_datetime">assigned_datetime</a></code></li> +<li><code><a title="sql_app.models.DeviceLicense.device_id" href="#sql_app.models.DeviceLicense.device_id">device_id</a></code></li> +<li><code><a title="sql_app.models.DeviceLicense.device_lic" href="#sql_app.models.DeviceLicense.device_lic">device_lic</a></code></li> +<li><code><a title="sql_app.models.DeviceLicense.id" href="#sql_app.models.DeviceLicense.id">id</a></code></li> +<li><code><a title="sql_app.models.DeviceLicense.license_id" href="#sql_app.models.DeviceLicense.license_id">license_id</a></code></li> +<li><code><a title="sql_app.models.DeviceLicense.licenses" href="#sql_app.models.DeviceLicense.licenses">licenses</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.HeadDevice" href="#sql_app.models.HeadDevice">HeadDevice</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.models.HeadDevice.h_logs" href="#sql_app.models.HeadDevice.h_logs">h_logs</a></code></li> +<li><code><a title="sql_app.models.HeadDevice.id" href="#sql_app.models.HeadDevice.id">id</a></code></li> +<li><code><a title="sql_app.models.HeadDevice.serial_number" href="#sql_app.models.HeadDevice.serial_number">serial_number</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.LDLog" href="#sql_app.models.LDLog">LDLog</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.models.LDLog.body_device" href="#sql_app.models.LDLog.body_device">body_device</a></code></li> +<li><code><a title="sql_app.models.LDLog.body_id" href="#sql_app.models.LDLog.body_id">body_id</a></code></li> +<li><code><a title="sql_app.models.LDLog.head_device" href="#sql_app.models.LDLog.head_device">head_device</a></code></li> +<li><code><a title="sql_app.models.LDLog.head_id" href="#sql_app.models.LDLog.head_id">head_id</a></code></li> +<li><code><a title="sql_app.models.LDLog.id" href="#sql_app.models.LDLog.id">id</a></code></li> +<li><code><a title="sql_app.models.LDLog.ldpc" href="#sql_app.models.LDLog.ldpc">ldpc</a></code></li> +<li><code><a title="sql_app.models.LDLog.pc_id" href="#sql_app.models.LDLog.pc_id">pc_id</a></code></li> +<li><code><a title="sql_app.models.LDLog.status" href="#sql_app.models.LDLog.status">status</a></code></li> +<li><code><a title="sql_app.models.LDLog.timestamp" href="#sql_app.models.LDLog.timestamp">timestamp</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.License" href="#sql_app.models.License">License</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.models.License.devices" href="#sql_app.models.License.devices">devices</a></code></li> +<li><code><a title="sql_app.models.License.expiration_date" href="#sql_app.models.License.expiration_date">expiration_date</a></code></li> +<li><code><a title="sql_app.models.License.id" href="#sql_app.models.License.id">id</a></code></li> +<li><code><a title="sql_app.models.License.name" href="#sql_app.models.License.name">name</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.PC" href="#sql_app.models.PC">PC</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.models.PC.assigned" href="#sql_app.models.PC.assigned">assigned</a></code></li> +<li><code><a title="sql_app.models.PC.hostname" href="#sql_app.models.PC.hostname">hostname</a></code></li> +<li><code><a title="sql_app.models.PC.id" href="#sql_app.models.PC.id">id</a></code></li> +<li><code><a title="sql_app.models.PC.ld_pc" href="#sql_app.models.PC.ld_pc">ld_pc</a></code></li> +<li><code><a title="sql_app.models.PC.logs_pc" href="#sql_app.models.PC.logs_pc">logs_pc</a></code></li> +<li><code><a title="sql_app.models.PC.team" href="#sql_app.models.PC.team">team</a></code></li> +<li><code><a title="sql_app.models.PC.team_id" href="#sql_app.models.PC.team_id">team_id</a></code></li> +<li><code><a title="sql_app.models.PC.username" href="#sql_app.models.PC.username">username</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.Team" href="#sql_app.models.Team">Team</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.models.Team.id" href="#sql_app.models.Team.id">id</a></code></li> +<li><code><a title="sql_app.models.Team.name" href="#sql_app.models.Team.name">name</a></code></li> +<li><code><a title="sql_app.models.Team.pcs" href="#sql_app.models.Team.pcs">pcs</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.models.USBLog" href="#sql_app.models.USBLog">USBLog</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.models.USBLog.device" href="#sql_app.models.USBLog.device">device</a></code></li> +<li><code><a title="sql_app.models.USBLog.device_id" href="#sql_app.models.USBLog.device_id">device_id</a></code></li> +<li><code><a title="sql_app.models.USBLog.id" href="#sql_app.models.USBLog.id">id</a></code></li> +<li><code><a title="sql_app.models.USBLog.pc" href="#sql_app.models.USBLog.pc">pc</a></code></li> +<li><code><a title="sql_app.models.USBLog.pc_id" href="#sql_app.models.USBLog.pc_id">pc_id</a></code></li> +<li><code><a title="sql_app.models.USBLog.status" href="#sql_app.models.USBLog.status">status</a></code></li> +<li><code><a title="sql_app.models.USBLog.timestamp" href="#sql_app.models.USBLog.timestamp">timestamp</a></code></li> +</ul> +</li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/doc/sql_app/schemas.html b/server/doc/sql_app/schemas.html new file mode 100644 index 0000000000000000000000000000000000000000..ffeb06ad564f37c611647446687629676155a8aa --- /dev/null +++ b/server/doc/sql_app/schemas.html @@ -0,0 +1,1808 @@ +<!doctype html> +<html lang="en"> +<head> +<meta charset="utf-8"> +<meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1" /> +<meta name="generator" content="pdoc 0.10.0" /> +<title>sql_app.schemas API documentation</title> +<meta name="description" content="" /> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/sanitize.min.css" integrity="sha256-PK9q560IAAa6WVRRh76LtCaI8pjTJ2z11v0miyNNjrs=" crossorigin> +<link rel="preload stylesheet" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/10up-sanitize.css/11.0.1/typography.min.css" integrity="sha256-7l/o7C8jubJiy74VsKTidCy1yBkRtiUGbVkYBylBqUg=" crossorigin> +<link rel="stylesheet preload" as="style" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/styles/github.min.css" crossorigin> +<style>:root{--highlight-color:#fe9}.flex{display:flex !important}body{line-height:1.5em}#content{padding:20px}#sidebar{padding:30px;overflow:hidden}#sidebar > *:last-child{margin-bottom:2cm}.http-server-breadcrumbs{font-size:130%;margin:0 0 15px 0}#footer{font-size:.75em;padding:5px 30px;border-top:1px solid #ddd;text-align:right}#footer p{margin:0 0 0 1em;display:inline-block}#footer p:last-child{margin-right:30px}h1,h2,h3,h4,h5{font-weight:300}h1{font-size:2.5em;line-height:1.1em}h2{font-size:1.75em;margin:1em 0 .50em 0}h3{font-size:1.4em;margin:25px 0 10px 0}h4{margin:0;font-size:105%}h1:target,h2:target,h3:target,h4:target,h5:target,h6:target{background:var(--highlight-color);padding:.2em 0}a{color:#058;text-decoration:none;transition:color .3s ease-in-out}a:hover{color:#e82}.title code{font-weight:bold}h2[id^="header-"]{margin-top:2em}.ident{color:#900}pre code{background:#f8f8f8;font-size:.8em;line-height:1.4em}code{background:#f2f2f1;padding:1px 4px;overflow-wrap:break-word}h1 code{background:transparent}pre{background:#f8f8f8;border:0;border-top:1px solid #ccc;border-bottom:1px solid #ccc;margin:1em 0;padding:1ex}#http-server-module-list{display:flex;flex-flow:column}#http-server-module-list div{display:flex}#http-server-module-list dt{min-width:10%}#http-server-module-list p{margin-top:0}.toc ul,#index{list-style-type:none;margin:0;padding:0}#index code{background:transparent}#index h3{border-bottom:1px solid #ddd}#index ul{padding:0}#index h4{margin-top:.6em;font-weight:bold}@media (min-width:200ex){#index .two-column{column-count:2}}@media (min-width:300ex){#index .two-column{column-count:3}}dl{margin-bottom:2em}dl dl:last-child{margin-bottom:4em}dd{margin:0 0 1em 3em}#header-classes + dl > dd{margin-bottom:3em}dd dd{margin-left:2em}dd p{margin:10px 0}.name{background:#eee;font-weight:bold;font-size:.85em;padding:5px 10px;display:inline-block;min-width:40%}.name:hover{background:#e0e0e0}dt:target .name{background:var(--highlight-color)}.name > span:first-child{white-space:nowrap}.name.class > span:nth-child(2){margin-left:.4em}.inherited{color:#999;border-left:5px solid #eee;padding-left:1em}.inheritance em{font-style:normal;font-weight:bold}.desc h2{font-weight:400;font-size:1.25em}.desc h3{font-size:1em}.desc dt code{background:inherit}.source summary,.git-link-div{color:#666;text-align:right;font-weight:400;font-size:.8em;text-transform:uppercase}.source summary > *{white-space:nowrap;cursor:pointer}.git-link{color:inherit;margin-left:1em}.source pre{max-height:500px;overflow:auto;margin:0}.source pre code{font-size:12px;overflow:visible}.hlist{list-style:none}.hlist li{display:inline}.hlist li:after{content:',\2002'}.hlist li:last-child:after{content:none}.hlist .hlist{display:inline;padding-left:1em}img{max-width:100%}td{padding:0 .5em}.admonition{padding:.1em .5em;margin-bottom:1em}.admonition-title{font-weight:bold}.admonition.note,.admonition.info,.admonition.important{background:#aef}.admonition.todo,.admonition.versionadded,.admonition.tip,.admonition.hint{background:#dfd}.admonition.warning,.admonition.versionchanged,.admonition.deprecated{background:#fd4}.admonition.error,.admonition.danger,.admonition.caution{background:lightpink}</style> +<style media="screen and (min-width: 700px)">@media screen and (min-width:700px){#sidebar{width:30%;height:100vh;overflow:auto;position:sticky;top:0}#content{width:70%;max-width:100ch;padding:3em 4em;border-left:1px solid #ddd}pre code{font-size:1em}.item .name{font-size:1em}main{display:flex;flex-direction:row-reverse;justify-content:flex-end}.toc ul ul,#index ul{padding-left:1.5em}.toc > ul > li{margin-top:.5em}}</style> +<style media="print">@media print{#sidebar h1{page-break-before:always}.source{display:none}}@media print{*{background:transparent !important;color:#000 !important;box-shadow:none !important;text-shadow:none !important}a[href]:after{content:" (" attr(href) ")";font-size:90%}a[href][title]:after{content:none}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}@page{margin:0.5cm}p,h2,h3{orphans:3;widows:3}h1,h2,h3,h4,h5,h6{page-break-after:avoid}}</style> +<script defer src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/10.1.1/highlight.min.js" integrity="sha256-Uv3H6lx7dJmRfRvH8TH6kJD1TSK1aFcwgx+mdg3epi8=" crossorigin></script> +<script>window.addEventListener('DOMContentLoaded', () => hljs.initHighlighting())</script> +</head> +<body> +<main> +<article id="content"> +<header> +<h1 class="title">Module <code>sql_app.schemas</code></h1> +</header> +<section id="section-intro"> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">from typing import List, Optional +from datetime import datetime, date +from pydantic import BaseModel + + +class DeviceLicenseBase(BaseModel): + device_id: int + license_id: int + assigned_datetime: str + + +class DeviceLicenseCreate(DeviceLicenseBase): + pass + + +class DeviceLicense(DeviceLicenseCreate): + """ + Class used for creating and reading devices_licenses entries + """ + id: int + + class Config: + orm_mode = True + + +class USBLogBase(BaseModel): + timestamp: datetime + status: str + + +class USBLogCreate(USBLogBase): + pass + + +class USBLog(USBLogBase): + """ + Class used for creating and reading usb_logs entries + """ + id: int + device_id: int + pc_id: int + + class Config: + orm_mode = True + + +class DeviceBase(BaseModel): + vendor_id: str + product_id: str + serial_number: str + + +class DeviceCreate(DeviceBase): + pass + + +class Device(DeviceCreate): + """ + Class used for creating and reading devices entries + """ + id: int + assigned: bool + logs: List[USBLog] = [] + licenses: List[DeviceLicense] = [] + + class Config: + orm_mode = True + + +class LDLogBase(BaseModel): + timestamp: datetime + status: str + + +class LDLogCreate(LDLogBase): + pass + + +class LDLog(LDLogCreate): + """ + Class used for creating and reading ld_logs entries + """ + id: int + head_id: int + body_id: int + + class Config: + orm_mode = True + + +class BodyDeviceBase(BaseModel): + serial_number: str + + +class BodyDeviceCreate(BodyDeviceBase): + pass + + +class BodyDevice(BodyDeviceCreate): + """ + Class used for creating and reading body_devices entries + """ + id: int + logs: List[LDLog] = [] + + class Config: + orm_mode = True + + +class HeadDeviceBase(BaseModel): + serial_number: str + + +class HeadDeviceCreate(HeadDeviceBase): + pass + + +class HeadDevice(HeadDeviceCreate): + """ + Class used for creating and reading head_devices entries + """ + id: int + logs: List[LDLog] = [] + + class Config: + orm_mode = True + + +class PCBase(BaseModel): + username: str + hostname: str + + +class PCCreate(PCBase): + pass + + +class PC(PCCreate): + """ + Class used for creating and reading pc entries + """ + id: int + assigned: bool + logs_pc: List[USBLog] = [] + + class Config: + orm_mode = True + + +class TeamBase(BaseModel): + name: str + + +class TeamCreate(TeamBase): + pass + + +class Team(TeamCreate): + """ + Class used for creating and reading team entries + """ + id: int + pcs: List[PC] = [] + + class Config: + orm_mode = True + + +class LicenseBase(BaseModel): + name: str + expiration_date: date + + +class LicenseCreate(LicenseBase): + pass + + +class License(LicenseCreate): + """ + Class used for creating and reading licenses entries + """ + id: int + devices: List[DeviceLicense] = [] + + class Config: + orm_mode = True + + +class USBTempBase(BaseModel): + """ + Class used for reading data from keyman detecting client messages + """ + username: str + hostname: str + timestamp: str + device: DeviceBase + status: str + + +class USBTempCreate(USBTempBase): + pass + + +class USBTemp(USBTempBase): + id: int + device_id: int + + class Config: + orm_mode = True + + +class LDTempBase(BaseModel): + """ + Class used for reading data from debugger detecting client messages + """ + username: str + hostname: str + timestamp: str + head_device: HeadDeviceBase + body_device: BodyDeviceBase + status: str + + +class LDTempCreate(LDTempBase): + pass + + +class LDTemp(LDTempCreate): + id: int + head_id: int + body_id: int + + class Config: + orm_mode = True</code></pre> +</details> +</section> +<section> +</section> +<section> +</section> +<section> +</section> +<section> +<h2 class="section-title" id="header-classes">Classes</h2> +<dl> +<dt id="sql_app.schemas.BodyDevice"><code class="flex name class"> +<span>class <span class="ident">BodyDevice</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading body_devices entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class BodyDevice(BodyDeviceCreate): + """ + Class used for creating and reading body_devices entries + """ + id: int + logs: List[LDLog] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.BodyDeviceCreate" href="#sql_app.schemas.BodyDeviceCreate">BodyDeviceCreate</a></li> +<li><a title="sql_app.schemas.BodyDeviceBase" href="#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.BodyDevice.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.BodyDevice.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.BodyDevice.logs"><code class="name">var <span class="ident">logs</span> : List[<a title="sql_app.schemas.LDLog" href="#sql_app.schemas.LDLog">LDLog</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.BodyDeviceBase"><code class="flex name class"> +<span>class <span class="ident">BodyDeviceBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class BodyDeviceBase(BaseModel): + serial_number: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.BodyDeviceCreate" href="#sql_app.schemas.BodyDeviceCreate">BodyDeviceCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.BodyDeviceBase.serial_number"><code class="name">var <span class="ident">serial_number</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.BodyDeviceCreate"><code class="flex name class"> +<span>class <span class="ident">BodyDeviceCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class BodyDeviceCreate(BodyDeviceBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.BodyDeviceBase" href="#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.BodyDevice" href="#sql_app.schemas.BodyDevice">BodyDevice</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.Device"><code class="flex name class"> +<span>class <span class="ident">Device</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading devices entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class Device(DeviceCreate): + """ + Class used for creating and reading devices entries + """ + id: int + assigned: bool + logs: List[USBLog] = [] + licenses: List[DeviceLicense] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceCreate" href="#sql_app.schemas.DeviceCreate">DeviceCreate</a></li> +<li><a title="sql_app.schemas.DeviceBase" href="#sql_app.schemas.DeviceBase">DeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +<li>pydantic.main.Device</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.Device.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Device.assigned"><code class="name">var <span class="ident">assigned</span> : bool</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Device.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Device.licenses"><code class="name">var <span class="ident">licenses</span> : List[<a title="sql_app.schemas.DeviceLicense" href="#sql_app.schemas.DeviceLicense">DeviceLicense</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Device.logs"><code class="name">var <span class="ident">logs</span> : List[<a title="sql_app.schemas.USBLog" href="#sql_app.schemas.USBLog">USBLog</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.DeviceBase"><code class="flex name class"> +<span>class <span class="ident">DeviceBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceBase(BaseModel): + vendor_id: str + product_id: str + serial_number: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceCreate" href="#sql_app.schemas.DeviceCreate">DeviceCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.DeviceBase.product_id"><code class="name">var <span class="ident">product_id</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.DeviceBase.serial_number"><code class="name">var <span class="ident">serial_number</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.DeviceBase.vendor_id"><code class="name">var <span class="ident">vendor_id</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.DeviceCreate"><code class="flex name class"> +<span>class <span class="ident">DeviceCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceCreate(DeviceBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceBase" href="#sql_app.schemas.DeviceBase">DeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.Device" href="#sql_app.schemas.Device">Device</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.DeviceLicense"><code class="flex name class"> +<span>class <span class="ident">DeviceLicense</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading devices_licenses entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceLicense(DeviceLicenseCreate): + """ + Class used for creating and reading devices_licenses entries + """ + id: int + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceLicenseCreate" href="#sql_app.schemas.DeviceLicenseCreate">DeviceLicenseCreate</a></li> +<li><a title="sql_app.schemas.DeviceLicenseBase" href="#sql_app.schemas.DeviceLicenseBase">DeviceLicenseBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +<li>pydantic.main.DeviceLicense</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.DeviceLicense.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.DeviceLicense.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.DeviceLicenseBase"><code class="flex name class"> +<span>class <span class="ident">DeviceLicenseBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceLicenseBase(BaseModel): + device_id: int + license_id: int + assigned_datetime: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceLicenseCreate" href="#sql_app.schemas.DeviceLicenseCreate">DeviceLicenseCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.DeviceLicenseBase.assigned_datetime"><code class="name">var <span class="ident">assigned_datetime</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.DeviceLicenseBase.device_id"><code class="name">var <span class="ident">device_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.DeviceLicenseBase.license_id"><code class="name">var <span class="ident">license_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.DeviceLicenseCreate"><code class="flex name class"> +<span>class <span class="ident">DeviceLicenseCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class DeviceLicenseCreate(DeviceLicenseBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceLicenseBase" href="#sql_app.schemas.DeviceLicenseBase">DeviceLicenseBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.DeviceLicense" href="#sql_app.schemas.DeviceLicense">DeviceLicense</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.HeadDevice"><code class="flex name class"> +<span>class <span class="ident">HeadDevice</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading head_devices entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class HeadDevice(HeadDeviceCreate): + """ + Class used for creating and reading head_devices entries + """ + id: int + logs: List[LDLog] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.HeadDeviceCreate" href="#sql_app.schemas.HeadDeviceCreate">HeadDeviceCreate</a></li> +<li><a title="sql_app.schemas.HeadDeviceBase" href="#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.HeadDevice.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.HeadDevice.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.HeadDevice.logs"><code class="name">var <span class="ident">logs</span> : List[<a title="sql_app.schemas.LDLog" href="#sql_app.schemas.LDLog">LDLog</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.HeadDeviceBase"><code class="flex name class"> +<span>class <span class="ident">HeadDeviceBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class HeadDeviceBase(BaseModel): + serial_number: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.HeadDeviceCreate" href="#sql_app.schemas.HeadDeviceCreate">HeadDeviceCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.HeadDeviceBase.serial_number"><code class="name">var <span class="ident">serial_number</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.HeadDeviceCreate"><code class="flex name class"> +<span>class <span class="ident">HeadDeviceCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class HeadDeviceCreate(HeadDeviceBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.HeadDeviceBase" href="#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.HeadDevice" href="#sql_app.schemas.HeadDevice">HeadDevice</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.LDLog"><code class="flex name class"> +<span>class <span class="ident">LDLog</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading ld_logs entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDLog(LDLogCreate): + """ + Class used for creating and reading ld_logs entries + """ + id: int + head_id: int + body_id: int + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDLogCreate" href="#sql_app.schemas.LDLogCreate">LDLogCreate</a></li> +<li><a title="sql_app.schemas.LDLogBase" href="#sql_app.schemas.LDLogBase">LDLogBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.LDLog</li> +<li>pydantic.main.LDLog</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.LDLog.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDLog.body_id"><code class="name">var <span class="ident">body_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDLog.head_id"><code class="name">var <span class="ident">head_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDLog.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LDLogBase"><code class="flex name class"> +<span>class <span class="ident">LDLogBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDLogBase(BaseModel): + timestamp: datetime + status: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDLogCreate" href="#sql_app.schemas.LDLogCreate">LDLogCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.LDLogBase.status"><code class="name">var <span class="ident">status</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDLogBase.timestamp"><code class="name">var <span class="ident">timestamp</span> : datetime.datetime</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LDLogCreate"><code class="flex name class"> +<span>class <span class="ident">LDLogCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDLogCreate(LDLogBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDLogBase" href="#sql_app.schemas.LDLogBase">LDLogBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDLog" href="#sql_app.schemas.LDLog">LDLog</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.LDTemp"><code class="flex name class"> +<span>class <span class="ident">LDTemp</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from debugger detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDTemp(LDTempCreate): + id: int + head_id: int + body_id: int + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDTempCreate" href="#sql_app.schemas.LDTempCreate">LDTempCreate</a></li> +<li><a title="sql_app.schemas.LDTempBase" href="#sql_app.schemas.LDTempBase">LDTempBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.LDTemp.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTemp.body_id"><code class="name">var <span class="ident">body_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTemp.head_id"><code class="name">var <span class="ident">head_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTemp.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LDTempBase"><code class="flex name class"> +<span>class <span class="ident">LDTempBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from debugger detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDTempBase(BaseModel): + """ + Class used for reading data from debugger detecting client messages + """ + username: str + hostname: str + timestamp: str + head_device: HeadDeviceBase + body_device: BodyDeviceBase + status: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDTempCreate" href="#sql_app.schemas.LDTempCreate">LDTempCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.LDTempBase.body_device"><code class="name">var <span class="ident">body_device</span> : <a title="sql_app.schemas.BodyDeviceBase" href="#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTempBase.head_device"><code class="name">var <span class="ident">head_device</span> : <a title="sql_app.schemas.HeadDeviceBase" href="#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTempBase.hostname"><code class="name">var <span class="ident">hostname</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTempBase.status"><code class="name">var <span class="ident">status</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTempBase.timestamp"><code class="name">var <span class="ident">timestamp</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LDTempBase.username"><code class="name">var <span class="ident">username</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LDTempCreate"><code class="flex name class"> +<span>class <span class="ident">LDTempCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from debugger detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LDTempCreate(LDTempBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDTempBase" href="#sql_app.schemas.LDTempBase">LDTempBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LDTemp" href="#sql_app.schemas.LDTemp">LDTemp</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.License"><code class="flex name class"> +<span>class <span class="ident">License</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading licenses entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class License(LicenseCreate): + """ + Class used for creating and reading licenses entries + """ + id: int + devices: List[DeviceLicense] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LicenseCreate" href="#sql_app.schemas.LicenseCreate">LicenseCreate</a></li> +<li><a title="sql_app.schemas.LicenseBase" href="#sql_app.schemas.LicenseBase">LicenseBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.License</li> +<li>pydantic.main.License</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.License.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.License.devices"><code class="name">var <span class="ident">devices</span> : List[<a title="sql_app.schemas.DeviceLicense" href="#sql_app.schemas.DeviceLicense">DeviceLicense</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.License.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LicenseBase"><code class="flex name class"> +<span>class <span class="ident">LicenseBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LicenseBase(BaseModel): + name: str + expiration_date: date</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LicenseCreate" href="#sql_app.schemas.LicenseCreate">LicenseCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.LicenseBase.expiration_date"><code class="name">var <span class="ident">expiration_date</span> : datetime.date</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.LicenseBase.name"><code class="name">var <span class="ident">name</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.LicenseCreate"><code class="flex name class"> +<span>class <span class="ident">LicenseCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class LicenseCreate(LicenseBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.LicenseBase" href="#sql_app.schemas.LicenseBase">LicenseBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.License" href="#sql_app.schemas.License">License</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.PC"><code class="flex name class"> +<span>class <span class="ident">PC</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading pc entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class PC(PCCreate): + """ + Class used for creating and reading pc entries + """ + id: int + assigned: bool + logs_pc: List[USBLog] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.PCCreate" href="#sql_app.schemas.PCCreate">PCCreate</a></li> +<li><a title="sql_app.schemas.PCBase" href="#sql_app.schemas.PCBase">PCBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +<li>pydantic.main.PC</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.PC.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.PC.assigned"><code class="name">var <span class="ident">assigned</span> : bool</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.PC.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.PC.logs_pc"><code class="name">var <span class="ident">logs_pc</span> : List[<a title="sql_app.schemas.USBLog" href="#sql_app.schemas.USBLog">USBLog</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.PCBase"><code class="flex name class"> +<span>class <span class="ident">PCBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class PCBase(BaseModel): + username: str + hostname: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.PCCreate" href="#sql_app.schemas.PCCreate">PCCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.PCBase.hostname"><code class="name">var <span class="ident">hostname</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.PCBase.username"><code class="name">var <span class="ident">username</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.PCCreate"><code class="flex name class"> +<span>class <span class="ident">PCCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class PCCreate(PCBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.PCBase" href="#sql_app.schemas.PCBase">PCBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.PC" href="#sql_app.schemas.PC">PC</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.Team"><code class="flex name class"> +<span>class <span class="ident">Team</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading team entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class Team(TeamCreate): + """ + Class used for creating and reading team entries + """ + id: int + pcs: List[PC] = [] + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.TeamCreate" href="#sql_app.schemas.TeamCreate">TeamCreate</a></li> +<li><a title="sql_app.schemas.TeamBase" href="#sql_app.schemas.TeamBase">TeamBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.Team</li> +<li>pydantic.main.Team</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.Team.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Team.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.Team.pcs"><code class="name">var <span class="ident">pcs</span> : List[<a title="sql_app.schemas.PC" href="#sql_app.schemas.PC">PC</a>]</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.TeamBase"><code class="flex name class"> +<span>class <span class="ident">TeamBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class TeamBase(BaseModel): + name: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.TeamCreate" href="#sql_app.schemas.TeamCreate">TeamCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.TeamBase.name"><code class="name">var <span class="ident">name</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.TeamCreate"><code class="flex name class"> +<span>class <span class="ident">TeamCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class TeamCreate(TeamBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.TeamBase" href="#sql_app.schemas.TeamBase">TeamBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.Team" href="#sql_app.schemas.Team">Team</a></li> +</ul> +</dd> +<dt id="sql_app.schemas.USBLog"><code class="flex name class"> +<span>class <span class="ident">USBLog</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for creating and reading usb_logs entries</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBLog(USBLogBase): + """ + Class used for creating and reading usb_logs entries + """ + id: int + device_id: int + pc_id: int + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBLogBase" href="#sql_app.schemas.USBLogBase">USBLogBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +<li>pydantic.main.USBLog</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.USBLog.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBLog.device_id"><code class="name">var <span class="ident">device_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBLog.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBLog.pc_id"><code class="name">var <span class="ident">pc_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.USBLogBase"><code class="flex name class"> +<span>class <span class="ident">USBLogBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBLogBase(BaseModel): + timestamp: datetime + status: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBLog" href="#sql_app.schemas.USBLog">USBLog</a></li> +<li><a title="sql_app.schemas.USBLogCreate" href="#sql_app.schemas.USBLogCreate">USBLogCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.USBLogBase.status"><code class="name">var <span class="ident">status</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBLogBase.timestamp"><code class="name">var <span class="ident">timestamp</span> : datetime.datetime</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.USBLogCreate"><code class="flex name class"> +<span>class <span class="ident">USBLogCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBLogCreate(USBLogBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBLogBase" href="#sql_app.schemas.USBLogBase">USBLogBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +</dd> +<dt id="sql_app.schemas.USBTemp"><code class="flex name class"> +<span>class <span class="ident">USBTemp</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from keyman detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBTemp(USBTempBase): + id: int + device_id: int + + class Config: + orm_mode = True</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBTempBase" href="#sql_app.schemas.USBTempBase">USBTempBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.USBTemp.Config"><code class="name">var <span class="ident">Config</span></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTemp.device_id"><code class="name">var <span class="ident">device_id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTemp.id"><code class="name">var <span class="ident">id</span> : int</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.USBTempBase"><code class="flex name class"> +<span>class <span class="ident">USBTempBase</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from keyman detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBTempBase(BaseModel): + """ + Class used for reading data from keyman detecting client messages + """ + username: str + hostname: str + timestamp: str + device: DeviceBase + status: str</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +<h3>Subclasses</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBTemp" href="#sql_app.schemas.USBTemp">USBTemp</a></li> +<li><a title="sql_app.schemas.USBTempCreate" href="#sql_app.schemas.USBTempCreate">USBTempCreate</a></li> +</ul> +<h3>Class variables</h3> +<dl> +<dt id="sql_app.schemas.USBTempBase.device"><code class="name">var <span class="ident">device</span> : <a title="sql_app.schemas.DeviceBase" href="#sql_app.schemas.DeviceBase">DeviceBase</a></code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTempBase.hostname"><code class="name">var <span class="ident">hostname</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTempBase.status"><code class="name">var <span class="ident">status</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTempBase.timestamp"><code class="name">var <span class="ident">timestamp</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +<dt id="sql_app.schemas.USBTempBase.username"><code class="name">var <span class="ident">username</span> : str</code></dt> +<dd> +<div class="desc"></div> +</dd> +</dl> +</dd> +<dt id="sql_app.schemas.USBTempCreate"><code class="flex name class"> +<span>class <span class="ident">USBTempCreate</span></span> +<span>(</span><span>**data: Any)</span> +</code></dt> +<dd> +<div class="desc"><p>Class used for reading data from keyman detecting client messages</p> +<p>Create a new model by parsing and validating input data from keyword arguments.</p> +<p>Raises ValidationError if the input data cannot be parsed to form a valid model.</p></div> +<details class="source"> +<summary> +<span>Expand source code</span> +</summary> +<pre><code class="python">class USBTempCreate(USBTempBase): + pass</code></pre> +</details> +<h3>Ancestors</h3> +<ul class="hlist"> +<li><a title="sql_app.schemas.USBTempBase" href="#sql_app.schemas.USBTempBase">USBTempBase</a></li> +<li>pydantic.main.BaseModel</li> +<li>pydantic.utils.Representation</li> +</ul> +</dd> +</dl> +</section> +</article> +<nav id="sidebar"> +<h1>Index</h1> +<div class="toc"> +<ul></ul> +</div> +<ul id="index"> +<li><h3>Super-module</h3> +<ul> +<li><code><a title="sql_app" href="index.html">sql_app</a></code></li> +</ul> +</li> +<li><h3><a href="#header-classes">Classes</a></h3> +<ul> +<li> +<h4><code><a title="sql_app.schemas.BodyDevice" href="#sql_app.schemas.BodyDevice">BodyDevice</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.BodyDevice.Config" href="#sql_app.schemas.BodyDevice.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.BodyDevice.id" href="#sql_app.schemas.BodyDevice.id">id</a></code></li> +<li><code><a title="sql_app.schemas.BodyDevice.logs" href="#sql_app.schemas.BodyDevice.logs">logs</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.BodyDeviceBase" href="#sql_app.schemas.BodyDeviceBase">BodyDeviceBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.BodyDeviceBase.serial_number" href="#sql_app.schemas.BodyDeviceBase.serial_number">serial_number</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.BodyDeviceCreate" href="#sql_app.schemas.BodyDeviceCreate">BodyDeviceCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.Device" href="#sql_app.schemas.Device">Device</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.Device.Config" href="#sql_app.schemas.Device.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.Device.assigned" href="#sql_app.schemas.Device.assigned">assigned</a></code></li> +<li><code><a title="sql_app.schemas.Device.id" href="#sql_app.schemas.Device.id">id</a></code></li> +<li><code><a title="sql_app.schemas.Device.licenses" href="#sql_app.schemas.Device.licenses">licenses</a></code></li> +<li><code><a title="sql_app.schemas.Device.logs" href="#sql_app.schemas.Device.logs">logs</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.DeviceBase" href="#sql_app.schemas.DeviceBase">DeviceBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.DeviceBase.product_id" href="#sql_app.schemas.DeviceBase.product_id">product_id</a></code></li> +<li><code><a title="sql_app.schemas.DeviceBase.serial_number" href="#sql_app.schemas.DeviceBase.serial_number">serial_number</a></code></li> +<li><code><a title="sql_app.schemas.DeviceBase.vendor_id" href="#sql_app.schemas.DeviceBase.vendor_id">vendor_id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.DeviceCreate" href="#sql_app.schemas.DeviceCreate">DeviceCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.DeviceLicense" href="#sql_app.schemas.DeviceLicense">DeviceLicense</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.DeviceLicense.Config" href="#sql_app.schemas.DeviceLicense.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.DeviceLicense.id" href="#sql_app.schemas.DeviceLicense.id">id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.DeviceLicenseBase" href="#sql_app.schemas.DeviceLicenseBase">DeviceLicenseBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.DeviceLicenseBase.assigned_datetime" href="#sql_app.schemas.DeviceLicenseBase.assigned_datetime">assigned_datetime</a></code></li> +<li><code><a title="sql_app.schemas.DeviceLicenseBase.device_id" href="#sql_app.schemas.DeviceLicenseBase.device_id">device_id</a></code></li> +<li><code><a title="sql_app.schemas.DeviceLicenseBase.license_id" href="#sql_app.schemas.DeviceLicenseBase.license_id">license_id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.DeviceLicenseCreate" href="#sql_app.schemas.DeviceLicenseCreate">DeviceLicenseCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.HeadDevice" href="#sql_app.schemas.HeadDevice">HeadDevice</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.HeadDevice.Config" href="#sql_app.schemas.HeadDevice.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.HeadDevice.id" href="#sql_app.schemas.HeadDevice.id">id</a></code></li> +<li><code><a title="sql_app.schemas.HeadDevice.logs" href="#sql_app.schemas.HeadDevice.logs">logs</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.HeadDeviceBase" href="#sql_app.schemas.HeadDeviceBase">HeadDeviceBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.HeadDeviceBase.serial_number" href="#sql_app.schemas.HeadDeviceBase.serial_number">serial_number</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.HeadDeviceCreate" href="#sql_app.schemas.HeadDeviceCreate">HeadDeviceCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDLog" href="#sql_app.schemas.LDLog">LDLog</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.LDLog.Config" href="#sql_app.schemas.LDLog.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.LDLog.body_id" href="#sql_app.schemas.LDLog.body_id">body_id</a></code></li> +<li><code><a title="sql_app.schemas.LDLog.head_id" href="#sql_app.schemas.LDLog.head_id">head_id</a></code></li> +<li><code><a title="sql_app.schemas.LDLog.id" href="#sql_app.schemas.LDLog.id">id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDLogBase" href="#sql_app.schemas.LDLogBase">LDLogBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.LDLogBase.status" href="#sql_app.schemas.LDLogBase.status">status</a></code></li> +<li><code><a title="sql_app.schemas.LDLogBase.timestamp" href="#sql_app.schemas.LDLogBase.timestamp">timestamp</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDLogCreate" href="#sql_app.schemas.LDLogCreate">LDLogCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDTemp" href="#sql_app.schemas.LDTemp">LDTemp</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.LDTemp.Config" href="#sql_app.schemas.LDTemp.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.LDTemp.body_id" href="#sql_app.schemas.LDTemp.body_id">body_id</a></code></li> +<li><code><a title="sql_app.schemas.LDTemp.head_id" href="#sql_app.schemas.LDTemp.head_id">head_id</a></code></li> +<li><code><a title="sql_app.schemas.LDTemp.id" href="#sql_app.schemas.LDTemp.id">id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDTempBase" href="#sql_app.schemas.LDTempBase">LDTempBase</a></code></h4> +<ul class="two-column"> +<li><code><a title="sql_app.schemas.LDTempBase.body_device" href="#sql_app.schemas.LDTempBase.body_device">body_device</a></code></li> +<li><code><a title="sql_app.schemas.LDTempBase.head_device" href="#sql_app.schemas.LDTempBase.head_device">head_device</a></code></li> +<li><code><a title="sql_app.schemas.LDTempBase.hostname" href="#sql_app.schemas.LDTempBase.hostname">hostname</a></code></li> +<li><code><a title="sql_app.schemas.LDTempBase.status" href="#sql_app.schemas.LDTempBase.status">status</a></code></li> +<li><code><a title="sql_app.schemas.LDTempBase.timestamp" href="#sql_app.schemas.LDTempBase.timestamp">timestamp</a></code></li> +<li><code><a title="sql_app.schemas.LDTempBase.username" href="#sql_app.schemas.LDTempBase.username">username</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LDTempCreate" href="#sql_app.schemas.LDTempCreate">LDTempCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.License" href="#sql_app.schemas.License">License</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.License.Config" href="#sql_app.schemas.License.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.License.devices" href="#sql_app.schemas.License.devices">devices</a></code></li> +<li><code><a title="sql_app.schemas.License.id" href="#sql_app.schemas.License.id">id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LicenseBase" href="#sql_app.schemas.LicenseBase">LicenseBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.LicenseBase.expiration_date" href="#sql_app.schemas.LicenseBase.expiration_date">expiration_date</a></code></li> +<li><code><a title="sql_app.schemas.LicenseBase.name" href="#sql_app.schemas.LicenseBase.name">name</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.LicenseCreate" href="#sql_app.schemas.LicenseCreate">LicenseCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.PC" href="#sql_app.schemas.PC">PC</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.PC.Config" href="#sql_app.schemas.PC.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.PC.assigned" href="#sql_app.schemas.PC.assigned">assigned</a></code></li> +<li><code><a title="sql_app.schemas.PC.id" href="#sql_app.schemas.PC.id">id</a></code></li> +<li><code><a title="sql_app.schemas.PC.logs_pc" href="#sql_app.schemas.PC.logs_pc">logs_pc</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.PCBase" href="#sql_app.schemas.PCBase">PCBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.PCBase.hostname" href="#sql_app.schemas.PCBase.hostname">hostname</a></code></li> +<li><code><a title="sql_app.schemas.PCBase.username" href="#sql_app.schemas.PCBase.username">username</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.PCCreate" href="#sql_app.schemas.PCCreate">PCCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.Team" href="#sql_app.schemas.Team">Team</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.Team.Config" href="#sql_app.schemas.Team.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.Team.id" href="#sql_app.schemas.Team.id">id</a></code></li> +<li><code><a title="sql_app.schemas.Team.pcs" href="#sql_app.schemas.Team.pcs">pcs</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.TeamBase" href="#sql_app.schemas.TeamBase">TeamBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.TeamBase.name" href="#sql_app.schemas.TeamBase.name">name</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.TeamCreate" href="#sql_app.schemas.TeamCreate">TeamCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBLog" href="#sql_app.schemas.USBLog">USBLog</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.USBLog.Config" href="#sql_app.schemas.USBLog.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.USBLog.device_id" href="#sql_app.schemas.USBLog.device_id">device_id</a></code></li> +<li><code><a title="sql_app.schemas.USBLog.id" href="#sql_app.schemas.USBLog.id">id</a></code></li> +<li><code><a title="sql_app.schemas.USBLog.pc_id" href="#sql_app.schemas.USBLog.pc_id">pc_id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBLogBase" href="#sql_app.schemas.USBLogBase">USBLogBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.USBLogBase.status" href="#sql_app.schemas.USBLogBase.status">status</a></code></li> +<li><code><a title="sql_app.schemas.USBLogBase.timestamp" href="#sql_app.schemas.USBLogBase.timestamp">timestamp</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBLogCreate" href="#sql_app.schemas.USBLogCreate">USBLogCreate</a></code></h4> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBTemp" href="#sql_app.schemas.USBTemp">USBTemp</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.USBTemp.Config" href="#sql_app.schemas.USBTemp.Config">Config</a></code></li> +<li><code><a title="sql_app.schemas.USBTemp.device_id" href="#sql_app.schemas.USBTemp.device_id">device_id</a></code></li> +<li><code><a title="sql_app.schemas.USBTemp.id" href="#sql_app.schemas.USBTemp.id">id</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBTempBase" href="#sql_app.schemas.USBTempBase">USBTempBase</a></code></h4> +<ul class=""> +<li><code><a title="sql_app.schemas.USBTempBase.device" href="#sql_app.schemas.USBTempBase.device">device</a></code></li> +<li><code><a title="sql_app.schemas.USBTempBase.hostname" href="#sql_app.schemas.USBTempBase.hostname">hostname</a></code></li> +<li><code><a title="sql_app.schemas.USBTempBase.status" href="#sql_app.schemas.USBTempBase.status">status</a></code></li> +<li><code><a title="sql_app.schemas.USBTempBase.timestamp" href="#sql_app.schemas.USBTempBase.timestamp">timestamp</a></code></li> +<li><code><a title="sql_app.schemas.USBTempBase.username" href="#sql_app.schemas.USBTempBase.username">username</a></code></li> +</ul> +</li> +<li> +<h4><code><a title="sql_app.schemas.USBTempCreate" href="#sql_app.schemas.USBTempCreate">USBTempCreate</a></code></h4> +</li> +</ul> +</li> +</ul> +</nav> +</main> +<footer id="footer"> +<p>Generated by <a href="https://pdoc3.github.io/pdoc" title="pdoc: Python API documentation generator"><cite>pdoc</cite> 0.10.0</a>.</p> +</footer> +</body> +</html> \ No newline at end of file diff --git a/server/requirements.txt b/server/requirements.txt index acad635871c4c30c3b5cc84b0047a1f39c0221c2..7d8e2322ad1c6e857548961c33d4d116ccba999d 100644 --- a/server/requirements.txt +++ b/server/requirements.txt @@ -4,4 +4,7 @@ SQLAlchemy==1.4.32 uvicorn==0.17.6 psycopg2-binary==2.8.6 jinja2==3.1.1 -python-multipart==0.0.5 \ No newline at end of file +python-multipart==0.0.5 +fastapi-jwt-auth==0.5.0 +passlib==1.7.4 +bcrypt==3.2.2 \ No newline at end of file diff --git a/server/sql_app/api/auth.py b/server/sql_app/api/auth.py new file mode 100644 index 0000000000000000000000000000000000000000..a66baca8ae992a30a80463068345a2ab20770478 --- /dev/null +++ b/server/sql_app/api/auth.py @@ -0,0 +1,217 @@ +from fastapi import Depends, APIRouter, Form +from fastapi import Request +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi.templating import Jinja2Templates +from fastapi_jwt_auth import AuthJWT +from sqlalchemy.orm import Session +from sql_app import crud +from passlib.context import CryptContext +from pydantic import BaseModel +from ..database import SessionLocal, engine + +# Path to html templates used in this file +templates = Jinja2Templates(directory="templates/auth") + +pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto") + +# prefix used for all endpoints in this file +auth = APIRouter(prefix="") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +class Settings(BaseModel): + authjwt_secret_key: str = "secret" + # Configure application to store and get JWT from cookies + authjwt_token_location: set = {"cookies"} + # Disable CSRF Protection for this example. default is True + authjwt_cookie_csrf_protect: bool = False + + +@AuthJWT.load_config +def get_config(): + return Settings() + + +# admin username and password +fake_users_db = { + "admin": { + "username": "admin", + "password": "admin" + } +} + + +def verify_password(plain_password, hashed_password): + return pwd_context.verify(plain_password, hashed_password) + + +def get_hash_password(password): + return pwd_context.hash(password) + + +def auth_user(db, username: str, password: str): + user = crud.find_user(db, username) + if not user: + return None + if not verify_password(password, user.password): + return None + return user + + +@auth.get("/signup", response_class=HTMLResponse) +async def signup_get(request: Request): + """ + return html template for signup + """ + return templates.TemplateResponse("signup.html", {"request": request}) + + +@auth.post("/signup", response_class=HTMLResponse) +async def signup(username: str = Form(...), password: str = Form(...), db: Session = Depends(get_db)): + """ + Endpoint called form signup template. Creates new user with role guest that can be changed by admin user + """ + users = crud.get_users(db, 0, 100) + users_names = [] + for u in users: + users_names.append(u.username) + if username not in users_names: + new_user = crud.create_user(db, username, get_hash_password(password), "guest") + if new_user is None: + print("something went wrong") + return """ + <html> + <head> + <title>Signup</title> + </head> + <body> + <h1>New user created. You can go back to previous page.</h1> + <form action="/logs-web" method="get"> + <input type="submit" value="Home Page" /> + </form> + </body> + </html> + """ + else: + return """ + <html> + <head> + <title>Signup</title> + </head> + <body> + <h1>Username taken. Try to choose different username.</h1> + <form action="/logs-web" method="get"> + <input type="submit" value="Home Page" /> + </form> + </body> + </html> + """ + +@auth.get("/login", response_class=HTMLResponse) +async def login_get(request: Request): + """ + return html template for login + """ + return templates.TemplateResponse("login.html", {"request": request}) + + +@auth.post("/login", response_class=HTMLResponse) +async def login(username: str = Form(...), password: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from login template. Checks if given username and password aligns with admin + username and password and returns token for browser according to given username and password + """ + user = auth_user(db, username, password) + if user != None: + if user.role == "admin": + access_token = Authorize.create_access_token(subject="admin", expires_time=False) + refresh_token = Authorize.create_refresh_token(subject="admin", expires_time=False) + else: + access_token = Authorize.create_access_token(subject="guest", expires_time=False) + refresh_token = Authorize.create_refresh_token(subject="guest", expires_time=False) + else: + usr = fake_users_db.get(username) + if usr != None: + if usr["username"] == username and usr["password"] == password: + access_token = Authorize.create_access_token(subject="admin", expires_time=False) + refresh_token = Authorize.create_refresh_token(subject="admin", expires_time=False) + else: + return """ + <html> + <head> + <title>Login</title> + </head> + <body> + <h1>Wrong Username or Password</h1> + <form action="/login" method="get"> + <input type="submit" value="Log again" /> + </form> + <form action="/login" method="get"> + <input type="submit" value="Home Page" /> + </form> + </body> + </html> + """ + + # Set the JWT cookies in the response + Authorize.set_access_cookies(access_token) + Authorize.set_refresh_cookies(refresh_token) + return """ + <html> + <head> + <title>Login</title> + </head> + <body> + <h1>Now you are logged in, you can continue to previous page.</h1> + <form action="/logs-web" method="get"> + <input type="submit" value="Home Page" /> + </form> + </body> + </html> + """ + + +@auth.post('/refresh') +def refresh(Authorize: AuthJWT = Depends()): + """ + endpoint for refreshing browser token. Not used at the moment since lifetime of given tokens are + unlimited. + """ + Authorize.jwt_refresh_token_required() + current_user = Authorize.get_jwt_subject() + new_access_token = Authorize.create_access_token(subject=current_user) + # Set the JWT cookies in the response + Authorize.set_access_cookies(new_access_token) + return {"msg": "The token has been refresh"} + + +@auth.get('/logout', response_class=HTMLResponse) +def logout(Authorize: AuthJWT = Depends()): + """ + Endpoint for deleting cookie token with acces role. + """ + Authorize.jwt_optional() + + Authorize.unset_jwt_cookies() + return """ + <html> + <head> + <title>Logout</title> + </head> + <body> + <h1>Logged Out</h1> + <form action="/logs-web" method="get"> + <input type="submit" value="Back" /> + </form> + </body> + </html> + """ diff --git a/server/sql_app/api/bodydevices_web.py b/server/sql_app/api/bodydevices_web.py new file mode 100644 index 0000000000000000000000000000000000000000..48b345e62ef1724a59a1854e9e8002c4c76870dc --- /dev/null +++ b/server/sql_app/api/bodydevices_web.py @@ -0,0 +1,143 @@ +from datetime import datetime + +from fastapi import Depends, APIRouter, Form +from fastapi import Request +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi.templating import Jinja2Templates +from fastapi_jwt_auth import AuthJWT +from pydantic import BaseModel +from sqlalchemy.orm import Session +from sql_app.api.auth import fake_users_db +from sql_app import crud, models +from ..database import SessionLocal, engine + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="templates/body-devices") + +# prefix used for all endpoints in this file +body_device_web = APIRouter(prefix="") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@body_device_web.get("/body-devices-web", response_class=HTMLResponse) +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all body devices and its current states + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + + devices = crud.get_body_devices(db, skip=skip, limit=limit) + statuses = [] + # adding state for each device in list + for i in range(0, len(devices)): + statuses.append(devices[i].b_logs[len(devices[i].b_logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + if current_user == "admin": + return templates.TemplateResponse("body_devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("body_devices_normal.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + + +@body_device_web.post("/body-devices-web", response_class=HTMLResponse) +async def filter_devices(request: Request, skip: int = 0, limit: int = 100, lic: str = Form("all"), + db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Endpoint used for filtering body devices by license. returns html template with only + body devices that has assigned license defined by user input + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + devices = crud.get_body_devices(db, skip=skip, limit=limit) + def_devices = [] + for dev in devices: + for l in dev.debug_licenses: + if dev not in def_devices and l.b_licenses.name == lic: + def_devices.append(dev) + # if input was default all + if lic == "all": + def_devices = devices + statuses = [] + for i in range(0, len(def_devices)): + statuses.append(def_devices[i].b_logs[len(def_devices[i].b_logs) - 1].status) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + if current_user == "admin": + return templates.TemplateResponse("body_devices.html", + {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("body_devices_normal.html", + {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + + +@body_device_web.get("/body-device-license/{device_id}", response_class=HTMLResponse) +async def connect_dev_lic(request: Request, device_id: int, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with one body device and all available licenses that can be assigned to it. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + device = crud.get_body_device(db, device_id) + dev_licenses = crud.get_bodydevice_license(db, device_id) + lic_names = [] + dev_lics = [] + for dev_lic in dev_licenses: + dev_lics.append(dev_lic.b_licenses) + for dev_lic in dev_licenses: + lic_names.append(dev_lic.b_licenses.name) + licenses = crud.get_licenses(db, 0, 100) + lic_left = [] + for lic in licenses: + if lic.name not in lic_names and lic not in lic_left: + lic_left.append(lic) + return templates.TemplateResponse("body_device_license.html", + {"request": request, "device": device, "licenses": lic_left, "dev_lic": dev_lics}) + + +@body_device_web.post("/body-devices-web/{device_id}") +async def connect_post(device_id: int, lic: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from template for connecting body device with license. Adds entry to bodydevices_licenses + table and redirects to body-devices-web endpoint + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + crud.create_body_device_license(db, device_id, int(lic), datetime.now()) + return RedirectResponse(url=f"/body-devices-web", status_code=303) + + +@body_device_web.post("/body-devices-web-del/{device_id}") +async def delete_post(device_id: int, b_lic: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from template for connecting body device with license. Adds entry to devices_licenses + table and redirects to body-devices-web endpoint + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + crud.delete_bodydevice_license(db, device_id, int(b_lic)) + return RedirectResponse(url=f"/body-devices-web", status_code=303) \ No newline at end of file diff --git a/server/sql_app/api/devices.py b/server/sql_app/api/devices.py index e42ee855b8dd6a3d2911cf0c8c51c35958b32321..ec5f3dcc0fe5e6eb17a9e92eb12aafb5fb2a0f71 100644 --- a/server/sql_app/api/devices.py +++ b/server/sql_app/api/devices.py @@ -7,8 +7,10 @@ from ..database import SessionLocal, engine models.Base.metadata.create_all(bind=engine) +# prefix used for all endpoints in this file device = APIRouter(prefix="/api/v1") + # Dependency def get_db(): db = SessionLocal() @@ -20,17 +22,26 @@ def get_db(): @device.post("/device", response_model=schemas.Device) def create_device(device: schemas.DeviceCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new device + """ print(crud.create_device(db=db, device=device)) @device.get("/devices", response_model=List[schemas.Device]) def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Endpoint returns all devices in database + """ devices = crud.get_devices(db, skip=skip, limit=limit) return devices @device.get("/device/{device_id}", response_model=schemas.Device) def read_device(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific device by given id + """ db_device = crud.get_device(db, device_id=device_id) if db_device is None: raise HTTPException(status_code=404, detail="Device not found") diff --git a/server/sql_app/api/devices_web.py b/server/sql_app/api/devices_web.py index 00c668da5cbbd5431765be136323de1d9f13bcac..0d82a6bed12835f300cfb75d9f09fc61cf560738 100644 --- a/server/sql_app/api/devices_web.py +++ b/server/sql_app/api/devices_web.py @@ -1,19 +1,23 @@ -from typing import List +from datetime import datetime -from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from fastapi import Depends, APIRouter, Form +from fastapi import Request +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi.templating import Jinja2Templates +from fastapi_jwt_auth import AuthJWT +from pydantic import BaseModel from sqlalchemy.orm import Session -from sql_app import crud, models, schemas -from datetime import datetime +from sql_app.api.auth import fake_users_db +from sql_app import crud, models from ..database import SessionLocal, engine -from fastapi import FastAPI, Request -from fastapi.responses import HTMLResponse -from fastapi.staticfiles import StaticFiles -from fastapi.templating import Jinja2Templates models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file templates = Jinja2Templates(directory="templates/devices") -device_web = APIRouter(prefix="/api/v1") +# prefix used for all endpoints in this file +device_web = APIRouter(prefix="") # Dependency @@ -26,51 +30,114 @@ def get_db(): @device_web.get("/devices-web", response_class=HTMLResponse) -async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all devices and its current states + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + devices = crud.get_devices(db, skip=skip, limit=limit) statuses = [] + # adding state for each device in list for i in range(0, len(devices)): - statuses.append(devices[i].logs[len(devices[i].logs)-1].status) + statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, - "statuses": statuses, "licenses": licenses}) + if current_user == "admin": + return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("devices_normal.html", {"request": request, "devs": len(devices), "devices": devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) @device_web.post("/devices-web", response_class=HTMLResponse) async def filter_devices(request: Request, skip: int = 0, limit: int = 100, lic: str = Form("all"), - db: Session = Depends(get_db)): + db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Endpoint used for filtering devices by license. returns html template with only + devices that has assigned license defined by user input + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() devices = crud.get_devices(db, skip=skip, limit=limit) def_devices = [] for dev in devices: for l in dev.licenses: if dev not in def_devices and l.licenses.name == lic: def_devices.append(dev) + # if input was default all if lic == "all": def_devices = devices statuses = [] for i in range(0, len(def_devices)): statuses.append(def_devices[i].logs[len(def_devices[i].logs) - 1].status) licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("devices.html", {"request": request, "devs": len(def_devices), "devices": def_devices, - "statuses": statuses, "licenses": licenses}) + if current_user == "admin": + return templates.TemplateResponse("devices.html", + {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("devices_normal.html", + {"request": request, "devs": len(def_devices), "devices": def_devices, + "statuses": statuses, "licenses": licenses, "user": current_user}) @device_web.get("/device-license/{device_id}", response_class=HTMLResponse) -async def connect_dev_lic(request: Request, device_id: int, db: Session = Depends(get_db)): +async def connect_dev_lic(request: Request, device_id: int, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with one device and all available licenses that can be assigned to it. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) device = crud.get_device(db, device_id) + dev_licenses = crud.get_device_licenses(db, device_id) + lic_names = [] + dev_lics = [] + for dev_lic in dev_licenses: + dev_lics.append(dev_lic.licenses) + for dev_lic in dev_licenses: + lic_names.append(dev_lic.licenses.name) licenses = crud.get_licenses(db, 0, 100) + lic_left = [] + for lic in licenses: + if lic.name not in lic_names and lic not in lic_left: + lic_left.append(lic) return templates.TemplateResponse("devicelicense.html", - {"request": request, "device": device, "licenses": licenses}) + {"request": request, "device": device, "licenses": lic_left, "dev_lic": dev_lics}) -@device_web.post("/devices-web/{device_id}", response_class=HTMLResponse) -async def connect_post(request: Request, device_id: int, lic: str = Form(...), skip: int = 0, limit: int = 100, - db: Session = Depends(get_db)): +@device_web.post("/devices-web/{device_id}") +async def connect_post(device_id: int, lic: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from template for connecting device with license. Adds entry to devices_licenses + table and redirects to devices-web endpoint + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) crud.create_device_license(db, device_id, int(lic), datetime.now()) - devices = crud.get_devices(db, skip=skip, limit=limit) - statuses = [] - for i in range(0, len(devices)): - statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) - licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, - "statuses": statuses, "licenses": licenses}) + return RedirectResponse(url=f"/devices-web", status_code=303) + + +@device_web.post("/devices-web-del/{device_id}") +async def delete_post(device_id: int, lic_del: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from template for deleting device-license connection. Adds entry to bodydevices_licenses + table and redirects to devices-web endpoint + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + crud.delete_device_license(db, device_id, int(lic_del)) + return RedirectResponse(url=f"/devices-web", status_code=303) diff --git a/server/sql_app/api/ld_logs_web.py b/server/sql_app/api/ld_logs_web.py new file mode 100644 index 0000000000000000000000000000000000000000..aef37335fa349529c1787ca624ced3f50b58d1ac --- /dev/null +++ b/server/sql_app/api/ld_logs_web.py @@ -0,0 +1,81 @@ +from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from datetime import datetime +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse +from fastapi_jwt_auth import AuthJWT +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="templates/ld-logs") + +# prefix used for all endpoints in this file +ldlogs_web = APIRouter(prefix="") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@ldlogs_web.get("/ldlogs-web", response_class=HTMLResponse) +async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all usb logs currently saved in database with its pcs, teams and licenses. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + logs = crud.get_ld_logs(db, skip=skip, limit=limit) + pcs = [] + for log in logs: + if log.pc_id not in pcs: + pcs.append(log.pc_id) + pc_obj = crud.find_pcs(db, pcs) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + if current_user == "admin": + return templates.TemplateResponse("ldlogs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("ldlogs_normal.html", + {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + + +@ldlogs_web.post("/ldlogs-web", response_class=HTMLResponse) +async def filter_logs(request: Request, pc: str = Form("all"), team: str = Form("all"), lic: str = Form("all"), + skip: int = 0, limit: int = 100, + db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Endpoint used for filtering ld logs by user given form inputs. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + log = crud.get_filtered_ldlogs(db, pc, team, lic) + logs_ids = [] + for l in log: + logs_ids.append(l[0]) + logs = crud.find_filtered_ldlogs(db, logs_ids) + pc_obj = crud.get_pcs(db, skip=skip, limit=limit) + teams = crud.get_teams(db, skip=skip, limit=limit) + licenses = crud.get_licenses(db, skip=skip, limit=limit) + if current_user == "admin": + return templates.TemplateResponse("ldlogs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("ldlogs_normal.html", + {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) diff --git a/server/sql_app/api/licenses.py b/server/sql_app/api/licenses.py index b79c7b9721a9d2f31c8d212a520f82f211e787be..4eb2a3ef22ee7c2cd88ae765834a1184228f1c92 100644 --- a/server/sql_app/api/licenses.py +++ b/server/sql_app/api/licenses.py @@ -8,6 +8,7 @@ from ..database import SessionLocal, engine models.Base.metadata.create_all(bind=engine) +# prefix used for all endpoints in this file licenses = APIRouter(prefix="/api/v1") @@ -22,11 +23,17 @@ def get_db(): @licenses.get("/licenses", response_model=List[schemas.License]) def read_licenses(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all licenses currently saved in database. + """ licenses = crud.get_licenses(db, skip=skip, limit=limit) return licenses @licenses.post("/device-license", response_model=schemas.DeviceLicense) def create_device_license(device_license: schemas.DeviceLicenseCreate, db: Session = Depends(get_db)): + """ + Creates entry for devices_licenses table thus connecting device with its license. + """ print(crud.create_device_license(db=db, device=device_license.device_id, license=device_license.license_id, time=datetime.now())) diff --git a/server/sql_app/api/licenses_web.py b/server/sql_app/api/licenses_web.py index 46d4011c49e5db593eba26861f850a1faebc5fd1..f402a1b6b667d68d7f320886cebb5280517d9dce 100644 --- a/server/sql_app/api/licenses_web.py +++ b/server/sql_app/api/licenses_web.py @@ -6,15 +6,19 @@ from datetime import date from sql_app import crud, models, schemas from ..database import SessionLocal, engine from fastapi import FastAPI, Request -from fastapi.responses import HTMLResponse +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi_jwt_auth import AuthJWT from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file templates = Jinja2Templates(directory="templates/licenses") device_templates = Jinja2Templates(directory="templates/devices") -licenses_web = APIRouter(prefix="/api/v1") +# prefix used for all endpoints in this file +licenses_web = APIRouter(prefix="") # Dependency @@ -27,26 +31,50 @@ def get_db(): @licenses_web.get("/license-create", response_class=HTMLResponse) -async def licenses_create_web(request: Request): - return templates.TemplateResponse("license_create.html", {"request": request}) +async def licenses_create_web(request: Request, Authorize: AuthJWT = Depends()): + """ + Returns template with Form for creating new license. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + return templates.TemplateResponse("license_create.html", {"request": request, "minimum_date": date.today()}) @licenses_web.get("/licenses-web", response_class=HTMLResponse) -async def read_licenses_web(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): - licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("licenses.html", {"request": request, "licenses": licenses}) - - -@licenses_web.post("/licenses-web", response_class=HTMLResponse) -def create_license(request: Request, name: str = Form(...), expdate: date = Form(...), skip: int = 0, limit: int = 100, - db: Session = Depends(get_db)): - db_license = crud.create_license(db, name, expdate) - if db_license is None: - print("something went wrong") - devices = crud.get_devices(db, skip=skip, limit=limit) - statuses = [] - for i in range(0, len(devices)): - statuses.append(devices[i].logs[len(devices[i].logs) - 1].status) +async def read_licenses_web(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all licenses currently saved in database + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() licenses = crud.get_licenses(db, skip=skip, limit=limit) - return device_templates.TemplateResponse("devices.html", {"request": request, "devs": len(devices), "devices": devices, - "statuses": statuses, "licenses": licenses}) \ No newline at end of file + if current_user == "admin": + return templates.TemplateResponse("licenses.html", {"request": request, "licenses": licenses, + "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("licenses_normal.html", {"request": request, "licenses": licenses, + "user": current_user}) + +@licenses_web.post("/licenses-web") +def create_license(name: str = Form(...), expdate: date = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from create license form. Creates new license and redirects to devices-web endpoint + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + licenses = crud.get_licenses(db, 0, 100) + licenses_names = [] + for l in licenses: + licenses_names.append(l.name) + if name not in licenses_names: + db_license = crud.create_license(db, name, expdate) + if db_license is None: + print("something went wrong") + return RedirectResponse(url=f"/devices-web", status_code=303) diff --git a/server/sql_app/api/pcs.py b/server/sql_app/api/pcs.py index ba78f06e8a48a7ca687af5911c2e3f73ce843556..11ce207154d3673bd0d46b6cb713f2649a8ca99d 100644 --- a/server/sql_app/api/pcs.py +++ b/server/sql_app/api/pcs.py @@ -6,6 +6,7 @@ from ..database import SessionLocal, engine models.Base.metadata.create_all(bind=engine) +# prefix used for all endpoints in this file pcs = APIRouter(prefix="/api/v1") @@ -20,17 +21,26 @@ def get_db(): @pcs.post("/pc", response_model=schemas.PC) def create_pc(pc: schemas.PCCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ print(crud.create_pc(db=db, user=pc.username, host=pc.hostname)) @pcs.get("/pcs", response_model=List[schemas.PC]) def read_pcs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs currently saved in database + """ pcs = crud.get_pcs(db, skip=skip, limit=limit) return pcs @pcs.get("/pc/{pc_id}", response_model=schemas.PC) def read_pc(pc_id: int, db: Session = Depends(get_db)): + """ + Returns one specific pc by given id + """ db_pc = crud.get_pc(db, pc_id=pc_id) if db_pc is None: raise HTTPException(status_code=404, detail="Device not found") diff --git a/server/sql_app/api/pcs_web.py b/server/sql_app/api/pcs_web.py index a181380c013bf9c268323ad769b611511372b9fa..2779e4605197791891502694dca81d6281890b7c 100644 --- a/server/sql_app/api/pcs_web.py +++ b/server/sql_app/api/pcs_web.py @@ -4,14 +4,18 @@ from sqlalchemy.orm import Session from sql_app import crud, models, schemas from ..database import SessionLocal, engine from fastapi import FastAPI, Request -from fastapi.responses import HTMLResponse +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi_jwt_auth import AuthJWT from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file templates = Jinja2Templates(directory="templates/pcs") -pcs_web = APIRouter(prefix="/api/v1") +# prefix used for all endpoints in this file +pcs_web = APIRouter(prefix="") # Dependency @@ -24,22 +28,46 @@ def get_db(): @pcs_web.get("/pcs-web", response_class=HTMLResponse) -async def read_pcs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): +async def read_pcs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all pcs currently saved in database + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() pcs = crud.get_pcs(db, skip=skip, limit=limit) - return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs}) + if current_user == "admin": + return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("pcs_normal.html", {"request": request, "pcs": pcs, "user": current_user}) @pcs_web.get("/pc-team/{pc_id}", response_class=HTMLResponse) -async def connect_pc_team(request: Request, pc_id: int, db: Session = Depends(get_db)): +async def connect_pc_team(request: Request, pc_id: int, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with Form for connecting pc with team + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) pc = crud.get_pc(db, pc_id) teams = crud.get_teams(db, 0, 100) return templates.TemplateResponse("pcteam.html", {"request": request, "pc": pc, "teams": teams}) -@pcs_web.post("/pcs-web/{pc_id}", response_class=HTMLResponse) -async def connect_post(request: Request, pc_id: int, team: str = Form(...), skip: int = 0, limit: int = 100, - db: Session = Depends(get_db)): +@pcs_web.post("/pcs-web/{pc_id}") +async def connect_post(pc_id: int, team: str = Form(...), db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Endpoint called from within form for connecting pc with team. Updates certain pc with new team. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) old_pc = crud.update_pc(db, pc_id, team) - pcs = crud.get_pcs(db, skip=skip, limit=limit) - return templates.TemplateResponse("pcs.html", {"request": request, "pcs": pcs}) + return RedirectResponse(url=f"/pcs-web", status_code=303) diff --git a/server/sql_app/api/teams.py b/server/sql_app/api/teams.py index b685b2892b0ab444816d04c2ee4777b59409db45..75c50728fd148d209576ef72cefd5b56ba142734 100644 --- a/server/sql_app/api/teams.py +++ b/server/sql_app/api/teams.py @@ -7,6 +7,7 @@ from ..database import SessionLocal, engine models.Base.metadata.create_all(bind=engine) +# prefix used for all endpoints in this file teams = APIRouter(prefix="/api/v1") # Dependency @@ -20,17 +21,26 @@ def get_db(): @teams.post("/team", response_model=schemas.Team) def create_device(team: schemas.TeamCreate, db: Session = Depends(get_db)): + """ + Endpoint used for creating new pc + """ print(crud.create_team(db=db, name=team.name)) @teams.get("/teams", response_model=List[schemas.Device]) def read_devices(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all pcs saved in database + """ teams = crud.get_teams(db, skip=skip, limit=limit) return teams @teams.get("/team/{team_id}", response_model=schemas.Device) def read_device(team_id: int, db: Session = Depends(get_db)): + """ + Returns one specific team by given id + """ db_team = crud.get_team(db, team_id=team_id) if db_team is None: raise HTTPException(status_code=404, detail="Device not found") diff --git a/server/sql_app/api/teams_web.py b/server/sql_app/api/teams_web.py index 20d31ac219fed1f87bdb9bcd3f0a569261c141ad..616c1c72764410a27a1997ed3898fb1943eaa58e 100644 --- a/server/sql_app/api/teams_web.py +++ b/server/sql_app/api/teams_web.py @@ -5,14 +5,18 @@ from sqlalchemy.orm import Session from sql_app import crud, models, schemas from ..database import SessionLocal, engine from fastapi import FastAPI, Request -from fastapi.responses import HTMLResponse +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi_jwt_auth import AuthJWT from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file templates = Jinja2Templates(directory="templates/teams") -teams_web = APIRouter(prefix="/api/v1") +# prefix used for all endpoints in this file +teams_web = APIRouter(prefix="") # Dependency @@ -25,21 +29,48 @@ def get_db(): @teams_web.get("/teams-web", response_class=HTMLResponse) -async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): +async def read_devices(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all teams currently saved in database + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() teams = crud.get_teams(db, skip=skip, limit=limit) - return templates.TemplateResponse("teams.html", {"request": request, "teams": teams}) + if current_user == "admin": + return templates.TemplateResponse("teams.html", {"request": request, "teams": teams, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("teams_normal.html", {"request": request, "teams": teams, "user": current_user}) @teams_web.get("/team-create", response_class=HTMLResponse) -async def team_create_web(request: Request): +async def team_create_web(request: Request, Authorize: AuthJWT = Depends()): + """ + Returns template with form for creating new team + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) return templates.TemplateResponse("team_create.html", {"request": request}) -@teams_web.post("/teams-web", response_class=HTMLResponse) -def create_team(request: Request, name: str = Form(...), skip: int = 0, limit: int = 100, - db: Session = Depends(get_db)): - team = crud.create_team(db, name) - if team is None: - print("something went wrong") - teams = crud.get_teams(db, skip=skip, limit=limit) - return templates.TemplateResponse("teams.html", {"request": request, "teams": teams}) +@teams_web.post("/teams-web-con") +def create_team(name: str = Form(...), db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Endpoint called from within form for creating new team. Creates new team and returns all teams in database + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + teams = crud.get_teams(db, 0, 100) + teams_names = [] + for t in teams: + teams_names.append(t.name) + if name not in teams_names: + team = crud.create_team(db, name) + if team is None: + print("something went wrong") + return RedirectResponse(url=f"/teams-web", status_code=303) diff --git a/server/sql_app/api/usb_logs.py b/server/sql_app/api/usb_logs.py index d07caeeabaf9e7608c77e325d9c34588ac4688c1..e61697f98afa68bb4a62cb9727f2cb5136cadfa8 100644 --- a/server/sql_app/api/usb_logs.py +++ b/server/sql_app/api/usb_logs.py @@ -7,6 +7,7 @@ from ..database import SessionLocal, engine models.Base.metadata.create_all(bind=engine) +# prefix used for all endpoints in this file usblogs = APIRouter(prefix="/api/v1") @@ -21,6 +22,11 @@ def get_db(): @usblogs.post("/usb-logs", response_model=schemas.USBLog) def create_device_logs(log: schemas.USBTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from keyman detecting client. Parses timestamp into datetime object. + Finds if device and pc defined in message already exists and creates them if necessary. + Saves log into database + """ dev = crud.find_device(db, log.device) dat = datetime.strptime(log.timestamp, '%Y-%m-%d %H:%M:%S') if dev is None: @@ -34,12 +40,17 @@ def create_device_logs(log: schemas.USBTempBase, db: Session = Depends(get_db)): @usblogs.post("/ld-logs", response_model=schemas.LDLog) def create_ld_logs(log: schemas.LDTempBase, db: Session = Depends(get_db)): + """ + Endpoint called from debugger detecting client. Parses timestamp into datetime object. + Finds if head device and body device defined in message already exists and creates them if necessary. + Saves log into database + """ head_dev = crud.find_head_device(db, log.head_device) body_dev = crud.find_body_device(db, log.body_device) if head_dev is None: - crud.create_head_device(db, log.head_device) + head_dev = crud.create_head_device(db, log.head_device) if body_dev is None: - crud.create_body_device(db, log.body_device) + body_dev = crud.create_body_device(db, log.body_device) pc = crud.find_pc(db, log.username, log.hostname) if pc is None: @@ -50,12 +61,18 @@ def create_ld_logs(log: schemas.LDTempBase, db: Session = Depends(get_db)): @usblogs.get("/logs", response_model=List[schemas.USBLog]) def read_logs(skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): + """ + Returns all usb logs saved in database + """ items = crud.get_logs(db, skip=skip, limit=limit) return items @usblogs.get("/logs/{device_id}", response_model=List[schemas.USBLog]) def read_log(device_id: int, db: Session = Depends(get_db)): + """ + Returns one specific log by given id + """ db_log = crud.get_log(db, device_id=device_id) if db_log is None: raise HTTPException(status_code=404, detail="Logs not found") diff --git a/server/sql_app/api/usb_logs_web.py b/server/sql_app/api/usb_logs_web.py index fbce50b6ffdb34dbcea1af559b5a45d7245c5afe..75ebdc67692200a841c11a27e5215a781469e143 100644 --- a/server/sql_app/api/usb_logs_web.py +++ b/server/sql_app/api/usb_logs_web.py @@ -6,13 +6,17 @@ from sql_app import crud, models, schemas from ..database import SessionLocal, engine from fastapi import FastAPI, Request from fastapi.responses import HTMLResponse +from fastapi_jwt_auth import AuthJWT from fastapi.staticfiles import StaticFiles from fastapi.templating import Jinja2Templates models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file templates = Jinja2Templates(directory="templates/usb-logs") -usblogs_web = APIRouter(prefix="/api/v1") +# prefix used for all endpoints in this file +usblogs_web = APIRouter(prefix="") # Dependency @@ -25,7 +29,13 @@ def get_db(): @usblogs_web.get("/logs-web", response_class=HTMLResponse) -async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db)): +async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all usb logs currently saved in database with its pcs, teams and licenses. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() logs = crud.get_logs(db, skip=skip, limit=limit) pcs = [] for log in logs: @@ -34,14 +44,24 @@ async def read_logs(request: Request, skip: int = 0, limit: int = 100, db: Sessi pc_obj = crud.find_pcs(db, pcs) teams = crud.get_teams(db, skip=skip, limit=limit) licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, - "licenses": licenses}) + if current_user == "admin": + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("logs_normal.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) @usblogs_web.post("/logs-web", response_class=HTMLResponse) async def filter_logs(request: Request, pc: str = Form("all"), team: str = Form("all"), lic: str = Form("all"), skip: int = 0, limit: int = 100, - db: Session = Depends(get_db)): + db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Endpoint used for filtering usb logs by user given form inputs. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() log = crud.get_filtered_logs(db, pc, team, lic) logs_ids = [] for l in log: @@ -50,6 +70,15 @@ async def filter_logs(request: Request, pc: str = Form("all"), team: str = Form( pc_obj = crud.get_pcs(db, skip=skip, limit=limit) teams = crud.get_teams(db, skip=skip, limit=limit) licenses = crud.get_licenses(db, skip=skip, limit=limit) - return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, - "licenses": licenses}) + if current_user == "admin": + return templates.TemplateResponse("logs.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + else: + current_user = "guest" + return templates.TemplateResponse("logs_normal.html", {"request": request, "logs": logs, "pcs": pc_obj, "teams": teams, + "licenses": licenses, "user": current_user}) + +@usblogs_web.get("/", response_class=HTMLResponse) +async def crossroad(request: Request): + return templates.TemplateResponse("crossroad.html", {"request": request}) diff --git a/server/sql_app/api/users_web.py b/server/sql_app/api/users_web.py new file mode 100644 index 0000000000000000000000000000000000000000..523b22fe71f47a3bb993a0bb49c9230ec2fee115 --- /dev/null +++ b/server/sql_app/api/users_web.py @@ -0,0 +1,59 @@ +from typing import List +from fastapi import Depends, FastAPI, HTTPException, APIRouter, Form +from sqlalchemy.orm import Session +from sql_app import crud, models, schemas +from ..database import SessionLocal, engine +from fastapi import FastAPI, Request +from fastapi.responses import HTMLResponse, RedirectResponse +from fastapi_jwt_auth import AuthJWT +from fastapi.staticfiles import StaticFiles +from fastapi.templating import Jinja2Templates + +models.Base.metadata.create_all(bind=engine) + +# Path to html templates used in this file +templates = Jinja2Templates(directory="templates/users") + +# prefix used for all endpoints in this file +users = APIRouter(prefix="") + + +# Dependency +def get_db(): + db = SessionLocal() + try: + yield db + finally: + db.close() + + +@users.get("/users-web", response_class=HTMLResponse) +async def read_usrs(request: Request, skip: int = 0, limit: int = 100, db: Session = Depends(get_db), + Authorize: AuthJWT = Depends()): + """ + Returns template with all users currently saved in database + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + users = crud.get_users(db, skip, limit) + if current_user == "admin": + return templates.TemplateResponse("users.html", {"request": request, "users": users}) + else: + return RedirectResponse(url=f"/logs-web", status_code=303) + + +@users.get("/user-role/{usr_id}", response_class=HTMLResponse) +async def connect_pc_team(usr_id: int, db: Session = Depends(get_db), Authorize: AuthJWT = Depends()): + """ + Changes role of user to either guest or admin depending on old role. + """ + Authorize.jwt_optional() + current_user = Authorize.get_jwt_subject() + if current_user != "admin": + return RedirectResponse(url=f"/logs-web", status_code=303) + user = crud.find_user_byid(db, usr_id) + if user.role == "admin": + crud.change_role(db, usr_id, "guest") + else: + crud.change_role(db, usr_id, "admin") + return RedirectResponse(url=f"/users-web", status_code=303) \ No newline at end of file diff --git a/server/sql_app/crud.py b/server/sql_app/crud.py index 239b6fbe6f9a8413b9c2f9a4a8b66829b8b2ce43..f2b3a9b6738960a8e98d22e8ef60faec011cbe15 100644 --- a/server/sql_app/crud.py +++ b/server/sql_app/crud.py @@ -6,20 +6,32 @@ from . import models, schemas def get_device(db: Session, device_id: int): + """ + returns one specific devices by given id + """ return db.query(models.Device).filter(models.Device.id == device_id).first() def get_devices(db: Session, skip: int = 0, limit: int = 100): + """ + returns all devices in database + """ return db.query(models.Device).offset(skip).limit(limit).all() def find_device(db: Session, device: schemas.DeviceBase): + """ + finds one device with product_id, vendor_id and serial_number same as in given DeviceBase object + """ return db.query(models.Device).filter(and_(models.Device.product_id == device.product_id, models.Device.vendor_id == device.vendor_id, models.Device.serial_number == device.serial_number)).first() def create_device(db: Session, device: schemas.DeviceBase): + """ + creates new device with data from given DeviceBase object + """ db_device = models.Device(vendor_id=device.vendor_id, product_id=device.product_id, serial_number=device.serial_number, assigned=False) db.add(db_device) @@ -29,18 +41,30 @@ def create_device(db: Session, device: schemas.DeviceBase): def get_license(db: Session, license_id: int): + """ + returns one specific license by given id + """ return db.query(models.License).filter(models.License.id == license_id).first() def get_licenses(db: Session, skip: int = 0, limit: int = 100): + """ + returns all licenses in database + """ return db.query(models.License).offset(skip).limit(limit).all() def find_license(db: Session, name: str): + """ + finds one license by given string name + """ return db.query(models.License).filter(models.License.name == name).first() def create_license(db: Session, name: str, expdate: date): + """ + creates new license with given name and expiration date + """ db_license = models.License(name=name, expiration_date=expdate) db.add(db_license) db.commit() @@ -49,10 +73,53 @@ def create_license(db: Session, name: str, expdate: date): def get_license_devices(db: Session, license_id: int): + """ + returns all entries in devices_licenses table with given license_id + """ return db.query(models.DeviceLicense).filter(models.DeviceLicense.license_id == license_id).all() +def get_device_licenses(db: Session, device_id: int): + """ + returns all entries in devices_licenses table with given license_id + """ + return db.query(models.DeviceLicense).filter(models.DeviceLicense.device_id == device_id).all() + + +def get_devicelicense_by_devicelicense(db: Session, device_id: int, license_id: int): + """ + returns entry in devices_licenses table with given device id and license id + """ + return db.query(models.DeviceLicense).filter(and_(models.DeviceLicense.device_id == device_id, + models.DeviceLicense.license_id == license_id)).first() + + +def get_bodydevicelicense_by_bodydevicelicense(db: Session, device_id: int, license_id: int): + """ + returns entry in bodydevices_licenses table with given body device id and license id + """ + return db.query(models.BodyDeviceLicense).filter(and_(models.BodyDeviceLicense.bodydevice_id == device_id, + models.BodyDeviceLicense.license_id == license_id)).first() + + +def get_license_bodydevice(db: Session, license_id: int): + """ + returns all entries in bodydevices_licenses with given license_id + """ + return db.query(models.BodyDeviceLicense).filter(models.BodyDeviceLicense.license_id == license_id).all() + + +def get_bodydevice_license(db: Session, device_id: int): + """ + returns all entries in bodydevices_licenses with given license_id + """ + return db.query(models.BodyDeviceLicense).filter(models.BodyDeviceLicense.bodydevice_id == device_id).all() + + def create_device_license(db: Session, device: int, license: int, time: datetime): + """ + creates new entry in devices_licenses table with device id, license id and time. + """ db_device_license = models.DeviceLicense(device_id=device, license_id=license, assigned_datetime=time) db.add(db_device_license) @@ -61,15 +128,56 @@ def create_device_license(db: Session, device: int, license: int, time: datetime return db_device_license +def delete_device_license(db: Session, device: int, license: int): + """ + deletes entry in devices_licenses table with device id, license id and time. + """ + db_device_license = get_devicelicense_by_devicelicense(db, device, license) + db_lic = db.delete(db_device_license) + db.commit() + return db_lic + + +def delete_bodydevice_license(db: Session, device: int, license: int): + """ + deletes entry in devices_licenses table with device id, license id and time. + """ + db_device_license = get_bodydevicelicense_by_bodydevicelicense(db, device, license) + db_lic = db.delete(db_device_license) + db.commit() + return db_lic + + +def create_body_device_license(db: Session, device: int, license: int, time: datetime): + """ + creates new entry in devices_licenses table with device id, license id and time. + """ + db_device_license = models.BodyDeviceLicense(bodydevice_id=device, license_id=license, + assigned_datetime=time) + db.add(db_device_license) + db.commit() + db.refresh(db_device_license) + return db_device_license + + def find_pc_by_username(db: Session, name: str): + """ + Finds one pc by given username + """ return db.query(models.PC).filter(models.PC.username == name).first() def get_pc(db: Session, pc_id: int): + """ + returns one specific pc by given id + """ return db.query(models.PC).filter(models.PC.id == pc_id).first() def update_pc(db: Session, pc_id: int, team: str): + """ + Updates team of one specific pc + """ old_pc = get_pc(db, pc_id) team = get_team(db, int(team)) new = {'id': old_pc.id, 'username': old_pc.username, 'hostname': old_pc.hostname, 'assigned': True, @@ -80,33 +188,66 @@ def update_pc(db: Session, pc_id: int, team: str): db.refresh(old_pc) return old_pc +def change_role(db: Session, usr_id: int, role: str): + """ + Updates team of one specific pc + """ + old_usr = find_user_byid(db, usr_id) + new = {'id': old_usr.id, 'username': old_usr.username, 'password': old_usr.password, 'role': role} + for key, value in new.items(): + setattr(old_usr, key, value) + db.commit() + db.refresh(old_usr) + return old_usr + def get_pcs(db: Session, skip: int = 0, limit: int = 100): + """ + returns all pcs in database + """ return db.query(models.PC).offset(skip).limit(limit).all() def find_pc(db: Session, username: str, hostname: str): + """ + Finds one pc with given username and hostname + """ return db.query(models.PC).filter(and_(models.PC.username == username, models.PC.hostname == hostname)).first() def find_pc_by_name(db: Session, username: str): + """ + Finds one pc by its username + """ return db.query(models.PC).filter(models.PC.username == username).first() def find_pc_by_name_all(db: Session, username: str): + """ + Finds all pcs with same username + """ return db.query(models.PC).filter(models.PC.username == username).offset(0).limit(100).all() def find_pcs(db: Session, pcs: []): + """ + Finds all pcs with ids in given id array + """ return db.query(models.PC).filter(models.PC.id.in_(pcs)).all() def get_pcs_by_team(db: Session, team_id: int): + """ + returns all pcs in given team by team id + """ return db.query(models.PC).filter(models.PC.team_id == team_id).all() def create_pc(db: Session, user: str, host: str): + """ + creates new pc with given username and hostname + """ db_pc = models.PC(username=user, hostname=host, assigned=False) db.add(db_pc) db.commit() @@ -115,18 +256,30 @@ def create_pc(db: Session, user: str, host: str): def get_team(db: Session, team_id: int): + """ + returns one specific team wit given id + """ return db.query(models.Team).filter(models.Team.id == team_id).first() def get_teams(db: Session, skip: int = 0, limit: int = 100): + """ + returns all teams currently saved in database + """ return db.query(models.Team).offset(skip).limit(limit).all() def find_team(db: Session, name: str): + """ + Finds one specific team by its name + """ return db.query(models.Team).filter(models.Team.name == name).first() def create_team(db: Session, name: str): + """ + Creates new team with given name + """ db_team = models.Team(name=name) db.add(db_team) db.commit() @@ -135,18 +288,30 @@ def create_team(db: Session, name: str): def get_head_device(db: Session, head_id: int): + """ + Returns one specific head device by given id + """ return db.query(models.HeadDevice).filter(models.HeadDevice.id == head_id).first() def get_head_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all head devices saved in database + """ return db.query(models.HeadDevice).offset(skip).limit(limit).all() def find_head_device(db: Session, serial: schemas.HeadDeviceBase): + """ + Finds one head device by its serial number + """ return db.query(models.HeadDevice).filter(models.HeadDevice.serial_number == serial.serial_number).first() def create_head_device(db: Session, log: schemas.HeadDeviceBase): + """ + Creates new head device + """ db_head = models.HeadDevice(serial_number=log.serial_number) db.add(db_head) db.commit() @@ -155,18 +320,30 @@ def create_head_device(db: Session, log: schemas.HeadDeviceBase): def get_body_device(db: Session, body_id: int): + """ + Returns one specific body device by given id + """ return db.query(models.BodyDevice).filter(models.BodyDevice.id == body_id).first() def get_body_devices(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all body devices saved in database + """ return db.query(models.BodyDevice).offset(skip).limit(limit).all() def find_body_device(db: Session, serial: schemas.BodyDeviceBase): + """ + Finds one body device by its serial number + """ return db.query(models.BodyDevice).filter(models.BodyDevice.serial_number == serial.serial_number).first() def create_body_device(db: Session, log: schemas.BodyDeviceBase): + """ + Creates new Body device + """ db_body = models.BodyDevice(serial_number=log.serial_number) db.add(db_body) db.commit() @@ -175,10 +352,16 @@ def create_body_device(db: Session, log: schemas.BodyDeviceBase): def get_ld_logs(db: Session, skip: int = 0, limit: int = 100): - return db.query(models.LDLog).offset(skip).limit(limit).all() + """ + Returns all ld debugger logs in database + """ + return db.query(models.LDLog).order_by(desc(models.LDLog.timestamp)).offset(skip).limit(limit).all() def create_ld_logs(db: Session, item: schemas.LDTempBase, head_id: int, body_id: int, pc_id: int, date: datetime): + """ + Creates new ld log for ld_logs database table + """ db_ld = models.LDLog(pc_id=pc_id, timestamp=date, status=item.status, head_id=head_id, body_id=body_id) db.add(db_ld) db.commit() @@ -187,52 +370,159 @@ def create_ld_logs(db: Session, item: schemas.LDTempBase, head_id: int, body_id: def get_logs(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database ordered by timestamp + """ return db.query(models.USBLog).order_by(desc(models.USBLog.timestamp)).offset(skip).limit(limit).all() def get_log(db: Session, device_id: int, skip: int = 0, limit: int = 100): + """ + Returns all usb logs in database sorted by id + """ return db.query(models.USBLog).filter(models.USBLog.device_id == device_id).offset(skip).limit(limit).all() def find_filtered_logs(db: Session, logs: []): + """ + Returns all usb logs with ids in given id array. + """ return db.query(models.USBLog).filter(models.USBLog.id.in_(logs)).order_by(desc(models.USBLog.timestamp)).all() +def find_filtered_ldlogs(db: Session, logs: []): + """ + Returns all ld logs with ids in given id array. + """ + return db.query(models.LDLog).filter(models.LDLog.id.in_(logs)).order_by(desc(models.LDLog.timestamp)).all() + + +def get_filtered_ldlogs(db: Session, pc: str, tema: str, lic: str): + """ + Function creates query string used for filtering by pc username, team name and license name. + Depending on selected filters assembles query string for database + """ + execute_string = "SELECT * FROM ld_logs AS logs" + pcs = find_pc_by_username(db, pc) + if pc != "all": + if pcs is not None: + execute_string += " WHERE logs.pc_id = " + str(pcs.id) + if tema != "all": + team = find_team(db, tema) + if team is not None: + pcst = get_pcs_by_team(db, team.id) + pc_ids = "(" + for p in pcst: + pc_ids += str(p.id) + ", " + def_pc_ids = pc_ids[:-2] + ")" + if pc != "all" and pcs is not None: + if len(def_pc_ids) > 1: + execute_string += " AND logs.pc_id IN " + def_pc_ids + else: + if len(def_pc_ids) > 1: + execute_string += " WHERE logs.pc_id IN " + def_pc_ids + if lic != "all": + license = find_license(db, lic) + if license is not None: + device_licenses = get_license_bodydevice(db, license.id) + dev_ids = "(" + for dev in device_licenses: + dev_ids += str(dev.bodydevice_id) + ", " + defin_ids = dev_ids[:-2] + ")" + if pc != "all" or tema != "all": + if len(defin_ids) > 1: + execute_string += " AND logs.body_id IN " + defin_ids + else: + if len(defin_ids) > 1: + execute_string += " WHERE logs.body_id IN " + defin_ids + + # executing assembled query string + result = db.execute(execute_string) + return result + + def get_filtered_logs(db: Session, pc: str, tema: str, lic: str): + """ + Function creates query string used for filtering by pc username, team name and license name. + Depending on selected filters assembles query string for database + """ execute_string = "SELECT * FROM usb_logs AS logs" + pcs = find_pc_by_username(db, pc) if pc != "all": - pcs = find_pc_by_username(db, pc) - execute_string += " WHERE logs.pc_id = " + str(pcs.id) + if pcs is not None: + execute_string += " WHERE logs.pc_id = " + str(pcs.id) if tema != "all": team = find_team(db, tema) - pcs = get_pcs_by_team(db, team.id) - pc_ids = "(" - for p in pcs: - pc_ids += str(p.id) + ", " - def_pc_ids = pc_ids[:-2] + ")" - if pc != "all": - execute_string += " AND logs.pc_id IN " + def_pc_ids - else: - execute_string += " WHERE logs.pc_id IN " + def_pc_ids + if team is not None: + pcst = get_pcs_by_team(db, team.id) + pc_ids = "(" + for p in pcst: + pc_ids += str(p.id) + ", " + def_pc_ids = pc_ids[:-2] + ")" + if pc != "all" and pcs is not None: + if len(def_pc_ids) > 1: + execute_string += " AND logs.pc_id IN " + def_pc_ids + else: + if len(def_pc_ids) > 1: + execute_string += " WHERE logs.pc_id IN " + def_pc_ids if lic != "all": license = find_license(db, lic) - device_licenses = get_license_devices(db, license.id) - dev_ids = "(" - for dev in device_licenses: - dev_ids += str(dev.device_id) + ", " - defin_ids = dev_ids[:-2] + ")" - if pc != "all" or tema != "all": - execute_string += " AND logs.device_id IN " + defin_ids - else: - execute_string += " WHERE logs.device_id IN " + defin_ids - + if license is not None: + device_licenses = get_license_devices(db, license.id) + dev_ids = "(" + for dev in device_licenses: + dev_ids += str(dev.device_id) + ", " + defin_ids = dev_ids[:-2] + ")" + if pc != "all" or tema != "all": + if len(defin_ids) > 1: + execute_string += " AND logs.device_id IN " + defin_ids + else: + if len(defin_ids) > 1: + execute_string += " WHERE logs.device_id IN " + defin_ids + + # executing assembled query string result = db.execute(execute_string) return result def create_device_logs(db: Session, item: schemas.USBTempBase, dev_id: int, pc_id: int, date: datetime): + """ + Creates new USB log for usb_logs database table + """ db_log = models.USBLog(pc_id=pc_id, timestamp=date, status=item.status, device_id=dev_id) db.add(db_log) db.commit() db.refresh(db_log) return db_log + + +def get_users(db: Session, skip: int = 0, limit: int = 100): + """ + Returns all users saved in database + """ + return db.query(models.User).offset(skip).limit(limit).all() + + +def find_user(db: Session, name: str): + """ + Finds one user by given username + """ + return db.query(models.User).filter(models.User.username == name).first() + + +def find_user_byid(db: Session, id: int): + """ + Finds one user by given id + """ + return db.query(models.User).filter(models.User.id == id).first() + + +def create_user(db: Session, name: str, passw: str, rol: str): + """ + Creates new user + """ + db_user = models.User(username=name, password=passw, role=rol) + db.add(db_user) + db.commit() + db.refresh(db_user) + return db_user diff --git a/server/sql_app/database.py b/server/sql_app/database.py index 6db363036e91348bf4446132ea7903ecfa458809..5269b289b1a53ad2c8f5b6fbae8ce84e121671f7 100644 --- a/server/sql_app/database.py +++ b/server/sql_app/database.py @@ -1,18 +1,25 @@ from sqlalchemy import create_engine from sqlalchemy.ext.declarative import declarative_base from sqlalchemy.orm import sessionmaker + + ''' +# used mainly for testing purposes. Creates local sqllite data file SQLALCHEMY_DATABASE_URL = "sqlite:///./sql_app.db" engine = create_engine( SQLALCHEMY_DATABASE_URL, connect_args={"check_same_thread": False} ) ''' + +# Defining connection url with postgresql database SQLALCHEMY_DATABASE_URL = "postgresql://postgres:postgres@10.5.0.5:5432/usb_api_db" +# Creating engine for database communication engine = create_engine( SQLALCHEMY_DATABASE_URL ) +# Session maker for data transmissions SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine) Base = declarative_base() \ No newline at end of file diff --git a/server/sql_app/main.py b/server/sql_app/main.py index 56e7830fbff46da42e4d9e9b3edcf939b75d28b6..224d1363e3d3d428504a35496094696ae2850a2e 100644 --- a/server/sql_app/main.py +++ b/server/sql_app/main.py @@ -9,21 +9,32 @@ from sql_app.api.usb_logs import usblogs from sql_app.api.usb_logs_web import usblogs_web from sql_app.api.teams import teams from sql_app.api.teams_web import teams_web +from sql_app.api.auth import auth +from sql_app.api.ld_logs_web import ldlogs_web +from sql_app.api.bodydevices_web import body_device_web +from sql_app.api.users_web import users from fastapi import FastAPI app = FastAPI() + +# including routers for endpoints used by clients app.include_router(device) app.include_router(licenses) app.include_router(pcs) app.include_router(usblogs) app.include_router(teams) +# including routers for endpoints called from web app.include_router(device_web) app.include_router(licenses_web) app.include_router(pcs_web) app.include_router(teams_web) app.include_router(usblogs_web) +app.include_router(ldlogs_web) +app.include_router(body_device_web) +app.include_router(users) +app.include_router(auth) ''' if __name__ == "__main__": diff --git a/server/sql_app/models.py b/server/sql_app/models.py index a4837e1c1762671e1f442f105590538553120178..d91cfa57050ca6e26cf2d199bc0f4fb6f98459aa 100644 --- a/server/sql_app/models.py +++ b/server/sql_app/models.py @@ -5,6 +5,9 @@ from .database import Base class Device(Base): + """ + Class defining database table devices + """ __tablename__ = "devices" id = Column(Integer, primary_key=True, index=True) @@ -13,11 +16,16 @@ class Device(Base): serial_number = Column(String, index=True, nullable=False) assigned = Column(Boolean, index=True, nullable=False) + # relationships for foreign keys, thus connecting table with usb_logs and licenses + # tables logs = relationship("USBLog", back_populates="device") licenses = relationship("DeviceLicense", back_populates="device_lic") class USBLog(Base): + """ + Class defining database table usb_logs + """ __tablename__ = "usb_logs" id = Column(Integer, primary_key=True, index=True) @@ -26,21 +34,30 @@ class USBLog(Base): status = Column(String, index=True, nullable=False) device_id = Column(Integer, ForeignKey("devices.id")) + # relationships for foreign keys, thus connecting table with devices and pc + # tables device = relationship("Device", back_populates="logs") pc = relationship("PC", back_populates="logs_pc") class License(Base): + """ + Class defining database table licenses + """ __tablename__ = "licenses" id = Column(Integer, primary_key=True, index=True) name = Column(String, index=True, nullable=False) expiration_date = Column(DateTime(timezone=True), server_default=func.now()) + # relationships for foreign keys, thus connecting table with devices table devices = relationship("DeviceLicense", back_populates="licenses") - + body_devices = relationship("BodyDeviceLicense", back_populates="b_licenses") class DeviceLicense(Base): + """ + Class defining database table devices_licenses + """ __tablename__ = "devices_licenses" id = Column(Integer, primary_key=True, index=True) @@ -48,11 +65,33 @@ class DeviceLicense(Base): license_id = Column(Integer, ForeignKey("licenses.id")) assigned_datetime = Column(String, index=True, nullable=False) + # relationships for foreign keys, thus connecting table with devices and licenses + # tables device_lic = relationship("Device", back_populates="licenses") licenses = relationship("License", back_populates="devices") +class BodyDeviceLicense(Base): + """ + Class defining database table bodydevices_licenses + """ + __tablename__ = "bodydevices_licenses" + + id = Column(Integer, primary_key=True, index=True) + bodydevice_id = Column(Integer, ForeignKey("body_devices.id")) + license_id = Column(Integer, ForeignKey("licenses.id")) + assigned_datetime = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with devices and licenses + # tables + bodydevice_lic = relationship("BodyDevice", back_populates="debug_licenses") + b_licenses = relationship("License", back_populates="body_devices") + + class PC(Base): + """ + Class defining database table pc + """ __tablename__ = "pc" id = Column(Integer, primary_key=True, index=True) @@ -61,38 +100,57 @@ class PC(Base): assigned = Column(Boolean, index=True, nullable=False) team_id = Column(Integer, ForeignKey("teams.id")) + # relationships for foreign keys, thus connecting table with teams, usb_logs and ld_logs + # tables team = relationship("Team", back_populates="pcs") logs_pc = relationship("USBLog", back_populates="pc") ld_pc = relationship("LDLog", back_populates="ldpc") class Team(Base): + """ + Class defining database table teams + """ __tablename__ = "teams" id = Column(Integer, primary_key=True, index=True) name = Column(String, index=True, nullable=False) + + # relationships for foreign keys, thus connecting table with pc table pcs = relationship("PC", back_populates="team") class HeadDevice(Base): + """ + Class defining database table head_devices + """ __tablename__ = "head_devices" id = Column(Integer, primary_key=True, index=True) serial_number = Column(String, index=True, nullable=False) + # relationships for foreign keys, thus connecting table with ld_logs table h_logs = relationship("LDLog", back_populates="head_device") class BodyDevice(Base): + """ + Class defining database table body_devices + """ __tablename__ = "body_devices" id = Column(Integer, primary_key=True, index=True) serial_number = Column(String, index=True, nullable=False) + # relationships for foreign keys, thus connecting table with ld_logs table b_logs = relationship("LDLog", back_populates="body_device") + debug_licenses = relationship("BodyDeviceLicense", back_populates="bodydevice_lic") class LDLog(Base): + """ + Class defining database table ld_logs + """ __tablename__ = "ld_logs" id = Column(Integer, primary_key=True, index=True) @@ -102,6 +160,19 @@ class LDLog(Base): head_id = Column(Integer, ForeignKey("head_devices.id")) body_id = Column(Integer, ForeignKey("body_devices.id")) + # relationships for foreign keys, thus connecting table with pc, head_devices and body_devices + # tables ldpc = relationship("PC", back_populates="ld_pc") head_device = relationship("HeadDevice", back_populates="h_logs") body_device = relationship("BodyDevice", back_populates="b_logs") + +class User(Base): + """ + Class defining user in database with its own role + """ + __tablename__ = "users" + + id = Column(Integer, primary_key=True, index=True) + username = Column(String, index=True, nullable=False) + password = Column(String, index=True, nullable=False) + role = Column(String, index=True, nullable=False) diff --git a/server/sql_app/schemas.py b/server/sql_app/schemas.py index 25baafdd30b5044cf1d48b4647dcd02b5a890e34..79becdc2eec3f3c9d067a1a70613166494be8464 100644 --- a/server/sql_app/schemas.py +++ b/server/sql_app/schemas.py @@ -14,6 +14,9 @@ class DeviceLicenseCreate(DeviceLicenseBase): class DeviceLicense(DeviceLicenseCreate): + """ + Class used for creating and reading devices_licenses entries + """ id: int class Config: @@ -30,6 +33,9 @@ class USBLogCreate(USBLogBase): class USBLog(USBLogBase): + """ + Class used for creating and reading usb_logs entries + """ id: int device_id: int pc_id: int @@ -49,6 +55,9 @@ class DeviceCreate(DeviceBase): class Device(DeviceCreate): + """ + Class used for creating and reading devices entries + """ id: int assigned: bool logs: List[USBLog] = [] @@ -68,6 +77,9 @@ class LDLogCreate(LDLogBase): class LDLog(LDLogCreate): + """ + Class used for creating and reading ld_logs entries + """ id: int head_id: int body_id: int @@ -85,6 +97,9 @@ class BodyDeviceCreate(BodyDeviceBase): class BodyDevice(BodyDeviceCreate): + """ + Class used for creating and reading body_devices entries + """ id: int logs: List[LDLog] = [] @@ -101,6 +116,9 @@ class HeadDeviceCreate(HeadDeviceBase): class HeadDevice(HeadDeviceCreate): + """ + Class used for creating and reading head_devices entries + """ id: int logs: List[LDLog] = [] @@ -118,6 +136,9 @@ class PCCreate(PCBase): class PC(PCCreate): + """ + Class used for creating and reading pc entries + """ id: int assigned: bool logs_pc: List[USBLog] = [] @@ -135,6 +156,9 @@ class TeamCreate(TeamBase): class Team(TeamCreate): + """ + Class used for creating and reading team entries + """ id: int pcs: List[PC] = [] @@ -152,6 +176,9 @@ class LicenseCreate(LicenseBase): class License(LicenseCreate): + """ + Class used for creating and reading licenses entries + """ id: int devices: List[DeviceLicense] = [] @@ -160,6 +187,9 @@ class License(LicenseCreate): class USBTempBase(BaseModel): + """ + Class used for reading data from keyman detecting client messages + """ username: str hostname: str timestamp: str @@ -180,6 +210,9 @@ class USBTemp(USBTempBase): class LDTempBase(BaseModel): + """ + Class used for reading data from debugger detecting client messages + """ username: str hostname: str timestamp: str @@ -199,3 +232,22 @@ class LDTemp(LDTempCreate): class Config: orm_mode = True + + +class UserBase(BaseModel): + """ + Classes used for creating new User entry + """ + username: str + password: str + role: str + +class UserCreate(UserBase): + pass + + +class User(UserCreate): + id: int + + class Config: + orm_mode = True diff --git a/server/templates/auth/login.html b/server/templates/auth/login.html new file mode 100644 index 0000000000000000000000000000000000000000..fa536c5bfbe0385a96e14efb1c13c69b70ee0578 --- /dev/null +++ b/server/templates/auth/login.html @@ -0,0 +1,16 @@ +<!DOCTYPE html> +<html lang="en"> +<head> + <meta charset="UTF-8"> + <title>Login</title> +</head> +<body> +<form action="/login" method="post"> + <label for="username">Username:</label><br> + <input type="text" id="username" name="username"><br><br> + <label for="password">Password:</label> + <input type="password" id="password" name="password"> + <input type="submit" value="LogIn"> +</form> +</body> +</html> \ No newline at end of file diff --git a/server/templates/auth/signup.html b/server/templates/auth/signup.html new file mode 100644 index 0000000000000000000000000000000000000000..b8b19ffc797a0b2239b7340f64b397c62faa7f8a --- /dev/null +++ b/server/templates/auth/signup.html @@ -0,0 +1,16 @@ +<!DOCTYPE html> +<html lang="en"> +<head> + <meta charset="UTF-8"> + <title>Sign Up</title> +</head> +<body> +<form action="/signup" method="post"> + <label for="username">Username:</label><br> + <input type="text" id="username" name="username"><br><br> + <label for="password">Password:</label> + <input type="password" id="password" name="password"> + <input type="submit" value="Signup"> +</form> +</body> +</html> \ No newline at end of file diff --git a/server/templates/body-devices/body_device_license.html b/server/templates/body-devices/body_device_license.html new file mode 100644 index 0000000000000000000000000000000000000000..d0c1896e7237ae44794a98e8e95d23d20b51627b --- /dev/null +++ b/server/templates/body-devices/body_device_license.html @@ -0,0 +1,30 @@ +<!DOCTYPE html> +<html lang="en"> +<head> + <meta charset="UTF-8"> + <title>Body Device License Connect</title> +</head> +<body> +<h6><p>Vendor ID: {{device.vendor_id}}</p> + <p>Serial Number: {{device.serial_number}}</p> +</h6> +<form action="/body-devices-web/{{device.id}}" method="post"> + <label for="lic">Licenses:</label> + <select id="lic" name="lic"> + {% for license in licenses %} + <option value={{license.id}}>{{license.name}}</option> + {% endfor %} + </select> + <input type="submit" value="Connect"> +</form> +<form action="/body-devices-web-del/{{device.id}}" method="post"> + <label for="b_lic">Licenses:</label> + <select id="b_lic" name="b_lic" > + {% for license in dev_lic %} + <option value={{license.id}}>{{license.name}}</option> + {% endfor %} + </select> + <input type="submit" value="Delete"> +</form> +</body> +</html> \ No newline at end of file diff --git a/server/templates/body-devices/body_devices.html b/server/templates/body-devices/body_devices.html new file mode 100644 index 0000000000000000000000000000000000000000..b36a923de4f71ca881433e5dc5df3ec5a2f8431b --- /dev/null +++ b/server/templates/body-devices/body_devices.html @@ -0,0 +1,77 @@ +<html> +<head> + <title>Devices Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/body-devices-web" method="post"> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Serial Number</TH> + <TH>Licenses</TH> + <TH>Status</TH> + </TR> + {% for i in range(devs) %} + <TR> + <TD class="ID"><a href="/body-device-license/{{devices[i].id}}">{{devices[i].id}}</a></TD> + <TD class="Serial Number">{{devices[i].serial_number}}</TD> + <TD class="License"> + {% for lic in devices[i].debug_licenses %} + {{lic.b_licenses.name}}<BR> + {% endfor %} + </TD> + <TD class="Status">{{statuses[i]}}</TD> + </TR> + {% endfor %} + <TR> + <TD class="ID"></TD> + <TD class="Serial Number"></TD> + <TD class="License"> + <form action="/license-create" method="get"> + <input type="submit" value="Add"> + </form> + </TD> + </TR> +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/body-devices/body_devices_normal.html b/server/templates/body-devices/body_devices_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..ece156d223987493533a43f118acbcc14d6cd568 --- /dev/null +++ b/server/templates/body-devices/body_devices_normal.html @@ -0,0 +1,67 @@ +<html> +<head> + <title>Devices Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/body-devices-web" method="post"> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Serial Number</TH> + <TH>Licenses</TH> + <TH>Status</TH> + </TR> + {% for i in range(devs) %} + <TR> + <TD class="ID">{{devices[i].id}}</TD> + <TD class="Serial Number">{{devices[i].serial_number}}</TD> + <TD class="License"> + {% for lic in devices[i].debug_licenses %} + {{lic.b_licenses.name}}<BR> + {% endfor %} + </TD> + <TD class="Status">{{statuses[i]}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/devices/devicelicense.html b/server/templates/devices/devicelicense.html index 054c75ba193a17e000c649fb2f8e8cc09a0f652c..b8f8833dd4606ec05e1482fb2bd95a614e97cc55 100644 --- a/server/templates/devices/devicelicense.html +++ b/server/templates/devices/devicelicense.html @@ -9,7 +9,7 @@ <p>Product ID: {{device.product_id}}</p> <p>Serial Number: {{device.serial_number}}</p> </h6> -<form action="/api/v1/devices-web/{{device.id}}" method="post"> +<form action="/devices-web/{{device.id}}" method="post"> <label for="lic">Licenses:</label> <select id="lic" name="lic"> {% for license in licenses %} @@ -18,5 +18,14 @@ </select> <input type="submit" value="Connect"> </form> +<form action="/devices-web-del/{{device.id}}" method="post"> + <label for="lic_del">Licenses:</label> + <select id="lic_del" name="lic_del"> + {% for license in dev_lic %} + <option value={{license.id}}>{{license.name}}</option> + {% endfor %} + </select> + <input type="submit" value="Delete"> +</form> </body> </html> \ No newline at end of file diff --git a/server/templates/devices/devices.html b/server/templates/devices/devices.html index b5afad1243d52ae6590288aa57422134727074cd..e2f0bb73541eebc935dfdd6b3758c7ae5c731d7f 100644 --- a/server/templates/devices/devices.html +++ b/server/templates/devices/devices.html @@ -3,18 +3,38 @@ <title>Devices Details</title> </head> <body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> <form action="" method="get"> <label for="view">Choose view:</label> <select id="view" name="view" onchange="this.form.action=this.value;"> <option value=""></option> - <option value="/api/v1/logs-web">Logs</option> - <option value="/api/v1/devices-web">Devices</option> - <option value="/api/v1/teams-web">Teams</option> - <option value="/api/v1/pcs-web">PCs</option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> </select> <input type="submit" value="OK"> </form> -<form action="/api/v1/devices-web" method="post"> +<form action="/devices-web" method="post"> <label for="lic">License:</label> <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> <datalist id="licenses"> @@ -35,7 +55,7 @@ </TR> {% for i in range(devs) %} <TR> - <TD class="ID"><a href="/api/v1/device-license/{{devices[i].id}}">{{devices[i].id}}</a></TD> + <TD class="ID"><a href="/device-license/{{devices[i].id}}">{{devices[i].id}}</a></TD> <TD class="Vendor ID">{{devices[i].vendor_id}}</TD> <TD class="Product ID">{{devices[i].product_id}}</TD> <TD class="Serial Number">{{devices[i].serial_number}}</TD> @@ -53,7 +73,7 @@ <TD class="Product ID"></TD> <TD class="Serial Number"></TD> <TD class="License"> - <form action="/api/v1/license-create" method="get"> + <form action="/license-create" method="get"> <input type="submit" value="Add"> </form> </TD> diff --git a/server/templates/devices/devices_normal.html b/server/templates/devices/devices_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..4e0813fe2d7a9867a4ebc58ac58149e10ad456dd --- /dev/null +++ b/server/templates/devices/devices_normal.html @@ -0,0 +1,71 @@ +<html> +<head> + <title>Devices Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/devices-web" method="post"> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Vendor ID</TH> + <TH>Product ID</TH> + <TH>Serial Number</TH> + <TH>Licenses</TH> + <TH>Status</TH> + </TR> + {% for i in range(devs) %} + <TR> + <TD class="ID">{{devices[i].id}}</TD> + <TD class="Vendor ID">{{devices[i].vendor_id}}</TD> + <TD class="Product ID">{{devices[i].product_id}}</TD> + <TD class="Serial Number">{{devices[i].serial_number}}</TD> + <TD class="License"> + {% for lic in devices[i].licenses %} + {{lic.licenses.name}}<BR> + {% endfor %} + </TD> + <TD class="Status">{{statuses[i]}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/ld-logs/ldlogs.html b/server/templates/ld-logs/ldlogs.html new file mode 100644 index 0000000000000000000000000000000000000000..deda9b05f122d1cdf28a05e542d1feb86fa9d02a --- /dev/null +++ b/server/templates/ld-logs/ldlogs.html @@ -0,0 +1,90 @@ +<html> +<head> + <title> LD Logs Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/ldlogs-web" method="post"> + <label for="pc">PC:</label> + <input id="pc" name="pc" type="text" list="pcs" value="" placeholder="all"> + <datalist id="pcs"> + {% for pc in pcs %} + <option value="{{pc.username}}"></option> + {% endfor %} + </datalist> + <label for="team">Team:</label> + <input id="team" name="team" type="text" list="teams" value="" placeholder="all"> + <datalist id="teams"> + {% for team in teams %} + <option value="{{team.name}}"></option> + {% endfor %} + </datalist> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> + <table> + <TR> + <TH>ID</TH> + <TH>PC Username</TH> + <TH>PC Hostname</TH> + <TH>Team</TH> + <TH>Timestamp</TH> + <TH>Status</TH> + <TH>Head Device Serial Number</TH> + <TH>Body Device Serial Number</TH> + </TR> + {% for log in logs %} + <TR> + <TD class="ID">{{log.id}}</TD> + <TD class="Username">{{log.ldpc.username}}</TD> + <TD class="Hostname">{{log.ldpc.hostname}}</TD> + {% if log.ldpc.team == None %} + <TD class="Team">NONE</TD> + {% else %} + <TD class="Team">{{log.ldpc.team.name}}</TD> + {% endif %} + <TD class="Timestamp">{{log.timestamp}}</TD> + <TD class="Status">{{log.status}}</TD> + <TD class="HeadDeviceSerialNumber">{{log.head_device.serial_number}}</TD> + <TD class="BodyDeviceSerialNumber">{{log.body_device.serial_number}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/ld-logs/ldlogs_normal.html b/server/templates/ld-logs/ldlogs_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..0487981caca7dbfc484ad415a7fe1cc0779735cb --- /dev/null +++ b/server/templates/ld-logs/ldlogs_normal.html @@ -0,0 +1,89 @@ +<html> +<head> + <title> LD Logs Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/ldlogs-web" method="post"> + <label for="pc">PC:</label> + <input id="pc" name="pc" type="text" list="pcs" value="" placeholder="all"> + <datalist id="pcs"> + {% for pc in pcs %} + <option value="{{pc.username}}"></option> + {% endfor %} + </datalist> + <label for="team">Team:</label> + <input id="team" name="team" type="text" list="teams" value="" placeholder="all"> + <datalist id="teams"> + {% for team in teams %} + <option value="{{team.name}}"></option> + {% endfor %} + </datalist> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> + <table> + <TR> + <TH>ID</TH> + <TH>PC Username</TH> + <TH>PC Hostname</TH> + <TH>Team</TH> + <TH>Timestamp</TH> + <TH>Status</TH> + <TH>Head Device Serial Number</TH> + <TH>Body Device Serial Number</TH> + </TR> + {% for log in logs %} + <TR> + <TD class="ID">{{log.id}}</TD> + <TD class="Username">{{log.ldpc.username}}</TD> + <TD class="Hostname">{{log.ldpc.hostname}}</TD> + {% if log.ldpc.team == None %} + <TD class="Team">NONE</TD> + {% else %} + <TD class="Team">{{log.ldpc.team.name}}</TD> + {% endif %} + <TD class="Timestamp">{{log.timestamp}}</TD> + <TD class="Status">{{log.status}}</TD> + <TD class="HeadDeviceSerialNumber">{{log.head_device.serial_number}}</TD> + <TD class="BodyDeviceSerialNumber">{{log.body_device.serial_number}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/licenses/license_create.html b/server/templates/licenses/license_create.html index a68f7d8425a89daebc257a9ca6867eda9de70748..861174abfee77b4026697d89570ba2794fcac7db 100644 --- a/server/templates/licenses/license_create.html +++ b/server/templates/licenses/license_create.html @@ -5,11 +5,11 @@ <title>Create a License</title> </head> <body> -<form action="/api/v1/licenses-web" method="post"> +<form action="/licenses-web" method="post"> <label for="name">Name:</label><br> <input type="text" id="name" name="name"><br><br> <label for="expdate">Expiration Date</label> - <input type="date" id="expdate" name="expdate"> + <input type="date" id="expdate" name="expdate" min={{minimum_date}}> <input type="submit" value="Submit"> </form> </body> diff --git a/server/templates/licenses/licenses.html b/server/templates/licenses/licenses.html index e456ab037faea80da2da197ebb65a424a7d3e967..57a9b6120b8f6a7950ecdace9447f34f21370720 100644 --- a/server/templates/licenses/licenses.html +++ b/server/templates/licenses/licenses.html @@ -3,14 +3,34 @@ <title>Licenses Details</title> </head> <body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> <form action="" method="get"> <label for="view">Choose view:</label> <select id="view" name="view" onchange="this.form.action=this.value;"> <option value=""></option> - <option value="/api/v1/logs-web">Logs</option> - <option value="/api/v1/devices-web">Devices</option> - <option value="/api/v1/teams-web">Teams</option> - <option value="/api/v1/pcs-web">PCs</option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> </select> <input type="submit" value="OK"> </form> @@ -28,5 +48,8 @@ </TR> {% endfor %} </table> +<form action="/license-create" method="get"> + <input type="submit" value="Add"> +</form> </body> </html> \ No newline at end of file diff --git a/server/templates/licenses/licenses_normal.html b/server/templates/licenses/licenses_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..2f580d45946659d9a5cfbd8cbe61e97bbc51fc7e --- /dev/null +++ b/server/templates/licenses/licenses_normal.html @@ -0,0 +1,51 @@ +<html> +<head> + <title>Licenses Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Name</TH> + <TH>Expiration Date</TH> + </TR> + {% for license in licenses %} + <TR> + <TD class="ID">{{license.id}}</TD> + <TD class="Vendor ID">{{license.name}}</TD> + <TD class="Product ID">{{license.expiration_date}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/pcs/pcs.html b/server/templates/pcs/pcs.html index 3b0a2eb624651301d7fc00f363b87794dca54337..72295e2076eab9347d68118592678757ebd1d525 100644 --- a/server/templates/pcs/pcs.html +++ b/server/templates/pcs/pcs.html @@ -3,14 +3,34 @@ <title>Pcs Details</title> </head> <body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> <form action="" method="get"> <label for="view">Choose view:</label> <select id="view" name="view" onchange="this.form.action=this.value;"> <option value=""></option> - <option value="/api/v1/logs-web">Logs</option> - <option value="/api/v1/devices-web">Devices</option> - <option value="/api/v1/teams-web">Teams</option> - <option value="/api/v1/pcs-web">PCs</option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> </select> <input type="submit" value="OK"> </form> @@ -23,7 +43,7 @@ </TR> {% for pc in pcs %} <TR> - <TD class="ID"><a href="/api/v1/pc-team/{{pc.id}}">{{pc.id}}</a></TD> + <TD class="ID"><a href="/pc-team/{{pc.id}}">{{pc.id}}</a></TD> <TD class="Vendor ID">{{pc.username}}</TD> <TD class="Product ID">{{pc.hostname}}</TD> {% if pc.team == None %} diff --git a/server/templates/pcs/pcs_normal.html b/server/templates/pcs/pcs_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..b6b6cd54e568b75c25a5705211e25bad7a1a30c8 --- /dev/null +++ b/server/templates/pcs/pcs_normal.html @@ -0,0 +1,57 @@ +<html> +<head> + <title>Pcs Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Username</TH> + <TH>Hostname</TH> + <TH>Team</TH> + </TR> + {% for pc in pcs %} + <TR> + <TD class="ID">{{pc.id}}</TD> + <TD class="Vendor ID">{{pc.username}}</TD> + <TD class="Product ID">{{pc.hostname}}</TD> + {% if pc.team == None %} + <TD class="Team">NONE</TD> + {% else %} + <TD class="Team">{{pc.team.name}}</TD> + {% endif %} + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/pcs/pcteam.html b/server/templates/pcs/pcteam.html index 8559cbc49e5e11bc322e4cc277194822910ce5a7..eebc129a95c5b34982291caf81214fa15287f50e 100644 --- a/server/templates/pcs/pcteam.html +++ b/server/templates/pcs/pcteam.html @@ -8,7 +8,7 @@ <h6><p>Username: {{pc.username}}</p> <p>Hostname: {{pc.hostname}}</p> </h6> -<form action="/api/v1/pcs-web/{{pc.id}}" method="post"> +<form action="/pcs-web/{{pc.id}}" method="post"> <label for="team">Teams:</label> <select id="team" name="team"> {% for team in teams %} diff --git a/server/templates/teams/team_create.html b/server/templates/teams/team_create.html index 3ae1c25443d75026b336cac1ca70945ed29ddbc8..28fb63ddb85b63b8534061ebd69c38ad8668e8ce 100644 --- a/server/templates/teams/team_create.html +++ b/server/templates/teams/team_create.html @@ -5,7 +5,7 @@ <title>Create a Team</title> </head> <body> -<form action="/api/v1/teams-web" method="post"> +<form action="/teams-web-con" method="post"> <label for="name">Name:</label><br> <input type="text" id="name" name="name"><br><br> <input type="submit" value="Submit"> diff --git a/server/templates/teams/teams.html b/server/templates/teams/teams.html index 644f6d9243ccbf2cfd40ea41a56f4c3ce8cef575..f6945e69bf15947f5d4f825f581809b1af13b4f3 100644 --- a/server/templates/teams/teams.html +++ b/server/templates/teams/teams.html @@ -3,14 +3,34 @@ <title>Teams Details</title> </head> <body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> <form action="" method="get"> <label for="view">Choose view:</label> <select id="view" name="view" onchange="this.form.action=this.value;"> <option value=""></option> - <option value="/api/v1/logs-web">Logs</option> - <option value="/api/v1/devices-web">Devices</option> - <option value="/api/v1/teams-web">Teams</option> - <option value="/api/v1/pcs-web">PCs</option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> </select> <input type="submit" value="OK"> </form> @@ -18,15 +38,21 @@ <TR> <TH>ID</TH> <TH>Name</TH> + <TH>Members</TH> </TR> {% for team in teams %} <TR> <TD class="ID">{{team.id}}</TD> - <TD class="Vendor ID">{{team.name}}</TD> + <TD class="Name">{{team.name}}</TD> + <TD class="Members"> + {% for ppl in team.pcs %} + {{ppl.username}}<BR> + {% endfor %} + </TD> </TR> {% endfor %} </table> -<form action="/api/v1/team-create" method="get"> +<form action="/team-create" method="get"> <input type="submit" value="Add"> </form> </body> diff --git a/server/templates/teams/teams_normal.html b/server/templates/teams/teams_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..d25b5b99d0e7dd4d15f06b242afa9dfebfe7873e --- /dev/null +++ b/server/templates/teams/teams_normal.html @@ -0,0 +1,55 @@ +<html> +<head> + <title>Teams Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Name</TH> + <TH>Members</TH> + </TR> + {% for team in teams %} + <TR> + <TD class="ID">{{team.id}}</TD> + <TD class="Vendor ID">{{team.name}}</TD> + <TD class="Members"> + {% for ppl in team.pcs %} + {{ppl.username}}<BR> + {% endfor %} + </TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/usb-logs/crossroad.html b/server/templates/usb-logs/crossroad.html new file mode 100644 index 0000000000000000000000000000000000000000..f553dc4fb040934a9b4e7a5b1b3abc02104c2e5e --- /dev/null +++ b/server/templates/usb-logs/crossroad.html @@ -0,0 +1,59 @@ +<!DOCTYPE html> +<html lang="en"> +<head> + <meta charset="UTF-8"> + <title>Crossroad</title> +</head> +<body> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<h3>Available endpoints are accessible from selectBox above</h3> +<h4>Endpoints are:</h4> +<table> + <TR> + <TH>URL</TH> + <TH>Purpose</TH> + </TR> + <TR> + <TD class="URL">/logs-web</TD> + <TD class="Purpose">Shows all saves Keyman logs. User can filter through license, team and user</TD> + </TR> + <TR> + <TD class="URL">/ldlogs-web</TD> + <TD class="Purpose">Shows all saves LD debugger logs. User can filter through license, team and user</TD> + </TR> + <TR> + <TD class="URL">/devices-web</TD> + <TD class="Purpose">Shows all Keyman devices saved in database and its last state (connected, disconnected)</TD> + </TR> + <TR> + <TD class="URL">/body-devices-web</TD> + <TD class="Purpose">Shows all LD Body devices saved in database and its last state (connected, disconnected)</TD> + </TR> + <TR> + <TD class="URL">/teams-web</TD> + <TD class="Purpose">Shows all teams currently saved in database and its members</TD> + </TR> + <TR> + <TD class="URL">/pcs-web</TD> + <TD class="Purpose">Shows all PCS currently saved in database and its team</TD> + </TR> + <TR> + <TD class="URL">/licenses-web</TD> + <TD class="Purpose">Shows all Licenses currently saved in database and its expiration date</TD> + </TR> +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/usb-logs/logs.html b/server/templates/usb-logs/logs.html index 722c811e9795c4c5cdc5da3b67994641906c8f65..4f1bb0738588f12c16418e5e86fc88761aa387be 100644 --- a/server/templates/usb-logs/logs.html +++ b/server/templates/usb-logs/logs.html @@ -3,18 +3,38 @@ <title>Logs Details</title> </head> <body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> <form action="" method="get"> <label for="view">Choose view:</label> <select id="view" name="view" onchange="this.form.action=this.value;"> <option value=""></option> - <option value="/api/v1/logs-web">Logs</option> - <option value="/api/v1/devices-web">Devices</option> - <option value="/api/v1/teams-web">Teams</option> - <option value="/api/v1/pcs-web">PCs</option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> </select> <input type="submit" value="OK"> </form> -<form action="/api/v1/logs-web" method="post"> +<form action="/logs-web" method="post"> <label for="pc">PC:</label> <input id="pc" name="pc" type="text" list="pcs" value="" placeholder="all"> <datalist id="pcs"> diff --git a/server/templates/usb-logs/logs_normal.html b/server/templates/usb-logs/logs_normal.html new file mode 100644 index 0000000000000000000000000000000000000000..aaf52e878f62d5ddb00a30ae84976857898f6af4 --- /dev/null +++ b/server/templates/usb-logs/logs_normal.html @@ -0,0 +1,89 @@ +<html> +<head> + <title>Logs Details</title> +</head> +<body> +<div style='float:left;padding-right:20px'> +<b>Your role: {{user}}</b> +</div> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + </select> + <input type="submit" value="OK"> +</form> +<form action="/logs-web" method="post"> + <label for="pc">PC:</label> + <input id="pc" name="pc" type="text" list="pcs" value="" placeholder="all"> + <datalist id="pcs"> + {% for pc in pcs %} + <option value="{{pc.username}}"></option> + {% endfor %} + </datalist> + <label for="team">Team:</label> + <input id="team" name="team" type="text" list="teams" value="" placeholder="all"> + <datalist id="teams"> + {% for team in teams %} + <option value="{{team.name}}"></option> + {% endfor %} + </datalist> + <label for="lic">License:</label> + <input id="lic" name="lic" type="text" list="licenses" value="" placeholder="all"> + <datalist id="licenses"> + {% for license in licenses %} + <option value="{{license.name}}"></option> + {% endfor %} + </datalist> + <input type="submit" value="Filter"> +</form> + <table> + <TR> + <TH>ID</TH> + <TH>PC Username</TH> + <TH>PC Hostname</TH> + <TH>Team</TH> + <TH>Timestamp</TH> + <TH>Status</TH> + <TH>Device Product ID</TH> + <TH>Device Serial Number</TH> + </TR> + {% for log in logs %} + <TR> + <TD class="ID">{{log.id}}</TD> + <TD class="Username">{{log.pc.username}}</TD> + <TD class="Hostname">{{log.pc.hostname}}</TD> + {% if log.pc.team == None %} + <TD class="Team">NONE</TD> + {% else %} + <TD class="Team">{{log.pc.team.name}}</TD> + {% endif %} + <TD class="Timestamp">{{log.timestamp}}</TD> + <TD class="Status">{{log.status}}</TD> + <TD class="DeviceProductID">{{log.device.product_id}}</TD> + <TD class="DeviceSerialNumber">{{log.device.serial_number}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file diff --git a/server/templates/users/users.html b/server/templates/users/users.html new file mode 100644 index 0000000000000000000000000000000000000000..dfb9e874eb5cf2bccacc5c7ee5548be60ab4cfdb --- /dev/null +++ b/server/templates/users/users.html @@ -0,0 +1,49 @@ +<html> +<head> + <title>Users Details</title> +</head> +<body> +<div style='float:left;padding-right:5px'> +<form action="/login" method="get"> + <input type="submit" value="Login" /> +</form> +</div> +<div style='float:left;padding-right:5px'> +<form action="/signup" method="get"> + <input type="submit" value="Sign Up" /> +</form> +</div> +<form action="/logout" method="get"> + <input type="submit" value="Logout" /> +</form> +<form action="" method="get"> + <label for="view">Choose view:</label> + <select id="view" name="view" onchange="this.form.action=this.value;"> + <option value=""></option> + <option value="/logs-web">Logs</option> + <option value="/ldlogs-web">LD Logs</option> + <option value="/devices-web">Devices</option> + <option value="/body-devices-web">Body Devices</option> + <option value="/teams-web">Teams</option> + <option value="/pcs-web">PCs</option> + <option value="/licenses-web">Licenses</option> + <option value="/users-web">Users</option> + </select> + <input type="submit" value="OK"> +</form> +<table> + <TR> + <TH>ID</TH> + <TH>Username</TH> + <TH>Role</TH> + </TR> + {% for user in users %} + <TR> + <TD class="ID"><a href="/user-role/{{user.id}}">{{user.id}}</a></TD> + <TD class="Username">{{user.username}}</TD> + <TD class="Role">{{user.role}}</TD> + </TR> + {% endfor %} +</table> +</body> +</html> \ No newline at end of file