Scott Stafford
Scott Stafford

Reputation: 44818

Migrate to GeoDjango Points from longitude/latitude?

Using the Django ORM, Postgres/PostGIS, and Django migrations, how do I convert my existing longitude and latitude float fields into a single GeoDjango Point field?

I was looking for something like Location.objects.update(point=(F('longitude'), F('latitude'))).

Upvotes: 4

Views: 3646

Answers (2)

bryan60
bryan60

Reputation: 29345

assuming you have an object with a PointField like

from django.contrib.gis.db import models

class Location(models.Model):
    longitude = models.FloatField()
    latitude = models.FloatField()
    point = models.PointField(geography=True, default='POINT(0.0 0.0)') #or similar

you could just do:

from django.contrib.gis.geos import Point

for l in Location.objects.all():
    l.point = Point(x=l.longitude, y=l.latitude, srid=4326)
    l.save()

or this single statement should work if you really want a single update (untested though):

Location.objects.all().update(point=Point(x=F('longitude'), y=F('latitude'), srid=4326))

NOTE: though I've used GeoDjango and postgis quite a bit, I'm by no means an expert in it. I don't know what the PointField does under the hood... if it's creating a relationship then it will not work in a single statement as Django doesn't allow updating across tables in update statements, you must loop over, if it's just formatting the data then it should work fine... I did a little research and it seems like the srid is the only relationship, so this should be fine because creating static relationships IS fine in an update statement.

drawing from the answer you posted above, you would simply write that as a function (named set_points for instance) in your migration file and then add this in the operations section of your migration to run it:

migrations.RunPython(set_points),

migration writing reference:

https://docs.djangoproject.com/en/2.0/howto/writing-migrations/

Upvotes: 8

Scott Stafford
Scott Stafford

Reputation: 44818

I think I found a solution at https://stackoverflow.com/a/37487182/237091. Will still prefer a solution that doesn't drop to SQL.

Upvotes: 0

Related Questions