110 lines
2.9 KiB
Python
110 lines
2.9 KiB
Python
import asyncio
|
|
import re
|
|
from io import BytesIO
|
|
|
|
from cache import AsyncTTL
|
|
from cache.key import KEY
|
|
from webdav3.client import Client as WebDAVclient
|
|
|
|
from .settings import SETTINGS
|
|
|
|
|
|
class WebDAV:
|
|
_webdav_client = WebDAVclient(
|
|
{
|
|
"webdav_hostname": SETTINGS.webdav.url,
|
|
"webdav_login": SETTINGS.webdav.username,
|
|
"webdav_password": SETTINGS.webdav.password,
|
|
}
|
|
)
|
|
|
|
@classmethod
|
|
@AsyncTTL(time_to_live=SETTINGS.webdav.cache_ttl, skip_args=1)
|
|
async def list_files(
|
|
cls,
|
|
directory: str = "",
|
|
*,
|
|
regex: re.Pattern[str] = re.compile(""),
|
|
) -> list[str]:
|
|
"""
|
|
Liste aller Dateien im Ordner `directory`, die zur RegEx `regex` passen
|
|
"""
|
|
|
|
loop = asyncio.get_running_loop()
|
|
ls = await loop.run_in_executor(
|
|
None,
|
|
cls._webdav_client.list,
|
|
directory,
|
|
)
|
|
|
|
return [f"{directory}/{path}" for path in ls if regex.search(path)]
|
|
|
|
@classmethod
|
|
@AsyncTTL(time_to_live=SETTINGS.webdav.cache_ttl, skip_args=1)
|
|
async def file_exists(cls, path: str) -> bool:
|
|
"""
|
|
`True`, wenn an Pfad `path` eine Datei existiert
|
|
"""
|
|
|
|
loop = asyncio.get_running_loop()
|
|
return await loop.run_in_executor(
|
|
None,
|
|
cls._webdav_client.check,
|
|
path,
|
|
)
|
|
|
|
@classmethod
|
|
@(_rb_ttl := AsyncTTL(time_to_live=SETTINGS.webdav.cache_ttl, skip_args=1))
|
|
async def read_bytes(cls, path: str) -> bytes:
|
|
"""
|
|
Datei aus Pfad `path` als bytes laden
|
|
"""
|
|
|
|
buffer = BytesIO()
|
|
loop = asyncio.get_running_loop()
|
|
await loop.run_in_executor(
|
|
None,
|
|
cls._webdav_client.resource(path).write_to,
|
|
buffer,
|
|
)
|
|
buffer.seek(0)
|
|
|
|
return buffer.read()
|
|
|
|
@classmethod
|
|
async def read_str(cls, path: str, encoding="utf-8") -> str:
|
|
"""
|
|
Datei aus Pfad `path` als string laden
|
|
"""
|
|
|
|
return (await cls.read_bytes(path)).decode(encoding=encoding).strip()
|
|
|
|
@classmethod
|
|
async def write_bytes(cls, path: str, buffer: bytes) -> None:
|
|
"""
|
|
Bytes `buffer` in Datei in Pfad `path` schreiben
|
|
"""
|
|
|
|
loop = asyncio.get_running_loop()
|
|
await loop.run_in_executor(
|
|
None,
|
|
cls._webdav_client.resource(path).read_from,
|
|
buffer,
|
|
)
|
|
|
|
try:
|
|
# hack: zugehörigen Cache-Eintrag entfernen
|
|
# -> AsyncTTL._TTL.__contains__
|
|
del cls._rb_ttl.ttl[KEY((path,), {})]
|
|
|
|
except KeyError:
|
|
# Cache-Eintrag existierte nicht
|
|
pass
|
|
|
|
@classmethod
|
|
async def write_str(cls, path: str, content: str, encoding="utf-8") -> None:
|
|
"""
|
|
String `content` in Datei in Pfad `path` schreiben
|
|
"""
|
|
|
|
await cls.write_bytes(path, content.encode(encoding=encoding))
|