Attention une mise à jour du service Gitlab va être effectuée le mardi 30 novembre entre 17h30 et 18h00. Cette mise à jour va générer une interruption du service dont nous ne maîtrisons pas complètement la durée mais qui ne devrait pas excéder quelques minutes. Cette mise à jour intermédiaire en version 14.0.12 nous permettra de rapidement pouvoir mettre à votre disposition une version plus récente.

Commit ffc1a794 authored by BAIRE Anthony's avatar BAIRE Anthony
Browse files

support handling multiple credentials for docker registries

because it is not a good idea to send our secret token
(for our private registry) to the official docker registry
parent 60058ec0
......@@ -227,6 +227,26 @@ async def _make_aiohttp_client(host):
def make_aiohttp_client(host):
return asyncio.get_event_loop().run_until_complete(_make_aiohttp_client(host))
class DockerAuthConfigDict(dict):
"""dict of authentication credentials for docker.Client
Keys: repository names (or possibly subrepositories)
Values: auth config dicts (suitable for docker.Client.{pull,push})
"""
def get_auth_config(self, image):
"""Get the suitable authentication credential for a given docker_image
Return a 'auth_config' dict or None if no credentials are found
"""
for registry, auth_config in self.items():
if image.startswith(registry):
l = len(registry)
if image[l:l+1] in ("", "/", ":"):
log.debug("select auth_config %r for image %r", registry, image)
return auth_config
log.debug("select no auth_config for image %r", image)
class Manager:
"""A class for scheduling asynchronous jobs on a collection of keys
......@@ -1489,25 +1509,27 @@ class JobManager(Manager):
#
class PullManager(Manager):
def __init__(self, nb_threads, client, name, *, auth_config=None):
def __init__(self, nb_threads, client, name, *,
auth_dict=DockerAuthConfigDict()):
super().__init__(nb_threads, interruptible=True)
self.client = client
self.name = name
self.auth_config = auth_config
self.auth_dict = auth_dict
@asyncio.coroutine
def _process(self, img, reset, rescheduled):
image, version = img
log.info("pull to the %-10s %s:%s", self.name, image, version)
return self.run_in_executor(lambda:
self.client.pull(image, version, auth_config=self.auth_config))
self.client.pull(image, version,
auth_config=self.auth_dict.get_auth_config(image)))
class PushManager(Manager):
def __init__(self, nb_threads, ctrl, *, auth_config=None):
def __init__(self, nb_threads, ctrl, *, auth_dict=DockerAuthConfigDict()):
super().__init__(nb_threads, interruptible=True)
self.ctrl = ctrl
self.auth_config = auth_config
self.auth_dict = auth_dict
@asyncio.coroutine
def _process(self, version_id, reset, rescheduled):
......@@ -1540,8 +1562,9 @@ class PushManager(Manager):
tag = version.number
log.info("push from the %-8s %s:%s", "sandbox", image, tag)
yield from self.run_in_executor(docker_check_error, lambda:
self.ctrl.sandbox.push(image, tag, auth_config=self.auth_config))
yield from self.run_in_executor(lambda: docker_check_error(
self.ctrl.sandbox.push, image, tag,
auth_config=self.auth_dict.get_auth_config(image)))
reset()
......@@ -1571,16 +1594,16 @@ class ImageManager:
nb_push_sandbox = NB_PUSH_SANDBOX,
nb_pull_sandbox = NB_PULL_SANDBOX,
nb_pull_swarm = NB_PULL_SWARM,
*, auth_config=None):
*, auth_dict=None):
self.ctrl = ctrl
self.sandbox_push_manager = PushManager(nb_push_sandbox, ctrl,
auth_config=auth_config)
auth_dict=auth_dict)
self.sandbox_pull_manager = PullManager(nb_pull_sandbox, ctrl.sandbox, "sandbox",
auth_config=auth_config)
auth_dict=auth_dict)
self.swarm_pull_manager = PullManager(nb_pull_swarm, ctrl.swarm, "swarm",
auth_config=auth_config)
auth_dict=auth_dict)
# return a future
@auto_create_task
......@@ -1663,10 +1686,10 @@ class DockerController:
self.cpu_shares = cfg.get("cpus", None, int)
dct = cfg.get("registry_auth", None, dict)
auth_config = {
auth_dict = DockerAuthConfigDict({registry: {
"username": dct.get("username", str, required=True),
"password": dct.get("password", str, required=True),
} if dct else None
}} if dct else {})
self.sandbox = SharedSwarmClient(sandbox_host, config=cfg.get("sandbox", {}, dict), alias="sandbox")
self.sandbox.aiohttp_session, self.sandbox.aiohttp_url = (
......@@ -1685,7 +1708,7 @@ class DockerController:
self.redis_host = redis_host
self.redis_client = None
self.image_manager = ImageManager(self, auth_config=auth_config)
self.image_manager = ImageManager(self, auth_dict=auth_dict)
self.sandbox_manager = SandboxManager(self)
self.job_manager = JobManager(self)
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment