umap-project 3.3.6__py3-none-any.whl → 3.4.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (239) hide show
  1. umap/__init__.py +1 -1
  2. umap/context_processors.py +4 -1
  3. umap/locale/cs_CZ/LC_MESSAGES/django.mo +0 -0
  4. umap/locale/cs_CZ/LC_MESSAGES/django.po +43 -33
  5. umap/locale/da/LC_MESSAGES/django.mo +0 -0
  6. umap/locale/da/LC_MESSAGES/django.po +43 -33
  7. umap/locale/de/LC_MESSAGES/django.mo +0 -0
  8. umap/locale/de/LC_MESSAGES/django.po +35 -29
  9. umap/locale/el/LC_MESSAGES/django.mo +0 -0
  10. umap/locale/el/LC_MESSAGES/django.po +35 -29
  11. umap/locale/en/LC_MESSAGES/django.po +47 -41
  12. umap/locale/es/LC_MESSAGES/django.mo +0 -0
  13. umap/locale/es/LC_MESSAGES/django.po +43 -33
  14. umap/locale/et/LC_MESSAGES/django.mo +0 -0
  15. umap/locale/et/LC_MESSAGES/django.po +58 -54
  16. umap/locale/eu/LC_MESSAGES/django.mo +0 -0
  17. umap/locale/eu/LC_MESSAGES/django.po +43 -33
  18. umap/locale/fa_IR/LC_MESSAGES/django.mo +0 -0
  19. umap/locale/fa_IR/LC_MESSAGES/django.po +43 -33
  20. umap/locale/fr/LC_MESSAGES/django.mo +0 -0
  21. umap/locale/fr/LC_MESSAGES/django.po +36 -30
  22. umap/locale/gl/LC_MESSAGES/django.mo +0 -0
  23. umap/locale/gl/LC_MESSAGES/django.po +43 -33
  24. umap/locale/hu/LC_MESSAGES/django.mo +0 -0
  25. umap/locale/hu/LC_MESSAGES/django.po +35 -29
  26. umap/locale/is/LC_MESSAGES/django.mo +0 -0
  27. umap/locale/is/LC_MESSAGES/django.po +43 -33
  28. umap/locale/it/LC_MESSAGES/django.mo +0 -0
  29. umap/locale/it/LC_MESSAGES/django.po +43 -33
  30. umap/locale/nl/LC_MESSAGES/django.mo +0 -0
  31. umap/locale/nl/LC_MESSAGES/django.po +35 -29
  32. umap/locale/pl/LC_MESSAGES/django.mo +0 -0
  33. umap/locale/pl/LC_MESSAGES/django.po +114 -103
  34. umap/locale/pt/LC_MESSAGES/django.mo +0 -0
  35. umap/locale/pt/LC_MESSAGES/django.po +43 -33
  36. umap/locale/th_TH/LC_MESSAGES/django.mo +0 -0
  37. umap/locale/th_TH/LC_MESSAGES/django.po +310 -109
  38. umap/locale/zh_TW/LC_MESSAGES/django.mo +0 -0
  39. umap/locale/zh_TW/LC_MESSAGES/django.po +80 -70
  40. umap/management/commands/switch_user.py +2 -2
  41. umap/migrations/0018_datalayer_uuid.py +1 -1
  42. umap/models.py +7 -3
  43. umap/settings/local.py.sample +1 -1
  44. umap/static/umap/base.css +89 -32
  45. umap/static/umap/content.css +129 -33
  46. umap/static/umap/css/bar.css +82 -20
  47. umap/static/umap/css/browser.css +163 -0
  48. umap/static/umap/css/contextmenu.css +15 -0
  49. umap/static/umap/css/dialog.css +36 -16
  50. umap/static/umap/css/form.css +123 -33
  51. umap/static/umap/css/icon.css +46 -3
  52. umap/static/umap/css/panel.css +7 -3
  53. umap/static/umap/css/popup.css +34 -8
  54. umap/static/umap/css/tooltip.css +8 -4
  55. umap/static/umap/img/16-white.svg +26 -8
  56. umap/static/umap/img/16.svg +1 -1
  57. umap/static/umap/img/source/16-white.svg +36 -18
  58. umap/static/umap/img/source/16.svg +1 -1
  59. umap/static/umap/js/components/alerts/alert.css +69 -31
  60. umap/static/umap/js/components/alerts/alert.js +20 -2
  61. umap/static/umap/js/components/base.js +1 -1
  62. umap/static/umap/js/modules/browser.js +69 -61
  63. umap/static/umap/js/modules/caption.js +10 -7
  64. umap/static/umap/js/modules/data/features.js +85 -60
  65. umap/static/umap/js/modules/data/fields.js +446 -0
  66. umap/static/umap/js/modules/data/layer.js +78 -184
  67. umap/static/umap/js/modules/domutils.js +109 -0
  68. umap/static/umap/js/modules/filters.js +780 -0
  69. umap/static/umap/js/modules/form/builder.js +8 -5
  70. umap/static/umap/js/modules/form/fields.js +111 -221
  71. umap/static/umap/js/modules/formatter.js +24 -1
  72. umap/static/umap/js/modules/help.js +4 -3
  73. umap/static/umap/js/modules/i18n.js +1 -1
  74. umap/static/umap/js/modules/importer.js +1 -1
  75. umap/static/umap/js/modules/importers/opendata.js +15 -0
  76. umap/static/umap/js/modules/importers/openrouteservice.js +6 -1
  77. umap/static/umap/js/modules/managers.js +2 -2
  78. umap/static/umap/js/modules/permissions.js +39 -31
  79. umap/static/umap/js/modules/rendering/controls.js +11 -9
  80. umap/static/umap/js/modules/rendering/icon.js +3 -8
  81. umap/static/umap/js/modules/rendering/layers/base.js +1 -1
  82. umap/static/umap/js/modules/rendering/layers/classified.js +18 -11
  83. umap/static/umap/js/modules/rendering/layers/cluster.js +5 -3
  84. umap/static/umap/js/modules/rendering/layers/heat.js +27 -21
  85. umap/static/umap/js/modules/rendering/template.js +50 -23
  86. umap/static/umap/js/modules/rendering/ui.js +29 -23
  87. umap/static/umap/js/modules/rules.js +38 -44
  88. umap/static/umap/js/modules/schema.js +3 -6
  89. umap/static/umap/js/modules/share.js +5 -4
  90. umap/static/umap/js/modules/tableeditor.js +50 -38
  91. umap/static/umap/js/modules/templates.js +2 -3
  92. umap/static/umap/js/modules/ui/bar.js +55 -23
  93. umap/static/umap/js/modules/ui/dialog.js +38 -27
  94. umap/static/umap/js/modules/ui/panel.js +23 -8
  95. umap/static/umap/js/modules/ui/tooltip.js +6 -5
  96. umap/static/umap/js/modules/umap.js +151 -56
  97. umap/static/umap/js/modules/utils.js +24 -2
  98. umap/static/umap/js/umap.core.js +1 -110
  99. umap/static/umap/locale/am_ET.js +52 -17
  100. umap/static/umap/locale/am_ET.json +52 -17
  101. umap/static/umap/locale/ar.js +52 -17
  102. umap/static/umap/locale/ar.json +52 -17
  103. umap/static/umap/locale/ast.js +52 -17
  104. umap/static/umap/locale/ast.json +52 -17
  105. umap/static/umap/locale/bg.js +52 -17
  106. umap/static/umap/locale/bg.json +52 -17
  107. umap/static/umap/locale/br.js +48 -22
  108. umap/static/umap/locale/br.json +48 -22
  109. umap/static/umap/locale/ca.js +52 -17
  110. umap/static/umap/locale/ca.json +52 -17
  111. umap/static/umap/locale/cs_CZ.js +52 -17
  112. umap/static/umap/locale/cs_CZ.json +52 -17
  113. umap/static/umap/locale/da.js +54 -17
  114. umap/static/umap/locale/da.json +54 -17
  115. umap/static/umap/locale/de.js +51 -16
  116. umap/static/umap/locale/de.json +51 -16
  117. umap/static/umap/locale/el.js +52 -17
  118. umap/static/umap/locale/el.json +52 -17
  119. umap/static/umap/locale/en.js +53 -16
  120. umap/static/umap/locale/en.json +53 -16
  121. umap/static/umap/locale/en_US.json +52 -17
  122. umap/static/umap/locale/es.js +54 -17
  123. umap/static/umap/locale/es.json +54 -17
  124. umap/static/umap/locale/et.js +91 -56
  125. umap/static/umap/locale/et.json +91 -56
  126. umap/static/umap/locale/eu.js +84 -49
  127. umap/static/umap/locale/eu.json +84 -49
  128. umap/static/umap/locale/fa_IR.js +52 -17
  129. umap/static/umap/locale/fa_IR.json +52 -17
  130. umap/static/umap/locale/fi.js +52 -17
  131. umap/static/umap/locale/fi.json +52 -17
  132. umap/static/umap/locale/fr.js +53 -16
  133. umap/static/umap/locale/fr.json +53 -16
  134. umap/static/umap/locale/gl.js +52 -17
  135. umap/static/umap/locale/gl.json +52 -17
  136. umap/static/umap/locale/he.js +52 -17
  137. umap/static/umap/locale/he.json +52 -17
  138. umap/static/umap/locale/hr.js +52 -17
  139. umap/static/umap/locale/hr.json +52 -17
  140. umap/static/umap/locale/hu.js +59 -24
  141. umap/static/umap/locale/hu.json +59 -24
  142. umap/static/umap/locale/id.js +52 -17
  143. umap/static/umap/locale/id.json +52 -17
  144. umap/static/umap/locale/is.js +52 -17
  145. umap/static/umap/locale/is.json +52 -17
  146. umap/static/umap/locale/it.js +52 -17
  147. umap/static/umap/locale/it.json +52 -17
  148. umap/static/umap/locale/ja.js +52 -17
  149. umap/static/umap/locale/ja.json +52 -17
  150. umap/static/umap/locale/ko.js +52 -17
  151. umap/static/umap/locale/ko.json +52 -17
  152. umap/static/umap/locale/lt.js +52 -17
  153. umap/static/umap/locale/lt.json +52 -17
  154. umap/static/umap/locale/ms.js +52 -17
  155. umap/static/umap/locale/ms.json +52 -17
  156. umap/static/umap/locale/nl.js +52 -17
  157. umap/static/umap/locale/nl.json +52 -17
  158. umap/static/umap/locale/no.js +52 -17
  159. umap/static/umap/locale/no.json +52 -17
  160. umap/static/umap/locale/pl.js +53 -17
  161. umap/static/umap/locale/pl.json +53 -17
  162. umap/static/umap/locale/pl_PL.json +52 -17
  163. umap/static/umap/locale/pt.js +52 -17
  164. umap/static/umap/locale/pt.json +52 -17
  165. umap/static/umap/locale/pt_BR.js +52 -17
  166. umap/static/umap/locale/pt_BR.json +52 -17
  167. umap/static/umap/locale/pt_PT.js +52 -17
  168. umap/static/umap/locale/pt_PT.json +52 -17
  169. umap/static/umap/locale/ro.js +52 -17
  170. umap/static/umap/locale/ro.json +52 -17
  171. umap/static/umap/locale/ru.js +52 -17
  172. umap/static/umap/locale/ru.json +52 -17
  173. umap/static/umap/locale/si.js +1 -1
  174. umap/static/umap/locale/si.json +1 -1
  175. umap/static/umap/locale/sk_SK.js +52 -17
  176. umap/static/umap/locale/sk_SK.json +52 -17
  177. umap/static/umap/locale/sl.js +52 -17
  178. umap/static/umap/locale/sl.json +52 -17
  179. umap/static/umap/locale/sr.js +52 -17
  180. umap/static/umap/locale/sr.json +52 -17
  181. umap/static/umap/locale/sv.js +52 -17
  182. umap/static/umap/locale/sv.json +52 -17
  183. umap/static/umap/locale/th_TH.js +52 -17
  184. umap/static/umap/locale/th_TH.json +52 -17
  185. umap/static/umap/locale/tr.js +52 -17
  186. umap/static/umap/locale/tr.json +52 -17
  187. umap/static/umap/locale/uk_UA.js +52 -17
  188. umap/static/umap/locale/uk_UA.json +52 -17
  189. umap/static/umap/locale/vi.js +52 -17
  190. umap/static/umap/locale/vi.json +52 -17
  191. umap/static/umap/locale/vi_VN.json +52 -17
  192. umap/static/umap/locale/zh.js +52 -17
  193. umap/static/umap/locale/zh.json +52 -17
  194. umap/static/umap/locale/zh_CN.json +52 -17
  195. umap/static/umap/locale/zh_TW.Big5.json +52 -17
  196. umap/static/umap/locale/zh_TW.js +52 -16
  197. umap/static/umap/locale/zh_TW.json +52 -16
  198. umap/static/umap/map.css +63 -226
  199. umap/static/umap/unittests/utils.js +18 -0
  200. umap/static/umap/vars.css +23 -5
  201. umap/templates/umap/components/alerts/alert.html +32 -29
  202. umap/templates/umap/css.html +2 -1
  203. umap/templates/umap/login_popup_end.html +18 -9
  204. umap/templates/umap/user_map_table.html +7 -2
  205. umap/tests/integration/conftest.py +10 -6
  206. umap/tests/integration/test_anonymous_owned_map.py +90 -37
  207. umap/tests/integration/test_basics.py +25 -1
  208. umap/tests/integration/test_browser.py +37 -0
  209. umap/tests/integration/test_conditional_rules.py +107 -52
  210. umap/tests/integration/test_draw_polygon.py +6 -0
  211. umap/tests/integration/test_draw_polyline.py +11 -0
  212. umap/tests/integration/test_edit_marker.py +1 -1
  213. umap/tests/integration/test_export_map.py +19 -0
  214. umap/tests/integration/test_fields.py +541 -0
  215. umap/tests/integration/test_filters.py +616 -0
  216. umap/tests/integration/test_iframe.py +1 -1
  217. umap/tests/integration/test_import.py +38 -42
  218. umap/tests/integration/test_map_preview.py +1 -1
  219. umap/tests/integration/test_picto.py +1 -1
  220. umap/tests/integration/test_popup.py +31 -0
  221. umap/tests/integration/test_remote_data.py +60 -4
  222. umap/tests/integration/test_save.py +1 -1
  223. umap/tests/integration/test_share.py +4 -4
  224. umap/tests/integration/test_tableeditor.py +31 -7
  225. umap/tests/integration/test_websocket_sync.py +71 -20
  226. umap/tests/test_dashboard.py +11 -1
  227. umap/tests/test_statics.py +2 -2
  228. umap/tests/test_utils.py +19 -2
  229. umap/tests/test_views.py +1 -1
  230. umap/urls.py +1 -0
  231. umap/utils.py +8 -1
  232. umap/views.py +5 -0
  233. {umap_project-3.3.6.dist-info → umap_project-3.4.0.dist-info}/METADATA +15 -15
  234. {umap_project-3.3.6.dist-info → umap_project-3.4.0.dist-info}/RECORD +237 -233
  235. umap/static/umap/js/modules/facets.js +0 -164
  236. umap/tests/integration/test_facets_browser.py +0 -279
  237. {umap_project-3.3.6.dist-info → umap_project-3.4.0.dist-info}/WHEEL +0 -0
  238. {umap_project-3.3.6.dist-info → umap_project-3.4.0.dist-info}/entry_points.txt +0 -0
  239. {umap_project-3.3.6.dist-info → umap_project-3.4.0.dist-info}/licenses/LICENSE +0 -0
@@ -22,9 +22,8 @@ def test_layers_list_is_updated(live_server, tilelayer, page):
22
22
  page.locator("[name=layer-id]").select_option(label="Import in a new layer")
23
23
  page.get_by_role("button", name="Manage layers").click()
24
24
  page.get_by_role("button", name="Add a layer").click()
25
- page.locator('input[name="name"]').click()
26
25
  page.locator('input[name="name"]').fill("foobar")
27
- page.wait_for_timeout(300) # Time for the input debounce.
26
+ page.wait_for_timeout(300) # Wait for the input throttling.
28
27
  page.get_by_role("button", name=f"Import data ({modifier}+I)").click()
29
28
  # Should still work
30
29
  page.locator("[name=layer-id]").select_option(label="Import in a new layer")
@@ -76,6 +75,7 @@ def test_umap_import_from_textarea(live_server, tilelayer, page, settings):
76
75
  page.goto(f"{live_server.url}/map/new/")
77
76
  page.get_by_role("button", name="Open browser").click()
78
77
  page.get_by_title("Import data").click()
78
+ page.wait_for_timeout(300) # Time for the panel animation to finish
79
79
  textarea = page.locator(".umap-import textarea")
80
80
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.umap"
81
81
  textarea.fill(path.read_text())
@@ -108,9 +108,8 @@ def test_import_geojson_from_textarea(tilelayer, live_server, page):
108
108
  expect(markers).to_have_count(0)
109
109
  expect(paths).to_have_count(0)
110
110
  expect(layers).to_have_count(0)
111
- button = page.get_by_title("Import data")
112
- expect(button).to_be_visible()
113
- button.click()
111
+ page.get_by_title("Import data").click()
112
+ page.wait_for_timeout(300) # Time for the panel animation to finish
114
113
  textarea = page.locator(".umap-import textarea")
115
114
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.json"
116
115
  textarea.fill(path.read_text())
@@ -133,9 +132,8 @@ def test_import_invalid_data(tilelayer, live_server, page):
133
132
  expect(markers).to_have_count(0)
134
133
  expect(paths).to_have_count(0)
135
134
  expect(layers).to_have_count(0)
136
- button = page.get_by_title("Import data")
137
- expect(button).to_be_visible()
138
- button.click()
135
+ page.get_by_title("Import data").click()
136
+ page.wait_for_timeout(300) # Time for the panel animation to finish
139
137
  textarea = page.locator(".umap-import textarea")
140
138
  textarea.fill("invalid data")
141
139
  for format in ["geojson", "csv", "gpx", "kml", "georss", "osm", "umap"]:
@@ -153,9 +151,8 @@ def test_import_kml_from_textarea(tilelayer, live_server, page):
153
151
  expect(markers).to_have_count(0)
154
152
  expect(paths).to_have_count(0)
155
153
  expect(layers).to_have_count(0)
156
- button = page.get_by_title("Import data")
157
- expect(button).to_be_visible()
158
- button.click()
154
+ page.get_by_title("Import data").click()
155
+ page.wait_for_timeout(300) # Time for the panel animation to finish
159
156
  textarea = page.locator(".umap-import textarea")
160
157
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.kml"
161
158
  textarea.fill(path.read_text())
@@ -177,9 +174,8 @@ def test_import_gpx_from_textarea(tilelayer, live_server, page, settings):
177
174
  expect(markers).to_have_count(0)
178
175
  expect(paths).to_have_count(0)
179
176
  expect(layers).to_have_count(0)
180
- button = page.get_by_title("Import data")
181
- expect(button).to_be_visible()
182
- button.click()
177
+ page.get_by_title("Import data").click()
178
+ page.wait_for_timeout(300) # Time for the panel animation to finish
183
179
  textarea = page.locator(".umap-import textarea")
184
180
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.gpx"
185
181
  textarea.fill(path.read_text())
@@ -234,9 +230,8 @@ def test_import_osm_from_textarea(tilelayer, live_server, page):
234
230
  markers = page.locator(".leaflet-marker-icon")
235
231
  expect(markers).to_have_count(0)
236
232
  expect(layers).to_have_count(0)
237
- button = page.get_by_title("Import data")
238
- expect(button).to_be_visible()
239
- button.click()
233
+ page.get_by_title("Import data").click()
234
+ page.wait_for_timeout(300) # Time for the panel animation to finish
240
235
  textarea = page.locator(".umap-import textarea")
241
236
  path = Path(__file__).parent.parent / "fixtures/test_upload_data_osm.json"
242
237
  textarea.fill(path.read_text())
@@ -254,9 +249,8 @@ def test_import_csv_from_textarea(tilelayer, live_server, page):
254
249
  markers = page.locator(".leaflet-marker-icon")
255
250
  expect(markers).to_have_count(0)
256
251
  expect(layers).to_have_count(0)
257
- button = page.get_by_title("Import data")
258
- expect(button).to_be_visible()
259
- button.click()
252
+ page.get_by_title("Import data").click()
253
+ page.wait_for_timeout(300) # Time for the panel animation to finish
260
254
  textarea = page.locator(".umap-import textarea")
261
255
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.csv"
262
256
  textarea.fill(path.read_text())
@@ -276,6 +270,7 @@ def test_can_import_in_existing_datalayer(live_server, datalayer, page, openmap)
276
270
  expect(layers).to_have_count(1)
277
271
  page.get_by_role("button", name="Edit").click()
278
272
  page.get_by_title("Import data").click()
273
+ page.wait_for_timeout(300) # Time for the panel animation to finish
279
274
  textarea = page.locator(".umap-import textarea")
280
275
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.csv"
281
276
  textarea.fill(path.read_text())
@@ -297,6 +292,7 @@ def test_can_replace_datalayer_data(live_server, datalayer, page, openmap):
297
292
  expect(layers).to_have_count(1)
298
293
  page.get_by_role("button", name="Edit").click()
299
294
  page.get_by_title("Import data").click()
295
+ page.wait_for_timeout(300) # Time for the panel animation to finish
300
296
  textarea = page.locator(".umap-import textarea")
301
297
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.csv"
302
298
  textarea.fill(path.read_text())
@@ -318,6 +314,7 @@ def test_can_import_in_new_datalayer(live_server, datalayer, page, openmap):
318
314
  expect(layers).to_have_count(1)
319
315
  page.get_by_role("button", name="Edit").click()
320
316
  page.get_by_title("Import data").click()
317
+ page.wait_for_timeout(300) # Time for the panel animation to finish
321
318
  textarea = page.locator(".umap-import textarea")
322
319
  path = Path(__file__).parent.parent / "fixtures/test_upload_data.csv"
323
320
  textarea.fill(path.read_text())
@@ -364,6 +361,7 @@ def test_should_remove_dot_in_property_names(live_server, page, settings, tilela
364
361
  }
365
362
  page.goto(f"{live_server.url}/map/new/")
366
363
  page.get_by_title("Import data").click()
364
+ page.wait_for_timeout(300) # Time for the panel animation to finish
367
365
  textarea = page.locator(".umap-import textarea")
368
366
  textarea.fill(json.dumps(data))
369
367
  page.locator('select[name="format"]').select_option("geojson")
@@ -422,9 +420,8 @@ def test_import_geometry_collection(live_server, page, tilelayer):
422
420
  expect(markers).to_have_count(0)
423
421
  expect(paths).to_have_count(0)
424
422
  expect(layers).to_have_count(0)
425
- button = page.get_by_title("Import data")
426
- expect(button).to_be_visible()
427
- button.click()
423
+ page.get_by_title("Import data").click()
424
+ page.wait_for_timeout(300) # Time for the panel animation to finish
428
425
  textarea = page.locator(".umap-import textarea")
429
426
  textarea.fill(json.dumps(data))
430
427
  page.locator('select[name="format"]').select_option("geojson")
@@ -477,9 +474,8 @@ def test_import_geometry_collection_in_feature(live_server, page, tilelayer):
477
474
  expect(markers).to_have_count(0)
478
475
  expect(paths).to_have_count(0)
479
476
  expect(layers).to_have_count(0)
480
- button = page.get_by_title("Import data")
481
- expect(button).to_be_visible()
482
- button.click()
477
+ page.get_by_title("Import data").click()
478
+ page.wait_for_timeout(300) # Time for the panel animation to finish
483
479
  textarea = page.locator(".umap-import textarea")
484
480
  textarea.fill(json.dumps(data))
485
481
  page.locator('select[name="format"]').select_option("geojson")
@@ -513,9 +509,8 @@ def test_import_multipolygon(live_server, page, tilelayer):
513
509
  paths = page.locator("path")
514
510
  expect(paths).to_have_count(0)
515
511
  expect(layers).to_have_count(0)
516
- button = page.get_by_title("Import data")
517
- expect(button).to_be_visible()
518
- button.click()
512
+ page.get_by_title("Import data").click()
513
+ page.wait_for_timeout(300) # Time for the panel animation to finish
519
514
  textarea = page.locator(".umap-import textarea")
520
515
  textarea.fill(json.dumps(data))
521
516
  page.locator('select[name="format"]').select_option("geojson")
@@ -545,9 +540,8 @@ def test_import_multipolyline(live_server, page, tilelayer):
545
540
  paths = page.locator("path")
546
541
  expect(paths).to_have_count(0)
547
542
  expect(layers).to_have_count(0)
548
- button = page.get_by_title("Import data")
549
- expect(button).to_be_visible()
550
- button.click()
543
+ page.get_by_title("Import data").click()
544
+ page.wait_for_timeout(300) # Time for the panel animation to finish
551
545
  textarea = page.locator(".umap-import textarea")
552
546
  textarea.fill(json.dumps(data))
553
547
  page.locator('select[name="format"]').select_option("geojson")
@@ -577,9 +571,8 @@ def test_import_false_multipoint(live_server, page, tilelayer):
577
571
  markers = page.locator(".leaflet-marker-icon")
578
572
  expect(markers).to_have_count(0)
579
573
  expect(layers).to_have_count(0)
580
- button = page.get_by_title("Import data")
581
- expect(button).to_be_visible()
582
- button.click()
574
+ page.get_by_title("Import data").click()
575
+ page.wait_for_timeout(300) # Time for the panel animation to finish
583
576
  textarea = page.locator(".umap-import textarea")
584
577
  textarea.fill(json.dumps(data))
585
578
  page.locator('select[name="format"]').select_option("geojson")
@@ -644,6 +637,7 @@ def test_should_not_import_empty_coordinates(live_server, page, tilelayer):
644
637
  page.goto(f"{live_server.url}/map/new/")
645
638
  page.get_by_title("Open browser").click()
646
639
  page.get_by_title("Import data").click()
640
+ page.wait_for_timeout(300) # Time for the panel animation to finish
647
641
  textarea = page.locator(".umap-import textarea")
648
642
  textarea.fill(json.dumps(data))
649
643
  page.locator('select[name="format"]').select_option("geojson")
@@ -659,6 +653,7 @@ def test_import_csv_without_valid_latlon_headers(tilelayer, live_server, page):
659
653
  layers = page.locator(".umap-browser .datalayer")
660
654
  markers = page.locator(".leaflet-marker-icon")
661
655
  page.get_by_title("Import data").click()
656
+ page.wait_for_timeout(300) # Time for the panel animation to finish
662
657
  textarea = page.locator(".umap-import textarea")
663
658
  textarea.fill("a,b,c\n12.23,48.34,mypoint\n12.23,48.34,mypoint2")
664
659
  page.locator('select[name="format"]').select_option("csv")
