sql: add geolocation to views (#14784)
This commit is contained in:
parent
83826dd478
commit
e385356263
|
@ -191,6 +191,10 @@ def test_sql_geoloc():
|
|||
data_class = test_formdef.data_class(mode='sql')
|
||||
formdata = data_class()
|
||||
formdata.data = {}
|
||||
formdata.store() # NULL geolocation
|
||||
formdata2 = data_class.get(formdata.id)
|
||||
assert not formdata2.geolocations
|
||||
|
||||
formdata.geolocations = {'base': {'lat': 12, 'lon': 21}}
|
||||
formdata.store()
|
||||
|
||||
|
@ -1186,6 +1190,49 @@ def test_select_any_formdata():
|
|||
objects2 = sql.AnyFormData.select(order_by='receipt_time', limit=10, offset=20)
|
||||
assert [(x.formdef_id, x.id) for x in objects2] == [(x.formdef_id, x.id) for x in objects][20:30]
|
||||
|
||||
@postgresql
|
||||
def test_geoloc_in_global_view():
|
||||
drop_formdef_tables()
|
||||
conn, cur = sql.get_connection_and_cursor()
|
||||
|
||||
now = datetime.datetime.now()
|
||||
|
||||
formdef = FormDef()
|
||||
formdef.name = 'test no geoloc'
|
||||
formdef.fields = []
|
||||
formdef.store()
|
||||
|
||||
formdef2 = FormDef()
|
||||
formdef2.name = 'test with geoloc'
|
||||
formdef2.fields = []
|
||||
formdef2.geolocations = {'base': 'Plop'}
|
||||
formdef2.store()
|
||||
|
||||
data_class = formdef.data_class(mode='sql')
|
||||
formdata = data_class()
|
||||
formdata.just_created()
|
||||
formdata.store()
|
||||
|
||||
data_class = formdef2.data_class(mode='sql')
|
||||
formdata = data_class()
|
||||
formdata.just_created()
|
||||
formdata.geolocations = {'base': {'lat': 12, 'lon': 21}}
|
||||
formdata.store()
|
||||
|
||||
# test generic select
|
||||
objects = sql.AnyFormData.select()
|
||||
assert len(objects) == 2
|
||||
|
||||
# test clauses
|
||||
objects2 = sql.AnyFormData.select([st.Null('geoloc_base_x')])
|
||||
assert len(objects2) == 1
|
||||
assert not objects2[0].geolocations
|
||||
|
||||
objects2 = sql.AnyFormData.select([st.NotNull('geoloc_base_x')])
|
||||
assert len(objects2) == 1
|
||||
assert int(objects2[0].geolocations['base']['lat']) == formdata.geolocations['base']['lat']
|
||||
assert int(objects2[0].geolocations['base']['lon']) == formdata.geolocations['base']['lon']
|
||||
|
||||
@postgresql
|
||||
def test_actions_roles():
|
||||
drop_formdef_tables()
|
||||
|
|
22
wcs/sql.py
22
wcs/sql.py
|
@ -669,6 +669,16 @@ def do_views(formdef, conn, cur, rebuild_global_views=True):
|
|||
view_fields.append(('actions_roles_array', 'actions_roles_array'))
|
||||
view_fields.append(('fts', 'fts'))
|
||||
|
||||
if formdef.geolocations and 'base' in formdef.geolocations:
|
||||
# default geolocation is in the 'base' key; we have to unstructure the
|
||||
# field is the POINT type of postgresql cannot be used directly as it
|
||||
# doesn't have an equality operator.
|
||||
view_fields.append(('geoloc_base[0]', 'geoloc_base_x'))
|
||||
view_fields.append(('geoloc_base[1]', 'geoloc_base_y'))
|
||||
else:
|
||||
view_fields.append(('NULL::real', 'geoloc_base_x'))
|
||||
view_fields.append(('NULL::real', 'geoloc_base_y'))
|
||||
|
||||
fields_list = ', '.join(['%s AS %s' % x for x in view_fields])
|
||||
|
||||
cur.execute('''CREATE VIEW %s AS SELECT %s FROM %s''' % (
|
||||
|
@ -727,6 +737,8 @@ def do_global_views(conn, cur):
|
|||
common_fields.append(('formdef_name', 'formdef_name'))
|
||||
common_fields.append(('user_name', 'user_name'))
|
||||
common_fields.append(('criticality_level', 'criticality_level'))
|
||||
common_fields.append(('geoloc_base_x', 'geoloc_base_x'))
|
||||
common_fields.append(('geoloc_base_y', 'geoloc_base_y'))
|
||||
|
||||
union = ' UNION '.join(['''SELECT %s FROM %s''' % (
|
||||
', '.join([y[1] for y in common_fields]), x) for x in view_names])
|
||||
|
@ -1680,6 +1692,8 @@ class AnyFormData(SqlMixin):
|
|||
common_fields = get_view_fields(fake_formdef)
|
||||
cls.__table_static_fields = [(x[1], x[0]) for x in common_fields]
|
||||
cls.__table_static_fields.append(('criticality_level', 'criticality_level'))
|
||||
cls.__table_static_fields.append(('geoloc_base_x', 'geoloc_base_x'))
|
||||
cls.__table_static_fields.append(('geoloc_base_y', 'geoloc_base_y'))
|
||||
return cls.__table_static_fields
|
||||
|
||||
@classmethod
|
||||
|
@ -1704,6 +1718,9 @@ class AnyFormData(SqlMixin):
|
|||
# range (see [CRITICALITY_1])
|
||||
levels = len(formdef.workflow.criticality_levels or [0])
|
||||
o.criticality_level = levels + o.criticality_level
|
||||
# convert back unstructured geolocation to the 'native' formdata format.
|
||||
if o.geoloc_base_x is not None:
|
||||
o.geolocations = {'base': {'lon': o.geoloc_base_x, 'lat': o.geoloc_base_y}}
|
||||
return o
|
||||
|
||||
|
||||
|
@ -1834,7 +1851,7 @@ def get_yearly_totals(period_start=None, period_end=None, criterias=None):
|
|||
return result
|
||||
|
||||
|
||||
SQL_LEVEL = 18
|
||||
SQL_LEVEL = 19
|
||||
|
||||
def migrate_global_views(conn, cur):
|
||||
cur.execute('''SELECT COUNT(*) FROM information_schema.tables
|
||||
|
@ -1868,7 +1885,7 @@ def migrate():
|
|||
raise RuntimeError()
|
||||
if sql_level < 1: # 1: introduction of tracking_code table
|
||||
do_tracking_code_table()
|
||||
if sql_level < 17:
|
||||
if sql_level < 19:
|
||||
# 2: introduction of formdef_id in views
|
||||
# 5: add concerned_roles_array, is_at_endpoint and fts to views
|
||||
# 7: add backoffice_submission to tables
|
||||
|
@ -1879,6 +1896,7 @@ def migrate():
|
|||
# 13: add backoffice_submission to views
|
||||
# 14: add criticality_level to tables & views
|
||||
# 15: add geolocation to formdata
|
||||
# 19: add geolocation to views
|
||||
migrate_views(conn, cur)
|
||||
if sql_level < 16:
|
||||
# 3: introduction of _structured for user fields
|
||||
|
|
Loading…
Reference in New Issue