5

I'm new with Flask, and I'm having some problem trying to return an object which contains another object instance as field, like the follows:

class Park(object):
    park_id = 0
    address = ""
    services = []
    position = None

    def __init__(self, park_id, address, services, latitude, longitude):
        self.park_id = park_id
        self.address = address
        self.services = services
        self.position = Point(latitude, longitude)

where the Point class is simply the follow:

class Point(object):
    latitude = None
    longitude = None

    def __init__(self, latitude, longitude):
        self.latitude = latitude
        self.longitude = longitude

when I try to return a Park instance

@app.route('/')
def test():
    park = Park(....)
    return jsonify(park])

I obtain this error: TypeError: Object of type 'Park' is not JSON serializable.

Mattia Campana
  • 509
  • 2
  • 6
  • 15
  • 1
    I think you first have to think how you will convert a `Point` instance to a JSON object, like `{"latitude": 123.4, "longitude": 567.8}`? – Willem Van Onsem Jan 29 '18 at 21:59

2 Answers2

0

Python's default json module doesn't serialize complex objects by default.

You can use a library like jsonpickle; or simply implement a to_dict method in your Park class that transforms your objects into a dictionary, so you can call jsonify(park.to_dict()).

0

I think Willem is right, in that you first need to convert your class into a JSON like object, such as a dict. If you want to just convert the attributes of your Point class, you can use either __dict__ special attribute or the vars() builtin.

Below is a quick function to convert using vars. Note that I've hard coded it to check for the Point class, but this could easily be extended to be more generic. This also only checks one level deep, but could be written to recursive as deep as needed. You could also convert this function into a method of the Park class itself to keep everything together / more object orientated.

def convert_park_to_dict(park):
    park_dict = {}
    for attr in vars(park):
        attr_value = getattr(park, attr)
        if isinstance(attr_value, Point):
            point_dict = vars(attr_value)
            park_dict[attr] = point_dict
        else:
            park_dict[attr] = attr_value
    return park_dict

@app.route('/')
def test():
    park = Park(1, 'my_house', ['swings', 'shop'], 50, 60)
    park_dict = convert_park_to_dict(park)
    return jsonify(park_dict)

):

Read a bit more about __dict__ here.

North Laine
  • 384
  • 2
  • 14