Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(85)

Unified Diff: third_party/recipe_engine/field_composer.py

Issue 1347263002: Revert of Cross-repo recipe package system. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/tools/build
Patch Set: Created 5 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « third_party/recipe_engine/expect_tests/util.py ('k') | third_party/recipe_engine/lint_test.py » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: third_party/recipe_engine/field_composer.py
diff --git a/third_party/recipe_engine/field_composer.py b/third_party/recipe_engine/field_composer.py
new file mode 100644
index 0000000000000000000000000000000000000000..37c72934c69a7e763274ff0f9b4c7be68481e9a0
--- /dev/null
+++ b/third_party/recipe_engine/field_composer.py
@@ -0,0 +1,86 @@
+# Copyright 2013-2015 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+
+class FieldComposerError(BaseException):
+ """Base error class for this module."""
+ pass
+
+
+class RegistryConflict(FieldComposerError):
+ pass
+
+
+class DegenerateRegistryError(FieldComposerError):
+ pass
+
+
+class CompositionUndefined(FieldComposerError):
+ pass
+
+
+class FieldComposer(object):
+
+ def __init__(self, fields, registered_functors):
+ """Initialize the internal registry mapping names to functors."""
+ try:
+ self._registry = {
+ name: {'combine': value['combine']}
+ for name, value in registered_functors.iteritems()}
+ except KeyError:
+ raise DegenerateRegistryError(
+ 'Registry entries must contain key "combine."')
+ self._fields = fields
+
+ def __contains__(self, key):
+ return key in self._fields
+
+ def __getitem__(self, key):
+ return self._fields[key]
+
+ def get(self, index, default=None):
+ """Wrapper for self._fields.get."""
+ return self._fields.get(index, default)
+
+ def iteritems(self):
+ """Wrapper for self._fields.iteritems."""
+ return self._fields.iteritems()
+
+ def compose(self, second_compositor):
+ """Return the monoidal composition of two FieldComposers."""
+ # If second_compositor is a FieldComposer, registries shouldn't conflict.
+ if isinstance(second_compositor, dict):
+ second_compositor = FieldComposer(second_compositor, {})
+ new_registry = self._registry.copy()
+ second_registry = second_compositor._registry
+ for key, value in second_registry.iteritems():
+ if key in self._registry and value != self._registry[key]:
+ raise RegistryConflict('Conflicting values for key %s.' % key)
+ new_registry[key] = value
+
+ # populate new field dictionary with composed values
+ all_keys = set().union(self._fields, second_compositor._fields)
+ new_fields = {}
+ for name in all_keys:
+ if name not in new_registry:
+ raise CompositionUndefined(
+ "No combine function registered for %s." % name)
+ if name in second_compositor:
+ new_value = self.get_with_context(name, second_compositor[name])
+ else:
+ # Name is in exactly one compositor, so get that value.
+ new_value = self[name]
+ new_fields[name] = new_value
+
+ # create and return the new compositor
+ return FieldComposer(new_fields, new_registry)
+
+ def get_with_context(self, key, value):
+ """Combine the current value for key (if any) with value."""
+ if key not in self._registry:
+ raise CompositionUndefined(
+ "No combine function registered for %s." % key)
+ if key in self:
+ return self._registry[key]['combine'](self.get(key), value)
+ return value
« no previous file with comments | « third_party/recipe_engine/expect_tests/util.py ('k') | third_party/recipe_engine/lint_test.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698