Back to index

moin  1.9.0~rc2
Public Member Functions | Public Attributes | Private Attributes
MoinMoin.support.werkzeug.routing.Rule Class Reference
Inheritance diagram for MoinMoin.support.werkzeug.routing.Rule:
Inheritance graph
[legend]
Collaboration diagram for MoinMoin.support.werkzeug.routing.Rule:
Collaboration graph
[legend]

List of all members.

Public Member Functions

def __init__
def empty
def get_rules
def bind
def match
def build
def provides_defaults_for
def suitable_for
def match_compare
def build_compare
def __eq__
def __ne__
def __unicode__
def __str__
def __repr__

Public Attributes

 rule
 is_leaf
 map
 strict_slashes
 subdomain
 defaults
 build_only
 methods
 endpoint
 greediness
 redirect_to
 arguments

Private Attributes

 _trace
 _converters
 _regex
 _weights

Detailed Description

A Rule represents one URL pattern.  There are some options for `Rule`
that change the way it behaves and are passed to the `Rule` constructor.
Note that besides the rule-string all arguments *must* be keyword arguments
in order to not break the application on Werkzeug upgrades.

`string`
    Rule strings basically are just normal URL paths with placeholders in
    the format ``<converter(arguments):name>`` where the converter and the
    arguments are optional.  If no converter is defined the `default`
    converter is used which means `string` in the normal configuration.

    URL rules that end with a slash are branch URLs, others are leaves.
    If you have `strict_slashes` enabled (which is the default), all
    branch URLs that are matched without a trailing slash will trigger a
    redirect to the same URL with the missing slash appended.

    The converters are defined on the `Map`.

`endpoint`
    The endpoint for this rule. This can be anything. A reference to a
    function, a string, a number etc.  The preferred way is using a string
    as because the endpoint is used for URL generation.

`defaults`
    An optional dict with defaults for other rules with the same endpoint.
    This is a bit tricky but useful if you want to have unique URLs::

        url_map = Map([
            Rule('/all/', defaults={'page': 1}, endpoint='all_entries'),
            Rule('/all/page/<int:page>', endpoint='all_entries')
        ])

    If a user now visits ``http://example.com/all/page/1`` he will be
    redirected to ``http://example.com/all/``.  If `redirect_defaults` is
    disabled on the `Map` instance this will only affect the URL
    generation.

`subdomain`
    The subdomain rule string for this rule. If not specified the rule
    only matches for the `default_subdomain` of the map.  If the map is
    not bound to a subdomain this feature is disabled.

    Can be useful if you want to have user profiles on different subdomains
    and all subdomains are forwarded to your application::

        url_map = Map([
            Rule('/', subdomain='<username>', endpoint='user/homepage'),
            Rule('/stats', subdomain='<username>', endpoint='user/stats')
        ])

`methods`
    A sequence of http methods this rule applies to.  If not specified, all
    methods are allowed. For example this can be useful if you want different
    endpoints for `POST` and `GET`.  If methods are defined and the path
    matches but the method matched against is not in this list or in the
    list of another rule for that path the error raised is of the type
    `MethodNotAllowed` rather than `NotFound`.

`strict_slashes`
    Override the `Map` setting for `strict_slashes` only for this rule. If
    not specified the `Map` setting is used.

`build_only`
    Set this to True and the rule will never match but will create a URL
    that can be build. This is useful if you have resources on a subdomain
    or folder that are not handled by the WSGI application (like static data)

`redirect_to`
    If given this must be either a string or callable.  In case of a
    callable it's called with the url adapter that triggered the match and
    the values of the URL as keyword arguments and has to return the target
    for the redirect, otherwise it has to be a string with placeholders in
    rule syntax::

        def foo_with_slug(adapter, id):
            # ask the database for the slug for the old id.  this of
            # course has nothing to do with werkzeug.
            return 'foo/' + Foo.get_slug_for_id(id)

        url_map = Map([
            Rule('/foo/<slug>', endpoint='foo'),
            Rule('/some/old/url/<slug>', redirect_to='foo/<slug>'),
            Rule('/other/old/url/<int:id>', redirect_to=foo_with_slug)
        ])

    When the rule is matched the routing system will raise a
    `RequestRedirect` exception with the target for the redirect.

    Keep in mind that the URL will be joined against the URL root of the
    script so don't use a leading slash on the target URL unless you
    really mean root of that domain.