@@ -676,6 +671,7 @@ def test_import_csv_with_commas_in_latlon(tilelayer, live_server, page, settings
676
671
  layers = page.locator(".umap-browser .datalayer")
677
672
  markers = page.locator(".leaflet-marker-icon")
678
673
  page.get_by_title("Import data").click()
674
+ page.wait_for_timeout(300) # Time for the panel animation to finish
679
675
  textarea = page.locator(".umap-import textarea")
680
676
  textarea.fill("lat;lon;foobar\n12,24;48,34;mypoint\n12,23;48,35;mypoint2")
681
677
  page.locator('select[name="format"]').select_option("csv")
@@ -710,9 +706,10 @@ def test_import_csv_with_wkt_geom(tilelayer, live_server, page, settings):
710
706
  markers = page.locator(".leaflet-marker-icon")
711
707
  paths = page.locator("path")
712
708
  page.get_by_title("Import data").click()
709
+ page.wait_for_timeout(300) # Time for the panel animation to finish
713
710
  textarea = page.locator(".umap-import textarea")
714
711
  textarea.fill(
715
- "geom;foobar\nPOLYGON ((-64.8 32.3, -65.5 18.3, -80.3 25.2, -64.8 32.3));mypoly\nPOINT(48.35 12.23);mypoint"
712
+ "Geom;foobar\nPOLYGON ((-64.8 32.3, -65.5 18.3, -80.3 25.2, -64.8 32.3));mypoly\nPOINT(48.35 12.23);mypoint"
716
713
  )
717
714
  page.locator('select[name="format"]').select_option("csv")
718
715
  page.get_by_role("button", name="Import data", exact=True).click()
@@ -763,6 +760,7 @@ def test_import_csv_with_geojson_geom(tilelayer, live_server, page, settings):
763
760
  markers = page.locator(".leaflet-marker-icon")
764
761
  paths = page.locator("path")
765
762
  page.get_by_title("Import data").click()
763
+ page.wait_for_timeout(300) # Time for the panel animation to finish
766
764
  textarea = page.locator(".umap-import textarea")
767
765
  textarea.fill(
768
766
  "geojson;foobar\n"
@@ -1056,9 +1054,8 @@ def test_import_osm_relation(tilelayer, live_server, page):
1056
1054
  paths = page.locator("path")
1057
1055
  expect(paths).to_have_count(0)
1058
1056
  expect(layers).to_have_count(0)
1059
- button = page.get_by_title("Import data")
1060
- expect(button).to_be_visible()
1061
- button.click()
1057
+ page.get_by_title("Import data").click()
1058
+ page.wait_for_timeout(300) # Time for the panel animation to finish
1062
1059
  textarea = page.locator(".umap-import textarea")
1063
1060
  file_path = Path(__file__).parent.parent / "fixtures/test_import_osm_relation.json"
1064
1061
  textarea.fill(file_path.read_text())
@@ -1076,9 +1073,8 @@ def test_import_georss_from_textarea(tilelayer, live_server, page):
1076
1073
  markers = page.locator(".leaflet-marker-icon")
1077
1074
  expect(markers).to_have_count(0)
1078
1075
  expect(layers).to_have_count(0)
1079
- button = page.get_by_title("Import data")
1080
- expect(button).to_be_visible()
1081
- button.click()
1076
+ page.get_by_title("Import data").click()
1077
+ page.wait_for_timeout(300) # Time for the panel animation to finish
1082
1078
  textarea = page.locator(".umap-import textarea")
1083
1079
  path = Path(__file__).parent.parent / "fixtures/test_upload_georss.xml"
1084
1080
  textarea.fill(path.read_text())
@@ -58,7 +58,7 @@ def test_map_preview_can_load_remote_geojson(page, live_server, tilelayer):
58
58
  expect(markers).to_have_count(1)
59
59
 
60
60
 
61
- def test_map_preview_can_load_mutiple_remote_geojson(page, live_server, tilelayer):
61
+ def test_map_preview_can_load_multiple_remote_geojson(page, live_server, tilelayer):
62
62
  def handle(route):
63
63
  if "2" in route.request.url:
64
64
  route.fulfill(json=GEOJSON2)
@@ -136,7 +136,7 @@ def test_can_change_picto_at_marker_level(openmap, live_server, page, pictos):
136
136
  expect(define).to_be_visible()
137
137
  expect(undefine).to_be_hidden()
138
138
  define.click()
139
- # Map has an icon defined, so it shuold open on Recent tab
139
+ # Map has an icon defined, so it should open on Recent tab
140
140
  symbols = page.locator(".umap-pictogram-body .umap-pictogram-choice")
141
141
  expect(page.get_by_text("Recent")).to_be_visible()
142
142
  expect(symbols).to_have_count(1)
@@ -42,3 +42,34 @@ def test_openstreetmap_popup(live_server, map, page):
42
42
  "src",
43
43
  "https://api.panoramax.xyz/api/pictures/d811b398-d930-4cf8-95a2-0c29c34d9fca/sd.jpg",
44
44
  )
45
+
46
+
47
+ def test_table_popup(live_server, map, page):
48
+ data = {
49
+ "type": "FeatureCollection",
50
+ "features": [
51
+ {
52
+ "type": "Feature",
53
+ "geometry": {"type": "Point", "coordinates": [2.49, 48.79]},
54
+ "properties": {
55
+ "url": "https://restaurant.org",
56
+ "formatted": "with **bold**",
57
+ },
58
+ "id": "AzMjk",
59
+ },
60
+ ],
61
+ "_umap_options": {
62
+ "popupTemplate": "Table",
63
+ "fields": [
64
+ {"key": "url", "type": "String"},
65
+ {"key": "formatted", "type": "Text"},
66
+ ],
67
+ },
68
+ }
69
+ DataLayerFactory(map=map, data=data)
70
+ page.goto(f"{live_server.url}{map.get_absolute_url()}#18/48.79/2.49")
71
+ page.locator(".leaflet-marker-icon").click()
72
+ expect(page.get_by_role("link", name="https://restaurant.org")).to_be_visible()
73
+ expect(page.get_by_role("cell", name="with bold").locator("strong")).to_have_text(
74
+ "bold"
75
+ )
@@ -1,11 +1,15 @@
1
+ import json
2
+ import re
3
+ from pathlib import Path
4
+
1
5
  from playwright.sync_api import expect
2
6
 
3
- from umap.models import Map
7
+ from umap.models import DataLayer, Map
4
8
 
5
9
  from ..base import DataLayerFactory
6
10
 
7
11
 
8
- def test_dynamic_remote_data(page, live_server, tilelayer, map):
12
+ def intercept_remote_data(page):
9
13
  data = [
10
14
  {
11
15
  "type": "FeatureCollection",
@@ -38,6 +42,13 @@ def test_dynamic_remote_data(page, live_server, tilelayer, map):
38
42
  def handle(route):
39
43
  route.fulfill(json=data.pop())
40
44
 
45
+ # Intercept the route to the proxy
46
+ page.route("https://remote.org/data.json", handle)
47
+ page.on("request", lambda *a, **k: print(a, k))
48
+
49
+
50
+ def test_dynamic_remote_data(page, live_server, tilelayer, map):
51
+ intercept_remote_data(page)
41
52
  settings = {
42
53
  "remoteData": {
43
54
  "url": "https://remote.org/data.json",
@@ -55,8 +66,6 @@ def test_dynamic_remote_data(page, live_server, tilelayer, map):
55
66
  }
56
67
  map.save()
57
68
 
58
- # Intercept the route to the proxy
59
- page.route("https://remote.org/data.json", handle)
60
69
  page.goto(f"{live_server.url}{map.get_absolute_url()}")
61
70
 
62
71
  expect(page.get_by_role("tooltip", name="Point 1")).to_be_visible()
@@ -77,3 +86,50 @@ def test_dynamic_remote_data(page, live_server, tilelayer, map):
77
86
  # Map must not be dirty
78
87
  page.get_by_role("button", name="Edit").click()
79
88
  expect(page.locator(".edit-undo")).to_be_disabled()
89
+
90
+
91
+ def test_create_remote_data_layer(page, live_server, tilelayer, settings):
92
+ settings.UMAP_ALLOW_ANONYMOUS = True
93
+ intercept_remote_data(page)
94
+ page.goto(f"{live_server.url}/en/map/new#6/11.2707/4.3375")
95
+ page.get_by_role("button", name="Manage layers").click()
96
+ page.get_by_role("button", name="Add a layer").click()
97
+ page.get_by_text("Remote data").click()
98
+ page.locator('.panel input[name="url"]').fill("https://remote.org/data.json")
99
+ # We have a setTimeout on each input to throttle, so wait for it
100
+ page.wait_for_timeout(300)
101
+ page.locator('select[name="format"]').select_option("geojson")
102
+ # with page.expect_response(re.compile("https://remote.org/data.json")):
103
+ page.get_by_role("button", name="Verify remote URL").click()
104
+ expect(page.locator(".leaflet-marker-icon")).to_have_count(1)
105
+ with page.expect_response(re.compile(".*/datalayer/create/.*")):
106
+ page.get_by_role("button", name="Save draft", exact=True).click()
107
+ datalayer = DataLayer.objects.last()
108
+ data = json.loads(Path(datalayer.geojson.path).read_text())
109
+ assert data == {
110
+ "_umap_options": {
111
+ "browsable": True,
112
+ "displayOnLoad": True,
113
+ "editMode": "advanced",
114
+ "fields": [
115
+ {
116
+ "key": "name",
117
+ "type": "String",
118
+ },
119
+ {
120
+ "key": "description",
121
+ "type": "Text",
122
+ },
123
+ ],
124
+ "id": str(datalayer.pk),
125
+ "inCaption": True,
126
+ "name": "Layer 1",
127
+ "rank": 0,
128
+ "remoteData": {
129
+ "format": "geojson",
130
+ "url": "https://remote.org/data.json",
131
+ },
132
+ },
133
+ "features": [],
134
+ "type": "FeatureCollection",
135
+ }
@@ -1,7 +1,7 @@
1
1
  import re
2
2
 
3
3
 
4
- def test_reseting_map_would_remove_from_save_queue(
4
+ def test_resetting_map_would_remove_from_save_queue(
5
5
  live_server, openmap, page, datalayer
6
6
  ):
7
7
  page.goto(f"{live_server.url}{openmap.get_absolute_url()}?edit")
@@ -18,10 +18,10 @@ def test_iframe_code_can_contain_datalayers(map, live_server, datalayer, page):
18
18
  expect(textarea).not_to_have_text(re.compile(f"datalayers={datalayer.pk}"))
19
19
  # Open options
20
20
  page.get_by_text("Embed and link options").click()
21
- page.get_by_title("Keep current visible layers").click()
21
+ page.get_by_text("Keep current visible layers").click()
22
22
  expect(textarea).to_have_text(re.compile(f"datalayers={datalayer.pk}"))
23
23
  # Now click again
24
- page.get_by_title("Keep current visible layers").click()
24
+ page.get_by_text("Keep current visible layers").click()
25
25
  expect(textarea).not_to_have_text(re.compile(f"datalayers={datalayer.pk}"))
26
26
 
27
27
 
@@ -33,8 +33,8 @@ def test_iframe_code_can_contain_feature(map, live_server, datalayer, page):
33
33
  expect(textarea).not_to_have_text(re.compile("feature=Here"))
34
34
  # Open options
35
35
  page.get_by_text("Embed and link options").click()
36
- page.get_by_title("Open current feature on load").click()
36
+ page.get_by_text("Open current feature on load").click()
37
37
  expect(textarea).to_have_text(re.compile("feature=Here"))
38
38
  # Click again to deactivate it
39
- page.get_by_title("Open current feature on load").click()
39
+ page.get_by_text("Open current feature on load").click()
40
40
  expect(textarea).not_to_have_text(re.compile("feature=Here"))
@@ -4,7 +4,7 @@ from pathlib import Path
4
4
 
5
5
  from playwright.sync_api import expect
6
6
 
7
- from umap.models import DataLayer
7
+ from umap.models import DataLayer, Map
8
8
 
9
9
  from ..base import DataLayerFactory
10
10
 
@@ -79,7 +79,7 @@ def test_table_editor(live_server, openmap, datalayer, page):
79
79
  page.wait_for_timeout(300) # Time for the input debounce.
80
80
  page.keyboard.press("Enter")
81
81
  page.locator("thead button[data-property=name]").click()
82
- page.get_by_role("button", name="Delete this column").click()
82
+ page.get_by_role("button", name="Delete this field").click()
83
83
  page.locator("dialog").get_by_role("button", name="OK").click()
84
84
  with page.expect_response(re.compile(r".*/datalayer/update/.*")):
85
85
  page.get_by_role("button", name="Save").click()
@@ -116,14 +116,14 @@ def test_cannot_add_property_with_a_dot(live_server, openmap, datalayer, page):
116
116
  expect(page.locator("table th button[data-property=name]")).to_have_count(1)
117
117
 
118
118
 
119
- def test_rename_property(live_server, openmap, page):
119
+ def test_rename_field(live_server, openmap, page):
120
120
  DataLayerFactory(map=openmap, data=DATALAYER_DATA)
121
121
  page.goto(f"{live_server.url}{openmap.get_absolute_url()}?edit#6/48.093/1.890")
122
122
  page.get_by_role("button", name="Manage layers").click()
123
123
  page.locator(".panel").get_by_title("Edit properties in a table").click()
124
124
  expect(page.locator("table th button[data-property=mytype]")).to_have_count(1)
125
125
  page.locator("thead button[data-property=mytype]").click()
126
- page.get_by_text("Rename this column").click()
126
+ page.get_by_text("Edit this field").click()
127
127
  page.locator("dialog").locator("input").fill("mynewtype")
128
128
  page.get_by_role("button", name="OK").click()
129
129
  expect(page.locator("table th button[data-property=mynewtype]")).to_have_count(1)
@@ -142,14 +142,14 @@ def test_rename_property(live_server, openmap, page):
142
142
  expect(page.locator(".panel.right .umap-field-mytype")).to_be_visible()
143
143
 
144
144
 
145
- def test_delete_property(live_server, openmap, page):
145
+ def test_delete_field(live_server, openmap, page):
146
146
  DataLayerFactory(map=openmap, data=DATALAYER_DATA)
147
147
  page.goto(f"{live_server.url}{openmap.get_absolute_url()}?edit#6/48.093/1.890")
148
148
  page.get_by_role("button", name="Manage layers").click()
149
149
  page.locator(".panel").get_by_title("Edit properties in a table").click()
150
150
  expect(page.locator("table th button[data-property=mytype]")).to_have_count(1)
151
151
  page.locator("thead button[data-property=mytype]").click()
152
- page.get_by_text("Delete this column").click()
152
+ page.get_by_text("Delete this field").click()
153
153
  page.get_by_role("button", name="OK").click()
154
154
  expect(page.locator("table th button[data-property=mytype]")).to_have_count(0)
155
155
 
@@ -202,7 +202,8 @@ def test_filter_and_delete_rows(live_server, openmap, page):
202
202
  expect(table.locator("tbody tr")).to_have_count(4)
203
203
  expect(page.locator(".leaflet-marker-icon")).to_have_count(4)
204
204
  table.locator("thead button[data-property=mytype]").click()
205
- page.get_by_role("button", name="Add filter for this column").click()
205
+ page.get_by_role("button", name="Add filter for this field").click()
206
+ page.get_by_role("button", name="OK").click()
206
207
  expect(panel).to_be_visible()
207
208
  panel.get_by_label("even").check()
208
209
  table.locator("thead").get_by_role("checkbox").check()
@@ -214,3 +215,26 @@ def test_filter_and_delete_rows(live_server, openmap, page):
214
215
  expect(table.get_by_text("Point 3")).to_be_visible()
215
216
  expect(table.get_by_text("Point 2")).to_be_hidden()
216
217
  expect(table.get_by_text("Point 4")).to_be_hidden()
218
+
219
+
220
+ def test_add_filter_on_map_field(live_server, openmap, page):
221
+ openmap.settings["properties"]["fields"] = [{"key": "mynumber", "type": "Number"}]
222
+ openmap.save()
223
+ table = page.locator(".panel.full table")
224
+ DataLayerFactory(map=openmap, data=DATALAYER_DATA)
225
+ page.goto(f"{live_server.url}{openmap.get_absolute_url()}?edit#6/48.093/1.890")
226
+ page.get_by_role("button", name="Manage layers").click()
227
+ page.locator(".panel").get_by_title("Edit properties in a table").click()
228
+ table.locator("thead button[data-property=mynumber]").click()
229
+ page.get_by_role("button", name="Add filter for this field").click()
230
+ expect(page.locator("dialog").get_by_label("Min/Max", exact=True)).to_be_checked()
231
+ page.locator("dialog").get_by_label("human readable name").fill("My Fun Filter")
232
+ page.wait_for_timeout(300) # Throttling…
233
+ page.get_by_role("button", name="OK").click()
234
+ expect(page.locator(".panel.left.on").get_by_text("My Fun Filter")).to_be_visible()
235
+ with page.expect_response(re.compile("./update/settings/.*")):
236
+ page.get_by_role("button", name="Save").click()
237
+ saved = Map.objects.first()
238
+ assert saved.settings["properties"]["filters"] == [
239
+ {"fieldKey": "mynumber", "widget": "MinMax", "label": "My Fun Filter"}
240
+ ]