A lot of things updated.

Signed-off-by: Pavel Kirilin <win10@list.ru>
This commit is contained in:
2024-05-02 04:01:11 +02:00
parent 08c44219b0
commit 8559ec7a85
13 changed files with 2395 additions and 32 deletions

View File

@ -1,10 +1,11 @@
from pathlib import Path from pathlib import Path
from typing import Optional from typing import Optional
from fastapi import FastAPI from fastapi import FastAPI, HTTPException, Request, Response
from fastapi.staticfiles import StaticFiles from fastapi.staticfiles import StaticFiles
from typer import Typer, Argument from typer import Typer, Argument
import uvicorn import uvicorn
from anime.routes import router from anime.routes import router
from starlette.middleware.base import BaseHTTPMiddleware
CURRENT_DIR = Path(__file__).parent CURRENT_DIR = Path(__file__).parent
STATIC_DIR = CURRENT_DIR / "static" STATIC_DIR = CURRENT_DIR / "static"
@ -12,6 +13,20 @@ STATIC_DIR = CURRENT_DIR / "static"
cli = Typer() cli = Typer()
async def response_formatter(request: Request, call_next):
try:
response = await call_next(request)
print(response)
except Exception as e:
response = Response(
status_code=500,
content={
"detail": str(e),
},
)
return response
@cli.command() @cli.command()
def run_app( def run_app(
host: str = "0.0.0.0", host: str = "0.0.0.0",
@ -33,7 +48,9 @@ def run_app(
check_dir=False, check_dir=False,
), ),
) )
app.add_middleware(BaseHTTPMiddleware, dispatch=response_formatter)
app.state.anime_dir = anime_dir app.state.anime_dir = anime_dir
app.state.pid = None
uvicorn.run(app, host=host, port=port, workers=1) uvicorn.run(app, host=host, port=port, workers=1)

View File

@ -1,5 +1,7 @@
import os import os
from pathlib import Path from pathlib import Path
import shutil
import subprocess
from fastapi import APIRouter, HTTPException, Request from fastapi import APIRouter, HTTPException, Request
from anime.dtos import KillRequest, PlayerOffsetRequest from anime.dtos import KillRequest, PlayerOffsetRequest
@ -25,17 +27,54 @@ def start_watching(request: Request) -> None:
anime_dir = request.app.state.anime_dir anime_dir = request.app.state.anime_dir
if not anime_dir: if not anime_dir:
raise HTTPException(status_code=400, detail="Anime directory is not set.") raise HTTPException(status_code=400, detail="Anime directory is not set.")
os.chdir(anime_dir) if request.app.state.pid:
os.system("awatch") try:
os.chdir(CWD) os.kill(request.app.state.pid, 0)
except OSError:
pass
else:
raise HTTPException(
status_code=400,
detail="Awatch is already running.",
)
awatch = shutil.which("awatch")
if awatch is None:
raise Exception(
"awatch command is not available. Please install awatch.\n"
"https://gitlab.le-memese.com/s3rius/awatch/"
)
ret = subprocess.Popen(
[awatch],
cwd=anime_dir,
)
request.app.state.pid = ret.pid
ret.wait()
request.app.state.pid = None
@router.post("/player/offset") @router.post("/player/offset")
async def offset(req: PlayerOffsetRequest) -> None: async def offset(req: PlayerOffsetRequest) -> None:
direction = "+" if req.forward else "-" direction = "+" if req.forward else "-"
os.system(f"playerctl position {req.offset}{direction}") playerctl = shutil.which("playerctl")
if playerctl is None:
raise HTTPException(
status_code=500,
detail="playerctl command is not available.",
)
subprocess.run(
[playerctl, "position", f"{req.offset}{direction}"],
check=False,
)
@router.post("/player/play-pause") @router.post("/player/play-pause")
async def play_pause() -> None: async def play_pause() -> None:
os.system("playerctl play-pause") playerctl = shutil.which("playerctl")
if playerctl is None:
raise HTTPException(
status_code=500,
detail="playerctl command is not available.",
)
subprocess.run([playerctl, "play-pause"], check=False)

View File

