From 51a519f6538dd244ff5c59fec3770a0f14c8cc71 Mon Sep 17 00:00:00 2001 From: Joseph Schorr Date: Thu, 29 Sep 2016 16:02:44 +0200 Subject: [PATCH] Add hash-based staged rollout to build executors Fixes #1882 --- buildman/manager/executor.py | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/buildman/manager/executor.py b/buildman/manager/executor.py index 2ef5d04c9..70e777564 100644 --- a/buildman/manager/executor.py +++ b/buildman/manager/executor.py @@ -9,6 +9,7 @@ import trollius import datetime import release import socket +import hashlib from jinja2 import FileSystemLoader, Environment from trollius import coroutine, From, Return, get_event_loop @@ -68,11 +69,21 @@ class BuilderExecutor(object): def allowed_for_namespace(self, namespace): """ Returns true if this executor can be used for builds in the given namespace. """ - namespace_whitelist = self.executor_config.get('NAMESPACE_WHITELIST') - if namespace_whitelist is not None: - return namespace in namespace_whitelist - return True + # Check for an explicit namespace whitelist. + namespace_whitelist = self.executor_config.get('NAMESPACE_WHITELIST') + if namespace_whitelist is not None and namespace in namespace_whitelist: + return True + + # Check for a staged rollout percentage. If found, we hash the namespace and, if it is found + # in the first X% of the character space, we allow this executor to be used. + staged_rollout = self.executor_config.get('STAGED_ROLLOUT') + if staged_rollout is not None: + bucket = int(hashlib.sha256(namespace).hexdigest()[-2:], 16) + return bucket < (256 * staged_rollout) + + # If there are no restrictions in place, we are free to use this executor. + return staged_rollout is None and namespace_whitelist is None @property def minimum_retry_threshold(self):