Chromium Code Reviews| Index: tools/checkdeps/rules.py |
| diff --git a/tools/checkdeps/rules.py b/tools/checkdeps/rules.py |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..830384b3c8ae98e1fccced520eaf5afbe2849525 |
| --- /dev/null |
| +++ b/tools/checkdeps/rules.py |
| @@ -0,0 +1,89 @@ |
| +#!/usr/bin/env python |
|
M-A Ruel
2012/07/26 13:50:51
This file is not executable
Jói
2012/07/26 17:05:52
Done.
|
| +# Copyright (c) 2012 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. |
| + |
| +"""Base classes to represent dependency rules, used by checkdeps.py""" |
| + |
|
M-A Ruel
2012/07/26 13:50:51
2 lines
|
| +class Rule(object): |
| + """Specifies a single rule for an include, which can be one of |
| + ALLOW, DISALLOW and TEMP_ALLOW. |
| + """ |
| + |
| + # These are the prefixes used to indicate each type of rule. These |
| + # are also used as values for self.allow to indicate which type of |
| + # rule this is. |
| + ALLOW = "+" |
| + DISALLOW = "-" |
| + TEMP_ALLOW = "!" |
| + |
| + def __init__(self, allow, directory, source): |
| + self.allow = allow |
| + self._dir = directory |
| + self._source = source |
| + |
| + def __str__(self): |
| + return '"%s%s" from %s.' % (self.allow, self._dir, self._source) |
| + |
| + def ParentOrMatch(self, other): |
| + """Returns true if the input string is an exact match or is a parent |
| + of the current rule. For example, the input "foo" would match "foo/bar".""" |
| + return self._dir == other or self._dir.startswith(other + "/") |
| + |
| + def ChildOrMatch(self, other): |
| + """Returns true if the input string would be covered by this rule. For |
| + example, the input "foo/bar" would match the rule "foo".""" |
| + return self._dir == other or other.startswith(self._dir + "/") |
| + |
| + |
| +def ParseRuleString(rule_string, source): |
| + """Returns a tuple of a boolean indicating whether the directory is an allow |
| + rule, and a string holding the directory name. |
| + """ |
| + if not rule_string: |
| + raise Exception('The rule string "%s" is empty\nin %s' % |
| + (rule_string, source)) |
| + |
| + if not rule_string[0] in [Rule.ALLOW, Rule.DISALLOW, Rule.TEMP_ALLOW]: |
| + raise Exception( |
| + 'The rule string "%s" does not begin with a "+", "-" or "!".' % |
| + rule_string) |
| + |
| + return (rule_string[0], rule_string[1:]) |
| + |
| + |
| +class Rules(object): |
| + def __init__(self): |
| + """Initializes the current rules with an empty rule list.""" |
| + self._rules = [] |
| + |
| + def __str__(self): |
| + return 'Rules = [\n%s]' % '\n'.join(' %s' % x for x in self._rules) |
| + |
| + def AddRule(self, rule_string, source): |
| + """Adds a rule for the given rule string. |
| + |
| + Args: |
| + rule_string: The include_rule string read from the DEPS file to apply. |
| + source: A string representing the location of that string (filename, etc.) |
| + so that we can give meaningful errors. |
| + """ |
| + (add_rule, rule_dir) = ParseRuleString(rule_string, source) |
| + # Remove any existing rules or sub-rules that apply. For example, if we're |
| + # passed "foo", we should remove "foo", "foo/bar", but not "foobar". |
| + self._rules = [x for x in self._rules if not x.ParentOrMatch(rule_dir)] |
|
M-A Ruel
2012/07/26 13:50:51
I would probably have used instead:
self._rules =
|
| + self._rules.insert(0, Rule(add_rule, rule_dir, source)) |
| + |
| + def DirAllowed(self, allowed_dir): |
| + """Returns a tuple (success, message), where success indicates if the given |
| + directory is allowed given the current set of rules, and the message tells |
| + why if the comparison failed.""" |
| + for rule in self._rules: |
| + if rule.ChildOrMatch(allowed_dir): |
| + # This rule applies. |
| + why_failed = "" |
| + if rule.allow != Rule.ALLOW: |
| + why_failed = rule.__str__() |
|
M-A Ruel
2012/07/26 13:50:51
str(rule)
Jói
2012/07/26 17:05:52
Done.
|
| + return (rule.allow, why_failed) |
| + # No rules apply, fail. |
| + return (Rule.DISALLOW, "no rule applying") |