@ -1,6 +1,7 @@
import os import os
from pathlib import Path from pathlib import Path
from shutil import copytree, rmtree import shutil
import subprocess
CURRENT_DIR = Path(__file__).parent CURRENT_DIR = Path(__file__).parent
@ -29,15 +30,19 @@ def build(setup_kwargs):
This script is useful for packaging the application. This script is useful for packaging the application.
""" """
print("Starting building frontend ...") print("Starting building frontend ...")
pnpm_path = shutil.which("pnpm")
if pnpm_path is None:
raise Exception("pnpm command is not available. PLease install pnpm.")
with DirChanger(CURRENT_DIR / "frontend"): subprocess.run(
ret_status = os.system("pnpm build") [pnpm_path, "build"],
if ret_status != 0: cwd=CURRENT_DIR / "frontend",
raise Exception("Frontend build failed.") check=True,
)
print("Frontend build finished.") print("Frontend build finished.")
rmtree(STATIC_OUTPUT_DIR, ignore_errors=True) shutil.rmtree(STATIC_OUTPUT_DIR, ignore_errors=True)
copytree(symlinks=True, src=DIST_DIR, dst=STATIC_OUTPUT_DIR) shutil.copytree(symlinks=True, src=DIST_DIR, dst=STATIC_OUTPUT_DIR)
return setup_kwargs return setup_kwargs

1
frontend/.gitignore vendored
View File

@ -11,6 +11,7 @@ node_modules
.DS_Store .DS_Store
dist dist
dist-ssr dist-ssr
dev-dist
coverage coverage
*.local *.local

View File

@ -1,13 +1,18 @@
<!DOCTYPE html> <!DOCTYPE html>
<html lang="en"> <html lang="en">
<head> <head>
<meta charset="UTF-8"> <meta charset="UTF-8">
<link rel="icon" href="/favicon.ico"> <link rel="icon" href="/favicon.ico">
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="viewport" content="width=device-width,initial-scale=1">
<title>Vite App</title> <title>Anime</title>
<link rel="mask-icon" href="/mask-icon.svg" color="#FFFFFF">
<meta name="theme-color" content="#ffffff">
</head> </head>
<body> <body>
<div id="app"></div> <div id="app"></div>
<script type="module" src="/src/main.js"></script> <script type="module" src="/src/main.js"></script>
</body> </body>
</html> </html>

View File

@ -24,6 +24,7 @@
"eslint-plugin-vue": "^9.23.0", "eslint-plugin-vue": "^9.23.0",
"prettier": "^3.2.5", "prettier": "^3.2.5",
"vite": "^5.2.8", "vite": "^5.2.8",
"vite-plugin-pwa": "^0.20.0",
"vite-plugin-vue-devtools": "^7.0.25" "vite-plugin-vue-devtools": "^7.0.25"
} }
} }

2274
frontend/pnpm-lock.yaml generated

File diff suppressed because it is too large Load Diff

BIN
frontend/public/icon.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 67 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

View File

@ -1,5 +1,5 @@
<script setup> <script setup>
import { Tabbar, TabbarItem, ActionBar, ActionBarButton } from 'vant'; import { ActionBar, ActionBarButton } from 'vant';
import { postRequest } from '@/utils' import { postRequest } from '@/utils'

View File

@ -1,3 +1,5 @@
import { showFailToast } from 'vant';
async function postRequest(url, data) { async function postRequest(url, data) {
const response = await fetch(url, { const response = await fetch(url, {
method: 'POST', method: 'POST',
@ -6,7 +8,13 @@ async function postRequest(url, data) {
}, },
body: JSON.stringify(data) body: JSON.stringify(data)
}) })
return response.json() const resp_data = await response.json()
if (!response.ok) {
showFailToast({
message: resp_data.detail
})
}
return resp_data
} }

View File

@ -2,11 +2,36 @@ import { fileURLToPath, URL } from 'node:url'
import { defineConfig } from 'vite' import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue' import vue from '@vitejs/plugin-vue'
import { VitePWA } from 'vite-plugin-pwa'
// https://vitejs.dev/config/ // https://vitejs.dev/config/
export default defineConfig({ export default defineConfig({
plugins: [ plugins: [
vue(), vue(),
VitePWA({
manifest: {
name: 'Anime',
short_name: 'Anime',
start_url: '/',
theme_color: '#000000',
icons: [
{
src: '/pwa-192x192.jpg',
sizes: '192x192',
type: 'image/jpeg',
},
{
src: '/pwa-512x512.jpg',
sizes: '512x512',
type: 'image/jpeg',
}
]
},
devOptions: {
enabled: true,
},
registerType: "autoUpdate",
})
], ],
resolve: { resolve: {
alias: { alias: {