Definition at line 370 of file routing.py.


Constructor & Destructor Documentation

def MoinMoin.support.werkzeug.routing.Rule.__init__ (   self,
  string,
  defaults = None,
  subdomain = None,
  methods = None,
  build_only = False,
  endpoint = None,
  strict_slashes = None,
  redirect_to = None 
)

Definition at line 466 of file routing.py.

00466 
00467                  redirect_to=None):
00468         if not string.startswith('/'):
00469             raise ValueError('urls must start with a leading slash')
00470         self.rule = string
00471         self.is_leaf = not string.endswith('/')
00472 
00473         self.map = None
00474         self.strict_slashes = strict_slashes
00475         self.subdomain = subdomain
00476         self.defaults = defaults
00477         self.build_only = build_only
00478         if methods is None:
00479             self.methods = None
00480         else:
00481             self.methods = set([x.upper() for x in methods])
00482         self.endpoint = endpoint
00483         self.greediness = 0
00484         self.redirect_to = redirect_to
00485 
00486         self._trace = []
00487         if defaults is not None:
00488             self.arguments = set(map(str, defaults))
00489         else:
00490             self.arguments = set()
00491         self._converters = {}
00492         self._regex = None
00493         self._weights = []


Member Function Documentation

def MoinMoin.support.werkzeug.routing.Rule.__eq__ (   self,
  other 
)

Definition at line 705 of file routing.py.

00705 
00706     def __eq__(self, other):
00707         return self.__class__ is other.__class__ and \
00708                self._trace == other._trace

Here is the caller graph for this function:

def MoinMoin.support.werkzeug.routing.Rule.__ne__ (   self,
  other 
)

Definition at line 709 of file routing.py.

00709 
00710     def __ne__(self, other):
00711         return not self.__eq__(other)

Here is the call graph for this function:

Definition at line 719 of file routing.py.

00719 
00720     def __repr__(self):
00721         if self.map is None:
00722             return '<%s (unbound)>' % self.__class__.__name__
00723         charset = self.map is not None and self.map.charset or 'utf-8'
00724         tmp = []
00725         for is_dynamic, data in self._trace:
00726             if is_dynamic:
00727                 tmp.append('<%s>' % data)
00728             else:
00729                 tmp.append(data)
00730         return '<%s %r%s -> %s>' % (
00731             self.__class__.__name__,
00732             (u''.join(tmp).encode(charset)).lstrip('|'),
00733             self.methods is not None and ' (%s)' % \
00734                 ', '.join(self.methods) or '',
00735             self.endpoint
00736         )
00737 

Definition at line 715 of file routing.py.

00715 
00716     def __str__(self):
00717         charset = self.map is not None and self.map.charset or 'utf-8'
00718         return unicode(self).encode(charset)

Definition at line 712 of file routing.py.

00712 
00713     def __unicode__(self):
00714         return self.rule

Bind the url to a map and create a regular expression based on
the information from the rule itself and the defaults from the map.

:internal:

Definition at line 504 of file routing.py.

00504 
00505     def bind(self, map):
00506         """Bind the url to a map and create a regular expression based on
00507         the information from the rule itself and the defaults from the map.
00508 
00509         :internal:
00510         """
00511         if self.map is not None:
00512             raise RuntimeError('url rule %r already bound to map %r' %
00513                                (self, self.map))
00514         self.map = map
00515         if self.strict_slashes is None:
00516             self.strict_slashes = map.strict_slashes
00517         if self.subdomain is None:
00518             self.subdomain = map.default_subdomain
00519 
00520         rule = self.subdomain + '|' + (self.is_leaf and self.rule
00521                                        or self.rule.rstrip('/'))
00522 
00523         regex_parts = []
00524         for converter, arguments, variable in parse_rule(rule):
00525             if converter is None:
00526                 regex_parts.append(re.escape(variable))
00527                 self._trace.append((False, variable))
00528                 self._weights.append(len(variable))
00529             else:
00530                 convobj = get_converter(map, converter, arguments)
00531                 regex_parts.append('(?P<%s>%s)' % (variable, convobj.regex))
00532                 self._converters[variable] = convobj
00533                 self._trace.append((True, variable))
00534                 self._weights.append(convobj.weight)
00535                 self.arguments.add(str(variable))
00536                 if convobj.is_greedy:
00537                     self.greediness += 1
00538         if not self.is_leaf:
00539             self._trace.append((False, '/'))
00540 
00541         if not self.build_only:
00542             regex = r'^%s%s$' % (
00543                 u''.join(regex_parts),
00544                 (not self.is_leaf or not self.strict_slashes) and \
00545                     '(?<!/)(?P<__suffix__>/?)' or ''
00546             )
00547             self._regex = re.compile(regex, re.UNICODE)

