How to convert JSON to Python objects correctly?

I want to parse the JSON that I get from a web service into an object structure. Therefore, I implement a subclass json.JSONDecoderusing the method object_hook. I have not yet found a good way to choose the right class for the data. For classes that have the same attributes, it seems impossible to determine the correct one, since this requires knowing the key. Let's look at an example:

I have the following classes:

class Post:
    def __init__(self, title, user=None, group=None):
        self.title = title
        self.user = user
        self.group = group

class Group:
    def __init__(self, name):
        self.name = name

class User:
    def __init__(self, name):
        self.name = name

Note that classes Groupand Userhave the same attributes. Now my JSONDecoder looks like this:

 class JSONDecoder(json.JSONDecoder):

    def __init__(self, encoding="UTF-8"):
        json.JSONDecoder.__init__(self, object_hook=self.dict_to_object)

    def dict_to_object(self, d):

        if "posts" in d:
            return d["posts"]
        if "title" in d:
            if "user" in d:
               return Post(d["title"], user=d["user"])
            if "group" in d:
               return Post(d["title"], group=d["group"])
        if "name" in d:
            # How to decide if User(d["name"]) or Group(d["name")?
            return None
        return None

When he sees a dictionary containing the key "name", he cannot decide whether to create an object Groupor User(therefore, I am returning Nonefor the moment).

JSON, , :

s = """
{ "posts" : [ 
    {"title" : "Hello World", "user" : {"name" : "uli"}},
    {"title" : "Hello Group", "group" : {"name" : "Workgroup"}}
  ]
}
"""

Post, , .

? if -Statements dict_to_object ? ( - JSON.) , ? ( .)

+4
3

, IME JSON, dict , object_hook , , , .. //. ( @BrenBam)

classmethod make_xyz,

object_hook , . , , . - , , 100% , ( , , ad-hoc- -), , JSON ..

: , {"name" : "xyz"}, , JSON , , "user"/"group" :. class make_group(), make_user(). , - , object_hook. IME, .

0

- User Group , . , Post:

def dict_to_object(self, d):
    if "posts" in d:
        return d["posts"]
    if "title" in d:
        if "user" in d:
           d["user"] = User(d["user"]["name"])
        if "group" in d:
           d["group"] = Group(d["group"]["name"])
        return Post(d["title"],
                    d.get("user", None),
                    d.get("group", None))
    return d
0

, , , json.JSONDecoder:

class JSONDecoder:

    def decode_json(self, js):
        posts = []
        if "posts" in js:
            for p in js["posts"]:
                if "user" in p:
                    posts.append(Post(p["title"], user=self._decode_user(p["user"])))
                if "group" in p:
                    posts.append(Post(p["title"], group=self._decode_group(p["group"])))
        return posts

    def _decode_user(self, js):
        return User(js["name"])

    def _decode_group(self, js):
        return Group(js["name"])

JSONDecoder().decode_json(json.loads(s)). BW: Bitbucket.

0

All Articles