119 lines
3.0 KiB
Python
119 lines
3.0 KiB
Python
from __future__ import annotations
|
|
|
|
import sqlite3
|
|
import uuid
|
|
from typing import Any
|
|
|
|
from cracklab.server.repositories.methods import MethodsRepository
|
|
from cracklab.server.services.method_definition import (
|
|
MethodDefinitionError,
|
|
validate_method_definition,
|
|
)
|
|
|
|
|
|
class MethodServiceError(ValueError):
|
|
pass
|
|
|
|
|
|
class MethodService:
|
|
def __init__(self, conn: sqlite3.Connection) -> None:
|
|
self._methods = MethodsRepository(conn)
|
|
|
|
def create_method(
|
|
self,
|
|
name: str,
|
|
description: str | None = None,
|
|
method_id: str | None = None,
|
|
) -> str:
|
|
if not name or not name.strip():
|
|
raise MethodServiceError("Method name must not be empty")
|
|
|
|
if method_id is None:
|
|
method_id = f"MTH-{uuid.uuid4().hex}"
|
|
|
|
if not method_id:
|
|
raise MethodServiceError("Method ID must not be empty")
|
|
|
|
self._methods.create_method(
|
|
method_id=method_id,
|
|
name=name.strip(),
|
|
description=description.strip() if description else None,
|
|
)
|
|
|
|
return method_id
|
|
|
|
def create_method_version(
|
|
self,
|
|
method_id: str,
|
|
version: int,
|
|
definition: dict[str, Any],
|
|
) -> None:
|
|
if version <= 0:
|
|
raise MethodServiceError(
|
|
"Method version must be greater than zero"
|
|
)
|
|
|
|
try:
|
|
validate_method_definition(definition)
|
|
except MethodDefinitionError as exc:
|
|
raise MethodServiceError(str(exc)) from exc
|
|
|
|
self._methods.create_method_version(
|
|
method_id=method_id,
|
|
version=version,
|
|
definition=definition,
|
|
)
|
|
|
|
def create_next_method_version(
|
|
self,
|
|
method_id: str,
|
|
definition: dict[str, Any],
|
|
) -> int:
|
|
try:
|
|
validate_method_definition(definition)
|
|
except MethodDefinitionError as exc:
|
|
raise MethodServiceError(str(exc)) from exc
|
|
|
|
version = self._methods.get_next_method_version(method_id)
|
|
|
|
self._methods.create_method_version(
|
|
method_id=method_id,
|
|
version=version,
|
|
definition=definition,
|
|
)
|
|
|
|
return version
|
|
|
|
def get_method(self, method_id: str) -> sqlite3.Row | None:
|
|
return self._methods.get_method(method_id)
|
|
|
|
def list_methods(self) -> list[sqlite3.Row]:
|
|
return self._methods.list_methods()
|
|
|
|
def get_method_version(
|
|
self,
|
|
method_id: str,
|
|
version: int,
|
|
) -> sqlite3.Row | None:
|
|
return self._methods.get_method_version(
|
|
method_id,
|
|
version,
|
|
)
|
|
|
|
def list_method_versions(
|
|
self,
|
|
method_id: str,
|
|
) -> list[sqlite3.Row]:
|
|
return self._methods.list_method_versions(method_id)
|
|
|
|
def get_latest_method_version(
|
|
self,
|
|
method_id: str,
|
|
) -> sqlite3.Row | None:
|
|
versions = self._methods.list_method_versions(method_id)
|
|
|
|
if not versions:
|
|
return None
|
|
|
|
return versions[-1]
|