Project

General

Profile

Statistics
| Branch: | Revision:

root / env / lib / python2.7 / site-packages / django / utils / six.py @ 1a305335

History | View | Annotate | Download (10.6 KB)

1 1a305335 officers
"""Utilities for writing code that runs on Python 2 and 3"""
2
3
import operator
4
import sys
5
import types
6
7
__author__ = "Benjamin Peterson <benjamin@python.org>"
8
__version__ = "1.2.0"
9
10
11
# True if we are running on Python 3.
12
PY3 = sys.version_info[0] == 3
13
14
if PY3:
15
    string_types = str,
16
    integer_types = int,
17
    class_types = type,
18
    text_type = str
19
    binary_type = bytes
20
21
    MAXSIZE = sys.maxsize
22
else:
23
    string_types = basestring,
24
    integer_types = (int, long)
25
    class_types = (type, types.ClassType)
26
    text_type = unicode
27
    binary_type = str
28
29
    if sys.platform == "java":
30
        # Jython always uses 32 bits.
31
        MAXSIZE = int((1 << 31) - 1)
32
    else:
33
        # It's possible to have sizeof(long) != sizeof(Py_ssize_t).
34
        class X(object):
35
            def __len__(self):
36
                return 1 << 31
37
        try:
38
            len(X())
39
        except OverflowError:
40
            # 32-bit
41
            MAXSIZE = int((1 << 31) - 1)
42
        else:
43
            # 64-bit
44
            MAXSIZE = int((1 << 63) - 1)
45
            del X
46
47
48
def _add_doc(func, doc):
49
    """Add documentation to a function."""
50
    func.__doc__ = doc
51
52
53
def _import_module(name):
54
    """Import module, returning the module after the last dot."""
55
    __import__(name)
56
    return sys.modules[name]
57
58
59
class _LazyDescr(object):
60
61
    def __init__(self, name):
62
        self.name = name
63
64
    def __get__(self, obj, tp):
65
        result = self._resolve()
66
        setattr(obj, self.name, result)
67
        # This is a bit ugly, but it avoids running this again.
68
        delattr(tp, self.name)
69
        return result
70
71
72
class MovedModule(_LazyDescr):
73
74
    def __init__(self, name, old, new=None):
75
        super(MovedModule, self).__init__(name)
76
        if PY3:
77
            if new is None:
78
                new = name
79
            self.mod = new
80
        else:
81
            self.mod = old
82
83
    def _resolve(self):
84
        return _import_module(self.mod)
85
86
87
class MovedAttribute(_LazyDescr):
88
89
    def __init__(self, name, old_mod, new_mod, old_attr=None, new_attr=None):
90
        super(MovedAttribute, self).__init__(name)
91
        if PY3:
92
            if new_mod is None:
93
                new_mod = name
94
            self.mod = new_mod
95
            if new_attr is None:
96
                if old_attr is None:
97
                    new_attr = name
98
                else:
99
                    new_attr = old_attr
100
            self.attr = new_attr
101
        else:
102
            self.mod = old_mod
103
            if old_attr is None:
104
                old_attr = name
105
            self.attr = old_attr
106
107
    def _resolve(self):
108
        module = _import_module(self.mod)
109
        return getattr(module, self.attr)
110
111
112
113
class _MovedItems(types.ModuleType):
114
    """Lazy loading of moved objects"""
