Michael Merickel
2018-10-15 81576ee51564c49d5ff3c1c07f214f22a8438231
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
from pyramid.interfaces import (
    ILocaleNegotiator,
    ITranslationDirectories,
    )
 
from pyramid.exceptions import ConfigurationError
from pyramid.path import AssetResolver
 
from pyramid.config.util import action_method
 
class I18NConfiguratorMixin(object):
    @action_method
    def set_locale_negotiator(self, negotiator):
        """
        Set the :term:`locale negotiator` for this application.  The
        :term:`locale negotiator` is a callable which accepts a
        :term:`request` object and which returns a :term:`locale
        name`.  The ``negotiator`` argument should be the locale
        negotiator implementation or a :term:`dotted Python name`
        which refers to such an implementation.
 
        Later calls to this method override earlier calls; there can
        be only one locale negotiator active at a time within an
        application.  See :ref:`activating_translation` for more
        information.
 
        .. note::
 
           Using the ``locale_negotiator`` argument to the
           :class:`pyramid.config.Configurator` constructor can be used to
           achieve the same purpose.
        """
        def register():
            self._set_locale_negotiator(negotiator)
        intr = self.introspectable('locale negotiator', None,
                                   self.object_description(negotiator),
                                   'locale negotiator')
        intr['negotiator'] = negotiator
        self.action(ILocaleNegotiator, register, introspectables=(intr,))
 
    def _set_locale_negotiator(self, negotiator):
        locale_negotiator = self.maybe_dotted(negotiator)
        self.registry.registerUtility(locale_negotiator, ILocaleNegotiator)
 
    @action_method
    def add_translation_dirs(self, *specs, **kw):
        """ Add one or more :term:`translation directory` paths to the
        current configuration state.  The ``specs`` argument is a
        sequence that may contain absolute directory paths
        (e.g. ``/usr/share/locale``) or :term:`asset specification`
        names naming a directory path (e.g. ``some.package:locale``)
        or a combination of the two.
 
        Example:
 
        .. code-block:: python
 
           config.add_translation_dirs('/usr/share/locale',
                                       'some.package:locale')
 
        The translation directories are defined as a list in which
        translations defined later have precedence over translations defined
        earlier.
 
        By default, consecutive calls to ``add_translation_dirs`` will add
        directories to the start of the list. This means later calls to
        ``add_translation_dirs`` will have their translations trumped by
        earlier calls. If you explicitly need this call to trump an earlier
        call then you may set ``override`` to ``True``.
 
        If multiple specs are provided in a single call to
        ``add_translation_dirs``, the directories will be inserted in the
        order they're provided (earlier items are trumped by later items).
 
        .. versionchanged:: 1.8
 
           The ``override`` parameter was added to allow a later call
           to ``add_translation_dirs`` to override an earlier call, inserting
           folders at the beginning of the translation directory list.
 
        """
        introspectables = []
        override = kw.pop('override', False)
        if kw:
            raise TypeError('invalid keyword arguments: %s', sorted(kw.keys()))
 
        def register():
            directories = []
            resolver = AssetResolver(self.package_name)
 
            # defer spec resolution until register to allow for asset
            # overrides to take place in an earlier config phase
            for spec in specs:
                # the trailing slash helps match asset overrides for folders
                if not spec.endswith('/'):
                    spec += '/'
                asset = resolver.resolve(spec)
                directory = asset.abspath()
                if not asset.isdir():
                    raise ConfigurationError('"%s" is not a directory' %
                                            directory)
                intr = self.introspectable('translation directories', directory,
                                        spec, 'translation directory')
                intr['directory'] = directory
                intr['spec'] = spec
                introspectables.append(intr)
                directories.append(directory)
 
            tdirs = self.registry.queryUtility(ITranslationDirectories)
            if tdirs is None:
                tdirs = []
                self.registry.registerUtility(tdirs, ITranslationDirectories)
            if override:
                tdirs.extend(directories)
            else:
                for directory in reversed(directories):
                    tdirs.insert(0, directory)
 
        self.action(None, register, introspectables=introspectables)