Here is the call graph for this function:

def MoinMoin.support.werkzeug.routing.Rule.build (   self,
  values 
)
Assembles the relative url for that rule and the subdomain.
If building doesn't work for some reasons `None` is returned.

:internal:

Definition at line 584 of file routing.py.

00584 
00585     def build(self, values):
00586         """Assembles the relative url for that rule and the subdomain.
00587         If building doesn't work for some reasons `None` is returned.
00588 
00589         :internal:
00590         """
00591         tmp = []
00592         add = tmp.append
00593         processed = set(self.arguments)
00594         for is_dynamic, data in self._trace:
00595             if is_dynamic:
00596                 try:
00597                     add(self._converters[data].to_url(values[data]))
00598                 except ValidationError:
00599                     return
00600                 processed.add(data)
00601             else:
00602                 add(data)
00603         subdomain, url = (u''.join(tmp)).split('|', 1)
00604 
00605         query_vars = {}
00606         for key in set(values) - processed:
00607             query_vars[key] = unicode(values[key])
00608         if query_vars:
00609             url += '?' + url_encode(query_vars, self.map.charset,
00610                                     sort=self.map.sort_parameters,
00611                                     key=self.map.sort_key)
00612 
00613         return subdomain, url

Here is the call graph for this function:

Compare this object with another one for building.

:internal:

Definition at line 678 of file routing.py.

00678 
00679     def build_compare(self, other):
00680         """Compare this object with another one for building.
00681 
00682         :internal:
00683         """
00684         if not other.arguments and self.arguments:
00685             return -1
00686         elif other.arguments and not self.arguments:
00687             return 1
00688         elif other.defaults is None and self.defaults is not None:
00689             return -1
00690         elif other.defaults is not None and self.defaults is None:
00691             return 1
00692         elif self.provides_defaults_for(other):
00693             return -1
00694         elif other.provides_defaults_for(self):
00695             return 1
00696         elif self.greediness > other.greediness:
00697             return -1
00698         elif self.greediness < other.greediness:
00699             return 1
00700         elif len(self.arguments) > len(other.arguments):
00701             return -1
00702         elif len(self.arguments) < len(other.arguments):
00703             return 1
00704         return -1

Here is the call graph for this function:

Return an unbound copy of this rule.  This can be useful if you
want to reuse an already bound URL for another map.

Definition at line 494 of file routing.py.

00494 
00495     def empty(self):
00496         """Return an unbound copy of this rule.  This can be useful if you
00497         want to reuse an already bound URL for another map."""
00498         return Rule(self.rule, self.defaults, self.subdomain, self.methods,
00499                     self.build_only, self.endpoint, self.strict_slashes,
00500                     self.redirect_to)

Subclasses of `RuleFactory` have to override this method and return
an iterable of rules.

Reimplemented from MoinMoin.support.werkzeug.routing.RuleFactory.

Definition at line 501 of file routing.py.

00501 
00502     def get_rules(self, map):
00503         yield self

Check if the rule matches a given path. Path is a string in the
form ``"subdomain|/path(method)"`` and is assembled by the map.

If the rule matches a dict with the converted values is returned,
otherwise the return value is `None`.

:internal:

Definition at line 548 of file routing.py.