115
116
117
_moved_attributes = [
118
    MovedAttribute("cStringIO", "cStringIO", "io", "StringIO"),
119
    MovedAttribute("filter", "itertools", "builtins", "ifilter", "filter"),
120
    MovedAttribute("input", "__builtin__", "builtins", "raw_input", "input"),
121
    MovedAttribute("map", "itertools", "builtins", "imap", "map"),
122
    MovedAttribute("reload_module", "__builtin__", "imp", "reload"),
123
    MovedAttribute("reduce", "__builtin__", "functools"),
124
    MovedAttribute("StringIO", "StringIO", "io"),
125
    MovedAttribute("xrange", "__builtin__", "builtins", "xrange", "range"),
126
    MovedAttribute("zip", "itertools", "builtins", "izip", "zip"),
127
128
    MovedModule("builtins", "__builtin__"),
129
    MovedModule("configparser", "ConfigParser"),
130
    MovedModule("copyreg", "copy_reg"),
131
    MovedModule("http_cookiejar", "cookielib", "http.cookiejar"),
132
    MovedModule("http_cookies", "Cookie", "http.cookies"),
133
    MovedModule("html_entities", "htmlentitydefs", "html.entities"),
134
    MovedModule("html_parser", "HTMLParser", "html.parser"),
135
    MovedModule("http_client", "httplib", "http.client"),
136
    MovedModule("BaseHTTPServer", "BaseHTTPServer", "http.server"),
137
    MovedModule("CGIHTTPServer", "CGIHTTPServer", "http.server"),
138
    MovedModule("SimpleHTTPServer", "SimpleHTTPServer", "http.server"),
139
    MovedModule("cPickle", "cPickle", "pickle"),
140
    MovedModule("queue", "Queue"),
141
    MovedModule("reprlib", "repr"),
142
    MovedModule("socketserver", "SocketServer"),
143
    MovedModule("tkinter", "Tkinter"),
144
    MovedModule("tkinter_dialog", "Dialog", "tkinter.dialog"),
145
    MovedModule("tkinter_filedialog", "FileDialog", "tkinter.filedialog"),
146
    MovedModule("tkinter_scrolledtext", "ScrolledText", "tkinter.scrolledtext"),
147
    MovedModule("tkinter_simpledialog", "SimpleDialog", "tkinter.simpledialog"),
148
    MovedModule("tkinter_tix", "Tix", "tkinter.tix"),
149
    MovedModule("tkinter_constants", "Tkconstants", "tkinter.constants"),
150
    MovedModule("tkinter_dnd", "Tkdnd", "tkinter.dnd"),
151
    MovedModule("tkinter_colorchooser", "tkColorChooser",
152
                "tkinter.colorchooser"),
153
    MovedModule("tkinter_commondialog", "tkCommonDialog",
154
                "tkinter.commondialog"),
155
    MovedModule("tkinter_tkfiledialog", "tkFileDialog", "tkinter.filedialog"),
156
    MovedModule("tkinter_font", "tkFont", "tkinter.font"),
157
    MovedModule("tkinter_messagebox", "tkMessageBox", "tkinter.messagebox"),
158
    MovedModule("tkinter_tksimpledialog", "tkSimpleDialog",
159
                "tkinter.simpledialog"),
160
    MovedModule("urllib_robotparser", "robotparser", "urllib.robotparser"),
161
    MovedModule("winreg", "_winreg"),
162
]
163
for attr in _moved_attributes:
164
    setattr(_MovedItems, attr.name, attr)
165
del attr
166
167
moves = sys.modules["django.utils.six.moves"] = _MovedItems("moves")
168
169
170
def add_move(move):
171
    """Add an item to six.moves."""
172
    setattr(_MovedItems, move.name, move)
173
174
175
def remove_move(name):
176
    """Remove item from six.moves."""
177
    try:
178
        delattr(_MovedItems, name)
179
    except AttributeError:
180
        try:
181
            del moves.__dict__[name]
182
        except KeyError:
183
            raise AttributeError("no such move, %r" % (name,))
184
185
186
if PY3:
187
    _meth_func = "__func__"
188
    _meth_self = "__self__"
189
190
    _func_code = "__code__"
191
    _func_defaults = "__defaults__"
192
193
    _iterkeys = "keys"
194
    _itervalues = "values"
195
    _iteritems = "items"
196
else:
197
    _meth_func = "im_func"
198
    _meth_self = "im_self"
199
200
    _func_code = "func_code"
201
    _func_defaults = "func_defaults"
202
203
    _iterkeys = "iterkeys"
204
    _itervalues = "itervalues"
205
    _iteritems = "iteritems"
206
207
208
try:
209
    advance_iterator = next
210
except NameError:
211
    def advance_iterator(it):
212
        return it.next()
213
next = advance_iterator
214
215
216
if PY3:
217
    def get_unbound_function(unbound):
218
        return unbound
219
220
    Iterator = object
221
222
    def callable(obj):
223
        return any("__call__" in klass.__dict__ for klass in type(obj).__mro__)
224
else:
225
    def get_unbound_function(unbound):
226
        return unbound.im_func
227
228
    class Iterator(object):
229
230
        def next(self):
231
            return type(self).__next__(self)
232
233
    callable = callable
234
_add_doc(get_unbound_function,
235
         """Get the function out of a possibly unbound function""")
