diff --git a/changelogs/fragments/131-galaxy-client-context.yml b/changelogs/fragments/131-galaxy-client-context.yml
new file mode 100644
index 0000000..913cff6
--- /dev/null
+++ b/changelogs/fragments/131-galaxy-client-context.yml
@@ -0,0 +1,2 @@
+breaking_changes:
+ - "Remove ``GalaxyClient``'s and ``CollectionDownloader``'s ``galaxy_server`` arguments. You need to explicitly pass in a ``GalaxyContext`` object instead (https://github.com/ansible-community/antsibull-core/pull/131)."
diff --git a/src/antsibull_core/galaxy.py b/src/antsibull_core/galaxy.py
index 2edd9db..c12cbdc 100644
--- a/src/antsibull_core/galaxy.py
+++ b/src/antsibull_core/galaxy.py
@@ -7,7 +7,6 @@
from __future__ import annotations
-import asyncio
import dataclasses
import os.path
import typing as t
@@ -70,7 +69,7 @@ async def create(
Create a new Galaxy context.
:arg aio_session: A ``aiohttp.client.ClientSession`` object.
- :kwarg galaxy_server: A Galaxy server URL. Defaults to ``lib_ctx.get().galaxy_server``.
+ :kwarg galaxy_server: A Galaxy server URL. Defaults to ``lib_ctx.get().galaxy_url``.
"""
if galaxy_server is None:
galaxy_server = str(app_context.lib_ctx.get().galaxy_url)
@@ -96,64 +95,26 @@ async def create(
return cls(galaxy_server, version, base_url)
-_GALAXY_CONTEXT_CACHE: dict[str, t.Union[GalaxyContext, asyncio.Future]] = {}
-
-
-async def _get_cached_galaxy_context(
- aio_session: aiohttp.client.ClientSession, galaxy_server: str
-) -> GalaxyContext:
- context_or_future = _GALAXY_CONTEXT_CACHE.get(galaxy_server)
- if context_or_future is not None:
- if asyncio.isfuture(context_or_future):
- return await context_or_future
- return t.cast(GalaxyContext, context_or_future)
-
- loop = asyncio.get_running_loop()
- future = loop.create_future()
-
- async def _init():
- try:
- context = await GalaxyContext.create(aio_session, galaxy_server)
- future.set_result(context)
- _GALAXY_CONTEXT_CACHE[galaxy_server] = context
- except Exception as exc: # pylint: disable=broad-exception-caught
- future.set_exception(exc)
-
- loop.create_task(_init())
- _GALAXY_CONTEXT_CACHE[galaxy_server] = future
- return await future
-
-
class GalaxyClient:
"""Class for querying the Galaxy REST API."""
def __init__(
self,
aio_session: aiohttp.client.ClientSession,
- galaxy_server: t.Optional[str] = None,
- context: t.Optional[GalaxyContext] = None,
+ *,
+ context: GalaxyContext,
) -> None:
"""
Create a GalaxyClient object to query the Galaxy Server.
:arg aio_session: :obj:`aiohttp.ClientSession` with which to perform all
requests to galaxy.
- :kwarg galaxy_server: URL to the galaxy server. ``context`` must be provided instead
- in the future.
- :kwarg context: A ``GalaxyContext`` instance. Must be provided in the future.
+ :kwarg context: A ``GalaxyContext`` instance. Must be provided.
"""
- if galaxy_server is None and context is None:
- # TODO: deprecate
- galaxy_server = str(app_context.lib_ctx.get().galaxy_url)
- elif context is not None:
- # TODO: deprecate
- if galaxy_server is not None and galaxy_server != context.server:
- raise ValueError(
- f"galaxy_server ({galaxy_server}) does not coincide"
- f" with context.server ({context.server})"
- )
- galaxy_server = context.server
- self.galaxy_server = galaxy_server
+ if context is None:
+ raise ValueError(
+ "The context parameter must be provided to the GalaxyClient constructor"
+ )
self.context = context
self.aio_session = aio_session
self.headers: dict[str, str] = {"Accept": "application/json"}
@@ -165,20 +126,6 @@ def _update_from_context(self, context: GalaxyContext) -> None:
if context.version == GalaxyVersion.V2:
self.params["format"] = "json"
- async def _ensure_context(self) -> GalaxyContext:
- """
- Ensure that ``self.context`` is present.
- """
- context = self.context
- if context is not None:
- return context
- if self.galaxy_server is None:
- raise RuntimeError("Unexpected None for GalaxyClient.galaxy_server")
- context = await _get_cached_galaxy_context(self.aio_session, self.galaxy_server)
- self.context = context
- self._update_from_context(context)
- return context
-
async def _get_galaxy_versions(
self, context: GalaxyContext, versions_url: str, add_params: bool = True
) -> list[str]:
@@ -243,7 +190,7 @@ async def get_versions(self, collection: str) -> list[str]:
:arg collection: Name of the collection to get version info for.
:returns: List of all the versions of this collection on galaxy.
"""
- context = await self._ensure_context()
+ context = self.context
collection = collection.replace(".", "/")
galaxy_url = urljoin(context.base_url, f"collections/{collection}/versions/")
@@ -267,7 +214,7 @@ async def get_info(self, collection: str) -> dict[str, t.Any]:
and the `Galaxy v3 REST API
`_
"""
- context = await self._ensure_context()
+ context = self.context
collection = collection.replace(".", "/")
galaxy_url = urljoin(context.base_url, f"collections/{collection}/")
@@ -305,7 +252,7 @@ async def get_release_info(
and the `Galaxy v3 REST API
`_
"""
- context = await self._ensure_context()
+ context = self.context
collection = collection.replace(".", "/")
galaxy_url = urljoin(
@@ -382,9 +329,9 @@ def __init__(
self,
aio_session: aiohttp.client.ClientSession,
download_dir: StrPath,
- galaxy_server: t.Optional[str] = None,
+ *,
collection_cache: str | None = None,
- context: t.Optional[GalaxyContext] = None,
+ context: GalaxyContext,
trust_collection_cache: t.Optional[bool] = None,
) -> None:
"""
@@ -393,9 +340,7 @@ def __init__(
:arg aio_session: :obj:`aiohttp.ClientSession` with which to perform all
requests to galaxy.
:arg download_dir: Directory to download into.
- :kwarg galaxy_server: URL to the galaxy server. ``context`` must be provided instead
- in the future.
- :kwarg context: A ``GalaxyContext`` instance. Must be provided in the future.
+ :kwarg context: A ``GalaxyContext`` instance. Must be provided.
:kwarg collection_cache: If given, a path to a directory containing collection tarballs.
These tarballs will be used instead of downloading new tarballs provided that the
versions match the criteria (latest compatible version known to galaxy).
@@ -405,7 +350,7 @@ def __init__(
This avoids making a request to the Galaxy server to figure out the artifact's
checksum and comparing it before trusting the cached artifact.
"""
- super().__init__(aio_session, galaxy_server=galaxy_server, context=context)
+ super().__init__(aio_session, context=context)
self.download_dir = download_dir
lib_ctx = app_context.lib_ctx.get()
if collection_cache is None: