Files
galaxy/lib/tool_shed/managers/model_cache.py
T
Nicola Soranzo 7f89e0eab9 Code cleanups from pyupgrade
Found by running:

```
make pyupgrade
ruff check --fix .
ruff check --preview --unsafe-fixes --select=F401 --fix .
make format
make update-client-api-schema
```

The bulk of the changes are replacements of typing deprecated aliases
such as `Dict` and `List` with the standard library classes. These
aliases became redundant in Python 3.9 when the corresponding
pre-existing classes were enhanced to support `[]`, see
https://docs.python.org/3/library/typing.html#deprecated-aliases

Also:
- Update the `pyupgrade` Makefile target to use `--py38-plus` for the
  packages needed by Pulsar, including the new galaxy-tool-util-models
  package.
2025-07-31 11:17:22 +01:00

63 lines
2.1 KiB
Python

import json
import os
from typing import (
Any,
Optional,
TypeVar,
)
from pydantic import BaseModel
from galaxy.util.hash_util import md5_hash_str
RAW_CACHED_JSON = dict[str, Any]
def hash_model(model_class: type[BaseModel]) -> str:
return md5_hash_str(json.dumps(model_class.model_json_schema()))
MODEL_HASHES: dict[type[BaseModel], str] = {}
M = TypeVar("M", bound=BaseModel)
def ensure_model_has_hash(model_class: type[BaseModel]) -> None:
if model_class not in MODEL_HASHES:
MODEL_HASHES[model_class] = hash_model(model_class)
class ModelCache:
_cache_directory: str
def __init__(self, cache_directory: str):
if not os.path.exists(cache_directory):
os.makedirs(cache_directory)
self._cache_directory = cache_directory
def _cache_target(self, model_class: type[M], tool_id: str, tool_version: str) -> str:
ensure_model_has_hash(model_class)
# consider breaking this into multiple directories...
cache_target = os.path.join(self._cache_directory, MODEL_HASHES[model_class], tool_id, tool_version)
return cache_target
def get_cache_entry_for(self, model_class: type[M], tool_id: str, tool_version: str) -> Optional[M]:
cache_target = self._cache_target(model_class, tool_id, tool_version)
if not os.path.exists(cache_target):
return None
with open(cache_target) as f:
return model_class.model_validate(json.load(f))
def has_cached_entry_for(self, model_class: type[M], tool_id: str, tool_version: str) -> bool:
cache_target = self._cache_target(model_class, tool_id, tool_version)
return os.path.exists(cache_target)
def insert_cache_entry_for(self, model_object: M, tool_id: str, tool_version: str) -> None:
cache_target = self._cache_target(model_object.__class__, tool_id, tool_version)
parent_directory = os.path.dirname(cache_target)
if not os.path.exists(parent_directory):
os.makedirs(parent_directory)
with open(cache_target, "w") as f:
json.dump(model_object.dict(), f)