236
237
238
get_method_function = operator.attrgetter(_meth_func)
239
get_method_self = operator.attrgetter(_meth_self)
240
get_function_code = operator.attrgetter(_func_code)
241
get_function_defaults = operator.attrgetter(_func_defaults)
242
243
244
def iterkeys(d):
245
    """Return an iterator over the keys of a dictionary."""
246
    return iter(getattr(d, _iterkeys)())
247
248
def itervalues(d):
249
    """Return an iterator over the values of a dictionary."""
250
    return iter(getattr(d, _itervalues)())
251
252
def iteritems(d):
253
    """Return an iterator over the (key, value) pairs of a dictionary."""
254
    return iter(getattr(d, _iteritems)())
255
256
257
if PY3:
258
    def b(s):
259
        return s.encode("latin-1")
260
    def u(s):
261
        return s
262
    if sys.version_info[1] <= 1:
263
        def int2byte(i):
264
            return bytes((i,))
265
    else:
266
        # This is about 2x faster than the implementation above on 3.2+
267
        int2byte = operator.methodcaller("to_bytes", 1, "big")
268
    import io
269
    StringIO = io.StringIO
270
    BytesIO = io.BytesIO
271
else:
272
    def b(s):
273
        return s
274
    def u(s):
275
        return unicode(s, "unicode_escape")
276
    int2byte = chr
277
    import StringIO
278
    StringIO = BytesIO = StringIO.StringIO
279
_add_doc(b, """Byte literal""")
280
_add_doc(u, """Text literal""")
281
282
283
if PY3:
284
    import builtins
285
    exec_ = getattr(builtins, "exec")
286
287
288
    def reraise(tp, value, tb=None):
289
        if value.__traceback__ is not tb:
290
            raise value.with_traceback(tb)
291
        raise value
292
293
294
    print_ = getattr(builtins, "print")
295
    del builtins
296
297
else:
298
    def exec_(code, globs=None, locs=None):
299
        """Execute code in a namespace."""
300
        if globs is None:
301
            frame = sys._getframe(1)
302
            globs = frame.f_globals
303
            if locs is None:
304
                locs = frame.f_locals
305
            del frame
306
        elif locs is None:
307
            locs = globs
308
        exec("""exec code in globs, locs""")
309
310
311
    exec_("""def reraise(tp, value, tb=None):
312
    raise tp, value, tb
313
""")
314
315
316
    def print_(*args, **kwargs):
317
        """The new-style print function."""
318
        fp = kwargs.pop("file", sys.stdout)
319
        if fp is None:
320
            return
321
        def write(data):
322
            if not isinstance(data, basestring):
323
                data = str(data)
324
            fp.write(data)
325
        want_unicode = False
326
        sep = kwargs.pop("sep", None)
327
        if sep is not None:
328
            if isinstance(sep, unicode):
329
                want_unicode = True
330
            elif not isinstance(sep, str):
331
                raise TypeError("sep must be None or a string")
332
        end = kwargs.pop("end", None)
333
        if end is not None:
334
            if isinstance(end, unicode):
335
                want_unicode = True
336
            elif not isinstance(end, str):
337
                raise TypeError("end must be None or a string")
338
        if kwargs:
339
            raise TypeError("invalid keyword arguments to print()")
340
        if not want_unicode:
341
            for arg in args:
342
                if isinstance(arg, unicode):
343
                    want_unicode = True
344
                    break
345
        if want_unicode:
346
            newline = unicode("\n")
347
            space = unicode(" ")
348
        else:
349
            newline = "\n"
350
            space = " "
351
        if sep is None:
352
            sep = space
353
        if end is None:
354
            end = newline
355
        for i, arg in enumerate(args):
356
            if i:
357
                write(sep)
358
            write(arg)
359
        write(end)
360
361
_add_doc(reraise, """Reraise an exception.""")
362
363
364
def with_metaclass(meta, base=object):
365
    """Create a base class with a metaclass."""
366
    return meta("NewBase", (base,), {})
367
368
369
### Additional customizations for Django ###
370
371
if PY3:
372
    _iterlists = "lists"
373
else:
374
    _iterlists = "iterlists"
375
376
def iterlists(d):
377
    """Return an iterator over the values of a MultiValueDict."""
378
    return getattr(d, _iterlists)()
379
380
381
add_move(MovedModule("_dummy_thread", "dummy_thread"))
382
add_move(MovedModule("_thread", "thread"))