00548 
00549     def match(self, path):
00550         """Check if the rule matches a given path. Path is a string in the
00551         form ``"subdomain|/path(method)"`` and is assembled by the map.
00552 
00553         If the rule matches a dict with the converted values is returned,
00554         otherwise the return value is `None`.
00555 
00556         :internal:
00557         """
00558         if not self.build_only:
00559             m = self._regex.search(path)
00560             if m is not None:
00561                 groups = m.groupdict()
00562                 # we have a folder like part of the url without a trailing
00563                 # slash and strict slashes enabled. raise an exception that
00564                 # tells the map to redirect to the same url but with a
00565                 # trailing slash
00566                 if self.strict_slashes and not self.is_leaf and \
00567                    not groups.pop('__suffix__'):
00568                     raise RequestSlash()
00569                 # if we are not in strict slashes mode we have to remove
00570                 # a __suffix__
00571                 elif not self.strict_slashes:
00572                     del groups['__suffix__']
00573 
00574                 result = {}
00575                 for name, value in groups.iteritems():
00576                     try:
00577                         value = self._converters[name].to_python(value)
00578                     except ValidationError:
00579                         return
00580                     result[str(name)] = value
00581                 if self.defaults is not None:
00582                     result.update(self.defaults)
00583                 return result

Here is the caller graph for this function:

Compare this object with another one for matching.

:internal:

Definition at line 646 of file routing.py.

00646 
00647     def match_compare(self, other):
00648         """Compare this object with another one for matching.
00649 
00650         :internal:
00651         """
00652         for sw, ow in izip(self._weights, other._weights):
00653             if sw > ow:
00654                 return -1
00655             elif sw < ow:
00656                 return 1
00657         if len(self._weights) > len(other._weights):
00658             return -1
00659         if len(self._weights) < len(other._weights):
00660             return 1
00661         if not other.arguments and self.arguments:
00662             return 1
00663         elif other.arguments and not self.arguments:
00664             return -1
00665         elif other.defaults is None and self.defaults is not None:
00666             return 1
00667         elif other.defaults is not None and self.defaults is None:
00668             return -1
00669         elif self.greediness > other.greediness:
00670             return -1
00671         elif self.greediness < other.greediness:
00672             return 1
00673         elif len(self.arguments) > len(other.arguments):
00674             return 1
00675         elif len(self.arguments) < len(other.arguments):
00676             return -1
00677         return 1

Check if this rule has defaults for a given rule.

:internal:

Definition at line 614 of file routing.py.

00614 
00615     def provides_defaults_for(self, rule):
00616         """Check if this rule has defaults for a given rule.
00617 
00618         :internal:
00619         """
00620         return not self.build_only and self.defaults is not None and \
00621                self.endpoint == rule.endpoint and self != rule and \
00622                self.arguments == rule.arguments

Here is the caller graph for this function:

def MoinMoin.support.werkzeug.routing.Rule.suitable_for (   self,
  values,
  method 
)
Check if the dict of values has enough data for url generation.

:internal:

Definition at line 623 of file routing.py.

00623 
00624     def suitable_for(self, values, method):
00625         """Check if the dict of values has enough data for url generation.
00626 
00627         :internal:
00628         """
00629         if self.methods is not None and method not in self.methods:
00630             return False
00631 
00632         valueset = set(values)
00633 
00634         for key in self.arguments - set(self.defaults or ()):
00635             if key not in values:
00636                 return False
00637 
00638         if self.arguments.issubset(valueset):
00639             if self.defaults is None:
00640                 return True
00641             for key, value in self.defaults.iteritems():
00642                 if value != values[key]:
00643                     return False
00644 
00645         return True


Member Data Documentation

Definition at line 490 of file routing.py.

Definition at line 491 of file routing.py.

Definition at line 485 of file routing.py.

Definition at line 492 of file routing.py.

Definition at line 487 of file routing.py.

Definition at line 476 of file routing.py.

Definition at line 475 of file routing.py.

Definition at line 481 of file routing.py.

Definition at line 482 of file routing.py.

Definition at line 470 of file routing.py.

Definition at line 472 of file routing.py.

Definition at line 478 of file routing.py.

Definition at line 483 of file routing.py.

Definition at line 469 of file routing.py.

Definition at line 473 of file routing.py.

Definition at line 474 of file routing.py.


The documentation for this class was generated from the following file: