diff options
| author | 2011-04-13 18:03:06 -0400 | |
|---|---|---|
| committer | 2011-04-13 18:03:06 -0400 | |
| commit | bb60e50be17a57842d525498ad5125d25aa5b93f (patch) | |
| tree | 30d6f8212f81c8f74c5770d68383cb7cb25a34b1 | |
| parent | basic readme (diff) | |
| download | python-github3-bb60e50be17a57842d525498ad5125d25aa5b93f.tar.xz python-github3-bb60e50be17a57842d525498ad5125d25aa5b93f.zip | |
vendorization!
| -rw-r--r-- | NOTICE | 64 | ||||
| -rw-r--r-- | github3/packages/__init__.py | 0 | ||||
| -rw-r--r-- | github3/packages/anyjson.py | 117 | ||||
| -rw-r--r-- | github3/packages/ordereddict.py | 127 | 
4 files changed, 308 insertions, 0 deletions
| @@ -0,0 +1,64 @@ +python-github3 includes some vendorized python libraries: ordereddict and anyjson. + + +OrderedDict License +=================== + +Copyright (c) 2009 Raymond Hettinger + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation files +(the "Software"), to deal in the Software without restriction, +including without limitation the rights to use, copy, modify, merge, +publish, distribute, sublicense, and/or sell copies of the Software, +and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +    The above copyright notice and this permission notice shall be +    included in all copies or substantial portions of the Software. + +    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +    EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +    OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +    NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +    HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +    WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +    FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +    OTHER DEALINGS IN THE SOFTWARE. + + + +AnyJSON License +================== + +This software is licensed under the ``New BSD License``: + +Copyright (c) 2009, by the authors +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +    * Redistributions of source code must retain the above copyright notice, +      this list of conditions and the following disclaimer. +    * Redistributions in binary form must reproduce the above copyright +      notice, this list of conditions and the following disclaimer in the +      documentation and/or other materials provided with the distribution. + +Neither the name of the authors nor the names of its contributors may be used +to endorse or promote products derived from this software without specific +prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, +THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS +BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +POSSIBILITY OF SUCH DAMAGE. + + diff --git a/github3/packages/__init__.py b/github3/packages/__init__.py new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/github3/packages/__init__.py diff --git a/github3/packages/anyjson.py b/github3/packages/anyjson.py new file mode 100644 index 0000000..a7d1a5f --- /dev/null +++ b/github3/packages/anyjson.py @@ -0,0 +1,117 @@ +""" +Wraps the best available JSON implementation available in a common interface +""" + +__version__ = "0.2.0" +__author__ = "Rune Halvorsen <runefh@gmail.com>" +__homepage__ = "http://bitbucket.org/runeh/anyjson/" +__docformat__ = "restructuredtext" + +""" + +.. function:: serialize(obj) + +    Serialize the object to JSON. + +.. function:: deserialize(str) + +    Deserialize JSON-encoded object to a Python object. + +.. function:: force_implementation(name) + +    Load a specific json module. This is useful for testing and not much else + +.. attribute:: implementation + +    The json implementation object. This is probably not useful to you, +    except to get the name of the implementation in use. The name is +    available through `implementation.name`. +""" + +import sys + +implementation = None + +""" +.. data:: _modules + +    List of known json modules, and the names of their serialize/unserialize +    methods, as well as the exception they throw. Exception can be either +    an exception class or a string. +""" +_modules = [("cjson", "encode", "EncodeError", "decode", "DecodeError"), +            ("jsonlib2", "write", "WriteError", "read", "ReadError"), +            ("jsonlib", "write", "WriteError", "read", "ReadError"), +            ("simplejson", "dumps", TypeError, "loads", ValueError), +            ("json", "dumps", TypeError, "loads", ValueError), +            ("django.utils.simplejson", "dumps", TypeError, "loads", +             ValueError)] +_fields = ("modname", "encoder", "encerror", "decoder", "decerror") + + +class _JsonImplementation(object): +    """Incapsulates a JSON implementation""" + +    def __init__(self, modspec): +        modinfo = dict(list(zip(_fields, modspec))) + +        # No try block. We want importerror to end up at caller +        module = self._attempt_load(modinfo["modname"]) + +        self.implementation = modinfo["modname"] +        self._encode = getattr(module, modinfo["encoder"]) +        self._decode = getattr(module, modinfo["decoder"]) +        self._encode_error = modinfo["encerror"] +        self._decode_error = modinfo["decerror"] + +        if isinstance(modinfo["encerror"], str): +            self._encode_error = getattr(module, modinfo["encerror"]) +        if isinstance(modinfo["decerror"], str): +            self._decode_error = getattr(module, modinfo["decerror"]) + +        self.name = modinfo["modname"] + +    def _attempt_load(self, modname): +        """Attempt to load module name modname, returning it on success, +        throwing ImportError if module couldn't be imported""" +        __import__(modname) +        return sys.modules[modname] + +    def serialize(self, data): +        """Serialize the datastructure to json. Returns a string. Raises +        TypeError if the object could not be serialized.""" +        try: +            return self._encode(data) +        except self._encode_error as exc: +            raise TypeError(*exc.args) + +    def deserialize(self, s): +        """deserialize the string to python data types. Raises +        ValueError if the string vould not be parsed.""" +        try: +            return self._decode(s) +        except self._decode_error as exc: +            raise ValueError(*exc.args) + + +def force_implementation(modname): +    """Forces anyjson to use a specific json module if it's available""" +    global implementation +    for name, spec in [(e[0], e) for e in _modules]: +        if name == modname: +            implementation = _JsonImplementation(spec) +            return +    raise ImportError("No module named: %s" % modname) + + +for modspec in _modules: +    try: +        implementation = _JsonImplementation(modspec) +        break +    except ImportError: +        pass +else: +    raise ImportError("No supported JSON module found") + +serialize = lambda value: implementation.serialize(value) +deserialize = lambda value: implementation.deserialize(value) diff --git a/github3/packages/ordereddict.py b/github3/packages/ordereddict.py new file mode 100644 index 0000000..a5b896d --- /dev/null +++ b/github3/packages/ordereddict.py @@ -0,0 +1,127 @@ +# Copyright (c) 2009 Raymond Hettinger +# +# Permission is hereby granted, free of charge, to any person +# obtaining a copy of this software and associated documentation files +# (the "Software"), to deal in the Software without restriction, +# including without limitation the rights to use, copy, modify, merge, +# publish, distribute, sublicense, and/or sell copies of the Software, +# and to permit persons to whom the Software is furnished to do so, +# subject to the following conditions: +# +#     The above copyright notice and this permission notice shall be +#     included in all copies or substantial portions of the Software. +# +#     THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +#     EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +#     OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +#     NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +#     HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +#     WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +#     FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +#     OTHER DEALINGS IN THE SOFTWARE. + +from UserDict import DictMixin + +class OrderedDict(dict, DictMixin): + +    def __init__(self, *args, **kwds): +        if len(args) > 1: +            raise TypeError('expected at most 1 arguments, got %d' % len(args)) +        try: +            self.__end +        except AttributeError: +            self.clear() +        self.update(*args, **kwds) + +    def clear(self): +        self.__end = end = [] +        end += [None, end, end]         # sentinel node for doubly linked list +        self.__map = {}                 # key --> [key, prev, next] +        dict.clear(self) + +    def __setitem__(self, key, value): +        if key not in self: +            end = self.__end +            curr = end[1] +            curr[2] = end[1] = self.__map[key] = [key, curr, end] +        dict.__setitem__(self, key, value) + +    def __delitem__(self, key): +        dict.__delitem__(self, key) +        key, prev, next = self.__map.pop(key) +        prev[2] = next +        next[1] = prev + +    def __iter__(self): +        end = self.__end +        curr = end[2] +        while curr is not end: +            yield curr[0] +            curr = curr[2] + +    def __reversed__(self): +        end = self.__end +        curr = end[1] +        while curr is not end: +            yield curr[0] +            curr = curr[1] + +    def popitem(self, last=True): +        if not self: +            raise KeyError('dictionary is empty') +        if last: +            key = next(reversed(self)) +        else: +            key = next(iter(self)) +        value = self.pop(key) +        return key, value + +    def __reduce__(self): +        items = [[k, self[k]] for k in self] +        tmp = self.__map, self.__end +        del self.__map, self.__end +        inst_dict = vars(self).copy() +        self.__map, self.__end = tmp +        if inst_dict: +            return (self.__class__, (items,), inst_dict) +        return self.__class__, (items,) + +    def keys(self): +        return list(self) + +    setdefault = DictMixin.setdefault +    update = DictMixin.update +    pop = DictMixin.pop +    values = DictMixin.values +    items = DictMixin.items +    iterkeys = DictMixin.iterkeys +    itervalues = DictMixin.itervalues +    iteritems = DictMixin.iteritems + +    def __repr__(self): +        if not self: +            return '%s()' % (self.__class__.__name__,) +        return '%s(%r)' % (self.__class__.__name__, list(self.items())) + +    def copy(self): +        return self.__class__(self) + +    @classmethod +    def fromkeys(cls, iterable, value=None): +        d = cls() +        for key in iterable: +            d[key] = value +        return d + +    def __eq__(self, other): +        if isinstance(other, OrderedDict): +            if len(self) != len(other): +                return False +            for p, q in  zip(list(self.items()), list(other.items())): +                if p != q: +                    return False +            return True +        return dict.__eq__(self, other) + +    def __ne__(self, other): +        return not self == other | 
