django-gisserver 1.5.0__tar.gz → 2.1__tar.gz
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.
- {django_gisserver-1.5.0 → django_gisserver-2.1}/CHANGES.md +91 -0
- {django_gisserver-1.5.0/django_gisserver.egg-info → django_gisserver-2.1}/PKG-INFO +34 -8
- {django_gisserver-1.5.0 → django_gisserver-2.1}/README.md +10 -3
- {django_gisserver-1.5.0 → django_gisserver-2.1/django_gisserver.egg-info}/PKG-INFO +34 -8
- {django_gisserver-1.5.0 → django_gisserver-2.1}/django_gisserver.egg-info/SOURCES.txt +25 -11
- {django_gisserver-1.5.0 → django_gisserver-2.1}/django_gisserver.egg-info/requires.txt +7 -1
- django_gisserver-2.1/gisserver/__init__.py +1 -0
- django_gisserver-2.1/gisserver/compat.py +23 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/conf.py +7 -0
- django_gisserver-2.1/gisserver/crs.py +401 -0
- django_gisserver-2.1/gisserver/db.py +215 -0
- django_gisserver-2.1/gisserver/exceptions.py +294 -0
- django_gisserver-2.1/gisserver/extensions/__init__.py +4 -0
- {django_gisserver-1.5.0/gisserver/parsers/fes20 → django_gisserver-2.1/gisserver/extensions}/functions.py +131 -31
- django_gisserver-2.1/gisserver/extensions/queries.py +266 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/features.py +253 -181
- django_gisserver-2.1/gisserver/geometries.py +111 -0
- django_gisserver-2.1/gisserver/management/commands/loadgeojson.py +311 -0
- django_gisserver-2.1/gisserver/operations/__init__.py +0 -0
- django_gisserver-2.1/gisserver/operations/base.py +266 -0
- django_gisserver-2.1/gisserver/operations/wfs20.py +516 -0
- django_gisserver-2.1/gisserver/output/__init__.py +39 -0
- django_gisserver-2.1/gisserver/output/base.py +283 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/output/csv.py +78 -75
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/output/geojson.py +37 -37
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/output/gml32.py +287 -259
- django_gisserver-1.5.0/gisserver/output/utils.py → django_gisserver-2.1/gisserver/output/iters.py +30 -2
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/output/results.py +73 -61
- django_gisserver-2.1/gisserver/output/stored.py +143 -0
- django_gisserver-2.1/gisserver/output/utils.py +91 -0
- django_gisserver-2.1/gisserver/output/xmlschema.py +161 -0
- django_gisserver-2.1/gisserver/parsers/__init__.py +13 -0
- django_gisserver-2.1/gisserver/parsers/ast.py +426 -0
- django_gisserver-2.1/gisserver/parsers/fes20/__init__.py +100 -0
- django_gisserver-2.1/gisserver/parsers/fes20/expressions.py +386 -0
- django_gisserver-2.1/gisserver/parsers/fes20/filters.py +168 -0
- django_gisserver-2.1/gisserver/parsers/fes20/identifiers.py +132 -0
- django_gisserver-2.1/gisserver/parsers/fes20/lookups.py +146 -0
- django_gisserver-2.1/gisserver/parsers/fes20/operators.py +924 -0
- django_gisserver-2.1/gisserver/parsers/fes20/sorting.py +154 -0
- django_gisserver-2.1/gisserver/parsers/gml/__init__.py +46 -0
- django_gisserver-2.1/gisserver/parsers/gml/base.py +58 -0
- django_gisserver-2.1/gisserver/parsers/gml/geometries.py +161 -0
- django_gisserver-2.1/gisserver/parsers/ows/__init__.py +25 -0
- django_gisserver-2.1/gisserver/parsers/ows/kvp.py +198 -0
- django_gisserver-2.1/gisserver/parsers/ows/requests.py +160 -0
- django_gisserver-2.1/gisserver/parsers/query.py +179 -0
- django_gisserver-2.1/gisserver/parsers/values.py +123 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/__init__.py +39 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/adhoc.py +253 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/base.py +148 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/projection.py +103 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/requests.py +483 -0
- django_gisserver-2.1/gisserver/parsers/wfs20/stored.py +193 -0
- django_gisserver-2.1/gisserver/parsers/xml.py +261 -0
- django_gisserver-2.1/gisserver/projection.py +367 -0
- django_gisserver-2.1/gisserver/static/gisserver/index.css +20 -0
- django_gisserver-2.1/gisserver/templates/gisserver/base.html +12 -0
- django_gisserver-2.1/gisserver/templates/gisserver/index.html +20 -0
- django_gisserver-2.1/gisserver/templates/gisserver/service_description.html +22 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/templates/gisserver/wfs/2.0.0/get_capabilities.xml +9 -9
- django_gisserver-2.1/gisserver/templates/gisserver/wfs/feature_field.html +10 -0
- django_gisserver-2.1/gisserver/templates/gisserver/wfs/feature_type.html +45 -0
- django_gisserver-2.1/gisserver/templatetags/__init__.py +0 -0
- django_gisserver-2.1/gisserver/templatetags/gisserver_tags.py +30 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/gisserver/types.py +445 -313
- django_gisserver-2.1/gisserver/views.py +489 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/pyproject.toml +4 -3
- {django_gisserver-1.5.0 → django_gisserver-2.1}/setup.py +12 -4
- django_gisserver-1.5.0/gisserver/__init__.py +0 -1
- django_gisserver-1.5.0/gisserver/db.py +0 -140
- django_gisserver-1.5.0/gisserver/exceptions.py +0 -166
- django_gisserver-1.5.0/gisserver/geometries.py +0 -358
- django_gisserver-1.5.0/gisserver/operations/base.py +0 -448
- django_gisserver-1.5.0/gisserver/operations/wfs20.py +0 -492
- django_gisserver-1.5.0/gisserver/output/__init__.py +0 -74
- django_gisserver-1.5.0/gisserver/output/base.py +0 -229
- django_gisserver-1.5.0/gisserver/output/xmlschema.py +0 -122
- django_gisserver-1.5.0/gisserver/parsers/__init__.py +0 -13
- django_gisserver-1.5.0/gisserver/parsers/base.py +0 -149
- django_gisserver-1.5.0/gisserver/parsers/fes20/__init__.py +0 -42
- django_gisserver-1.5.0/gisserver/parsers/fes20/expressions.py +0 -272
- django_gisserver-1.5.0/gisserver/parsers/fes20/filters.py +0 -97
- django_gisserver-1.5.0/gisserver/parsers/fes20/identifiers.py +0 -94
- django_gisserver-1.5.0/gisserver/parsers/fes20/operators.py +0 -668
- django_gisserver-1.5.0/gisserver/parsers/fes20/query.py +0 -285
- django_gisserver-1.5.0/gisserver/parsers/fes20/sorting.py +0 -75
- django_gisserver-1.5.0/gisserver/parsers/gml/__init__.py +0 -54
- django_gisserver-1.5.0/gisserver/parsers/gml/base.py +0 -37
- django_gisserver-1.5.0/gisserver/parsers/gml/geometries.py +0 -100
- django_gisserver-1.5.0/gisserver/parsers/tags.py +0 -102
- django_gisserver-1.5.0/gisserver/parsers/values.py +0 -40
- django_gisserver-1.5.0/gisserver/queries/__init__.py +0 -37
- django_gisserver-1.5.0/gisserver/queries/adhoc.py +0 -185
- django_gisserver-1.5.0/gisserver/queries/base.py +0 -186
- django_gisserver-1.5.0/gisserver/queries/projection.py +0 -240
- django_gisserver-1.5.0/gisserver/queries/stored.py +0 -206
- django_gisserver-1.5.0/gisserver/static/gisserver/index.css +0 -4
- django_gisserver-1.5.0/gisserver/templates/gisserver/index.html +0 -26
- django_gisserver-1.5.0/gisserver/templates/gisserver/service_description.html +0 -16
- django_gisserver-1.5.0/gisserver/templates/gisserver/wfs/2.0.0/describe_stored_queries.xml +0 -20
- django_gisserver-1.5.0/gisserver/templates/gisserver/wfs/2.0.0/list_stored_queries.xml +0 -14
- django_gisserver-1.5.0/gisserver/templates/gisserver/wfs/feature_field.html +0 -10
- django_gisserver-1.5.0/gisserver/templates/gisserver/wfs/feature_type.html +0 -23
- django_gisserver-1.5.0/gisserver/templatetags/gisserver_tags.py +0 -10
- django_gisserver-1.5.0/gisserver/views.py +0 -324
- {django_gisserver-1.5.0 → django_gisserver-2.1}/LICENSE +0 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/MANIFEST.in +0 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/django_gisserver.egg-info/dependency_links.txt +0 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/django_gisserver.egg-info/not-zip-safe +0 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/django_gisserver.egg-info/top_level.txt +0 -0
- {django_gisserver-1.5.0/gisserver/operations → django_gisserver-2.1/gisserver/management}/__init__.py +0 -0
- {django_gisserver-1.5.0/gisserver/templatetags → django_gisserver-2.1/gisserver/management/commands}/__init__.py +0 -0
- {django_gisserver-1.5.0 → django_gisserver-2.1}/setup.cfg +0 -0
|
@@ -1,10 +1,101 @@
|
|
|
1
|
+
# 2025-05-29 (2.1)
|
|
2
|
+
|
|
3
|
+
* Added support for `ArrayField` field in CSV exports.
|
|
4
|
+
* Added support for `models.DurationField` for features.
|
|
5
|
+
* Added proper axis ordering handling.
|
|
6
|
+
* Changed built-in fes functions to match current GeoServer signatures.
|
|
7
|
+
* Improved error handling for invalid filter input (also fixes 500 errors).
|
|
8
|
+
* Improved error handling for database query errors during rendering.
|
|
9
|
+
* Improved error messages for unexpected tags in the XML body.
|
|
10
|
+
* Improved error handling for fes 1.0 arithmetic operators (e.g. typing: `date > 2020-01-01` in QGis).
|
|
11
|
+
* Improved HTML index page, make it easier to override and restyle.
|
|
12
|
+
* Improved documentation, added API documentation.
|
|
13
|
+
* Fixed axis ordering handling for `EPSG:4326` and other longitude/latitude CRS definitions.
|
|
14
|
+
* Fixed comparing to `NULL` when date/time input is invalid.
|
|
15
|
+
* Fixed filter comparisons for `<`, `<=`, `>`, `>=` when using a reversed "value < property" ordering.
|
|
16
|
+
* Fixed crash when receiving WFS 1.0 POST requests.
|
|
17
|
+
* Fixed building readthedocs.
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
# 2025-04-28 (2.0)
|
|
21
|
+
|
|
22
|
+
* Added support for XML POST requests.
|
|
23
|
+
* Added support for geometry elements on child nodes.
|
|
24
|
+
* Added support for Django 5 `GeneratedField` fields as geometry field.
|
|
25
|
+
* Added `WFSView.check_permissions()` API to simplify permission checking.
|
|
26
|
+
* Added `WFSView.xml_namespace_aliases` attribute to configure custom namespace prefixes.
|
|
27
|
+
* Added example app and docker-compose setup for testing.
|
|
28
|
+
* Added `GISSERVER_EXTRA_OUTPUT_FORMATS` setting to define additional output formats.
|
|
29
|
+
* Added `GISSERVER_GET_FEATURE_OUTPUT_FORMATS` setting to override the default output formats.
|
|
30
|
+
* Added `CRS84` and `WEB_MERCATOR` constants in `gisserver.geometries`.
|
|
31
|
+
* Improved debugging by adding debug-level logging and better error messages.
|
|
32
|
+
* Improved font styling somewhat for browsable HTML pages.
|
|
33
|
+
* Fixed XML namespace support (e.g. handling `<ValueReference>ns0:tagname</ValueReference>`).
|
|
34
|
+
* Fixed bugs found by CITE compliance testing:
|
|
35
|
+
* Support `<fes:PropertyIsLike>` for array elements.
|
|
36
|
+
* Support `<fes:PropertyIsNil>` for geometry elements.
|
|
37
|
+
* Support `resulttype=hits` with `count` arguments.
|
|
38
|
+
* Fixed `ArrayField` detection when `django.contrib.postgres` is not in `INSTALLED_APPS`.
|
|
39
|
+
* Fixed `main_geometry_element` detection.
|
|
40
|
+
* Fixed swapped X/Y coordinates for systems that use a different axis-ordering (e.g. EPSG:3879 for Finland).
|
|
41
|
+
* Fixed GeoJSON CRS value to be `CRS84` (urn:ogc:def:crs:OGC::CRS84) instead of WGS84 (urn:ogc:def:crs:EPSG::4326).
|
|
42
|
+
* Fixed applying the `CRS.backend` when the client requests a custom coordinate system using `srsName`.
|
|
43
|
+
* Fixed rendering JSON exceptions during streaming errors.
|
|
44
|
+
* Fixed internal XML Schema; use proper model CamelCasing for class names (doesn't affect requests).
|
|
45
|
+
* Fixed internal XML schema; remove unneeded inheritance from `gml:AbstractFeatureType` for nested elements.
|
|
46
|
+
* Fixed CI testing.
|
|
47
|
+
* Confirmed support for Python 3.13.
|
|
48
|
+
|
|
49
|
+
This release has a lot of API changes, renamed and moved classes,
|
|
50
|
+
which was needed to implement POST support and XML namespace handling.
|
|
51
|
+
|
|
52
|
+
This won't affect most projects as they use the basic `FeatureType` functionality.
|
|
53
|
+
For implementations that have taken full advantage of our architecture,
|
|
54
|
+
the notable API changes are:
|
|
55
|
+
|
|
56
|
+
* Configuration:
|
|
57
|
+
* `WFSOperation.output_formats` still works, but `get_output_formats()` is preferred.
|
|
58
|
+
* `WFSOperation.parameters` is replaced by ``get_parameters()`` and only lists parameters that need to be mentioned in `GetCapabilities`.
|
|
59
|
+
* The `Parameter` class only exposes choices, parsing happens in `gisserver.parsers.wfs20` now.
|
|
60
|
+
* `FeatureType.xml_namespace` now defines which namespace the feature exists in (defaults to `WFSView.xml_namespace`).
|
|
61
|
+
* Overiding and extending queries:
|
|
62
|
+
* `FeatureType.get_extent()` was replaced with ``GmlBoundedByElement.get_value()``.
|
|
63
|
+
* `gisserver.operations`: renamed `WFSMethod` -> `WFSOperation`.
|
|
64
|
+
* `gisserver.extensions.functions` now tracks filter function registration.
|
|
65
|
+
* `gisserver.extensions.queries` now tracks stored query registration.
|
|
66
|
+
* The `StoredQuery` base class is now `StoredQueryImplementation` providing a `build_query()` method.
|
|
67
|
+
* The internal `CompiledQuery` moved to `gisserver.parsers.query` and receives a `feature_types` array now with a single element.
|
|
68
|
+
(This change reflects the WFS spec and allowing to potentially implement JOIN queries later).
|
|
69
|
+
* Request parsing:
|
|
70
|
+
* `WFSView.ows_request` and `request.ows_request` both provide access to the parsed WFS request.
|
|
71
|
+
* `WFSOperation.parser_class` allows to define a custom parser for a additional WFS operations.
|
|
72
|
+
* The WFS request parsing moved to `gisserver.parsers.wfs20`, which builds an Abstract Syntax Tree (AST) of the XML request.
|
|
73
|
+
* The GET request (KVP format) parsing is now a special-case of the XML-based parsing classes.
|
|
74
|
+
* Output formats:
|
|
75
|
+
* `gisserver.output` no longer exposes the auto-switching DB/non-DB rendering aliases, as `get_output_formats()` can do that easier.
|
|
76
|
+
* `OutputRenderer` only provides the basic XML aliasing, a new `CollectionOutputRenderer` base class provides the collection logic.
|
|
77
|
+
* `OutputRenderer.xml_namespaces` allows defining XML namespace aliases that construct default `xmlns` attributes.
|
|
78
|
+
* All rendering parameters (e.g. output CRS) moved to the `FeatureProjection` logic.
|
|
79
|
+
* The `decorate_queryset()` logic is no longer a classmethod.
|
|
80
|
+
* Internal XSD schema elements:
|
|
81
|
+
* XML tag parsing is reworked for simplicity and namespace handling.
|
|
82
|
+
* Namespace aliases/prefixes are removed entirely, and resolved during rendering.
|
|
83
|
+
* `FeatureType.xml_name` now returns the full XML name, not the QName.
|
|
84
|
+
* `XsdTypes` use fully qualified XML names, not the QName.
|
|
85
|
+
* `XsdElement.xml_name` now returns the full XML name, not the QName.
|
|
86
|
+
* `XsdElement.is_geometry` was unneeded, use `XsdElement.type.is_geometry` now.
|
|
87
|
+
* `XsdElement.orm_path` points to the absolute path, and `XsdElement.local_orm_path` to the relative path.
|
|
88
|
+
|
|
89
|
+
|
|
1
90
|
# 2024-11-25 (1.5.0)
|
|
2
91
|
|
|
3
92
|
* Added `PROPERTYNAME` support
|
|
4
93
|
* Added rendering of `<wfs:truncatedResponse>` when errors happen during output streaming.
|
|
94
|
+
* Fixed accessing a feature with 3 geometry fields (fixed our PostgreSQL `ST_Union` syntax).
|
|
5
95
|
* Make sure Django 4.1+ won't do double prefetches on relations that we prefetch.
|
|
6
96
|
* Hide the erroneous output formats in `GetCapabilities` that are supported for FME.
|
|
7
97
|
* Bump requirements to non-vulnerable versions (of lxml and orjson).
|
|
98
|
+
* Improved documentation.
|
|
8
99
|
* Cleaned up code, removing some internal methods.
|
|
9
100
|
* Cleaned up leftover Python 3.7 compat code.
|
|
10
101
|
|
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: django-gisserver
|
|
3
|
-
Version: 1
|
|
3
|
+
Version: 2.1
|
|
4
4
|
Summary: Django speaking WFS 2.0 (exposing GeoDjango model fields)
|
|
5
5
|
Home-page: https://github.com/amsterdam/django-gisserver
|
|
6
6
|
Author: Diederik van der Boor
|
|
7
7
|
Author-email: opensource@edoburu.nl
|
|
8
8
|
License: Mozilla Public License 2.0
|
|
9
|
-
Classifier: Development Status ::
|
|
9
|
+
Classifier: Development Status :: 5 - Production/Stable
|
|
10
10
|
Classifier: Environment :: Web Environment
|
|
11
11
|
Classifier: Intended Audience :: Developers
|
|
12
12
|
Classifier: License :: OSI Approved :: Mozilla Public License 2.0 (MPL 2.0)
|
|
@@ -16,6 +16,7 @@ Classifier: Programming Language :: Python :: 3.9
|
|
|
16
16
|
Classifier: Programming Language :: Python :: 3.10
|
|
17
17
|
Classifier: Programming Language :: Python :: 3.11
|
|
18
18
|
Classifier: Programming Language :: Python :: 3.12
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
20
|
Classifier: Framework :: Django
|
|
20
21
|
Classifier: Framework :: Django :: 3.2
|
|
21
22
|
Classifier: Framework :: Django :: 4.0
|
|
@@ -27,13 +28,14 @@ Classifier: Topic :: Internet :: WWW/HTTP :: Dynamic Content
|
|
|
27
28
|
Classifier: Topic :: Software Development :: Libraries :: Application Frameworks
|
|
28
29
|
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
29
30
|
Requires: Django (>=3.2)
|
|
30
|
-
Requires-Python: >=3.
|
|
31
|
+
Requires-Python: >=3.9
|
|
31
32
|
Description-Content-Type: text/markdown
|
|
32
33
|
License-File: LICENSE
|
|
33
34
|
Requires-Dist: Django>=3.2
|
|
34
|
-
Requires-Dist: defusedxml>=0.
|
|
35
|
+
Requires-Dist: defusedxml>=0.7.1
|
|
35
36
|
Requires-Dist: lru_dict>=1.1.7
|
|
36
37
|
Requires-Dist: orjson>=3.9.15
|
|
38
|
+
Requires-Dist: pyproj>=3.6.1
|
|
37
39
|
Provides-Extra: tests
|
|
38
40
|
Requires-Dist: django-environ>=0.4.5; extra == "tests"
|
|
39
41
|
Requires-Dist: psycopg2-binary>=2.8.4; extra == "tests"
|
|
@@ -41,6 +43,23 @@ Requires-Dist: lxml>=4.9.1; extra == "tests"
|
|
|
41
43
|
Requires-Dist: pytest>=6.2.3; extra == "tests"
|
|
42
44
|
Requires-Dist: pytest-django>=4.1.0; extra == "tests"
|
|
43
45
|
Requires-Dist: pytest-cov>=2.11.1; extra == "tests"
|
|
46
|
+
Provides-Extra: docs
|
|
47
|
+
Requires-Dist: Django~=5.0; extra == "docs"
|
|
48
|
+
Requires-Dist: sphinxcontrib-django>=2.5; extra == "docs"
|
|
49
|
+
Requires-Dist: psycopg2-binary>=2.8.4; extra == "docs"
|
|
50
|
+
Dynamic: author
|
|
51
|
+
Dynamic: author-email
|
|
52
|
+
Dynamic: classifier
|
|
53
|
+
Dynamic: description
|
|
54
|
+
Dynamic: description-content-type
|
|
55
|
+
Dynamic: home-page
|
|
56
|
+
Dynamic: license
|
|
57
|
+
Dynamic: license-file
|
|
58
|
+
Dynamic: provides-extra
|
|
59
|
+
Dynamic: requires
|
|
60
|
+
Dynamic: requires-dist
|
|
61
|
+
Dynamic: requires-python
|
|
62
|
+
Dynamic: summary
|
|
44
63
|
|
|
45
64
|
[](https://django-gisserver.readthedocs.io/en/latest/?badge=latest)
|
|
46
65
|
[](https://github.com/Amsterdam/django-gisserver/actions/workflows/tests.yaml)
|
|
@@ -66,6 +85,12 @@ Django speaking WFS 2.0 to expose geo data.
|
|
|
66
85
|
|
|
67
86
|
For more details, see: <https://django-gisserver.readthedocs.io/>
|
|
68
87
|
|
|
88
|
+
## Test drive
|
|
89
|
+
|
|
90
|
+
* Run `docker compose up`.
|
|
91
|
+
* Open http://localhost:8000/ to see this works.
|
|
92
|
+
* Connect to http://localhost:8000/wfs/ in your GIS client (e.g. QGis) and zoom to Amsterdam.
|
|
93
|
+
* Add more data on the map using the Django admin, username and password are both "admin".
|
|
69
94
|
|
|
70
95
|
## Quickstart
|
|
71
96
|
|
|
@@ -102,12 +127,13 @@ class Restaurant(models.Model):
|
|
|
102
127
|
Write a view that exposes this model as a WFS feature:
|
|
103
128
|
|
|
104
129
|
```python
|
|
130
|
+
from gisserver.crs import CRS, CRS84, WEB_MERCATOR
|
|
105
131
|
from gisserver.features import FeatureType, ServiceDescription
|
|
106
|
-
from gisserver.geometries import CRS, WGS84
|
|
107
132
|
from gisserver.views import WFSView
|
|
108
133
|
from .models import Restaurant
|
|
109
134
|
|
|
110
|
-
|
|
135
|
+
# As example, the local coordinate system for The Netherlands
|
|
136
|
+
RD_NEW = CRS.from_string("urn:ogc:def:crs:EPSG::28992")
|
|
111
137
|
|
|
112
138
|
|
|
113
139
|
class PlacesWFSView(WFSView):
|
|
@@ -130,7 +156,7 @@ class PlacesWFSView(WFSView):
|
|
|
130
156
|
FeatureType(
|
|
131
157
|
Restaurant.objects.all(),
|
|
132
158
|
fields="__all__",
|
|
133
|
-
other_crs=[RD_NEW]
|
|
159
|
+
other_crs=[RD_NEW, CRS84, WEB_MERCATOR]
|
|
134
160
|
),
|
|
135
161
|
]
|
|
136
162
|
```
|
|
@@ -22,6 +22,12 @@ Django speaking WFS 2.0 to expose geo data.
|
|
|
22
22
|
|
|
23
23
|
For more details, see: <https://django-gisserver.readthedocs.io/>
|
|
24
24
|
|
|
25
|
+
## Test drive
|
|
26
|
+
|
|
27
|
+
* Run `docker compose up`.
|
|
28
|
+
* Open http://localhost:8000/ to see this works.
|
|
29
|
+
* Connect to http://localhost:8000/wfs/ in your GIS client (e.g. QGis) and zoom to Amsterdam.
|
|
30
|
+
* Add more data on the map using the Django admin, username and password are both "admin".
|
|
25
31
|
|
|
26
32
|
## Quickstart
|
|
27
33
|
|
|
@@ -58,12 +64,13 @@ class Restaurant(models.Model):
|
|
|
58
64
|
Write a view that exposes this model as a WFS feature:
|
|
59
65
|
|
|
60
66
|
```python
|
|
67
|
+
from gisserver.crs import CRS, CRS84, WEB_MERCATOR
|
|
61
68
|
from gisserver.features import FeatureType, ServiceDescription
|
|
62
|
-
from gisserver.geometries import CRS, WGS84
|
|
63
69
|
from gisserver.views import WFSView
|
|
64
70
|
from .models import Restaurant
|
|
65
71
|
|
|
66
|
-
|
|
72
|
+
# As example, the local coordinate system for The Netherlands
|
|
73
|
+
RD_NEW = CRS.from_string("urn:ogc:def:crs:EPSG::28992")
|
|
67
74
|
|
|
68
75
|
|
|
69
76
|
class PlacesWFSView(WFSView):
|
|
@@ -86,7 +93,7 @@ class PlacesWFSView(WFSView):
|
|
|
86
93
|
FeatureType(
|
|
87
94
|
Restaurant.objects.all(),
|
|
88
95
|
fields="__all__",
|
|
89
|
-
other_crs=[RD_NEW]
|
|
96
|
+
other_crs=[RD_NEW, CRS84, WEB_MERCATOR]
|
|
90
97
|
),
|
|
91
98
|
]
|
|
92
99
|
```
|
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: django-gisserver
|
|
3
|
-
Version: 1
|
|
3
|
+
Version: 2.1
|
|
4
4
|
Summary: Django speaking WFS 2.0 (exposing GeoDjango model fields)
|
|
5
5
|
Home-page: https://github.com/amsterdam/django-gisserver
|
|
6
6
|
Author: Diederik van der Boor
|
|
7
7
|
Author-email: opensource@edoburu.nl
|
|
8
8
|
License: Mozilla Public License 2.0
|
|
9
|
-
Classifier: Development Status ::
|
|
9
|
+
Classifier: Development Status :: 5 - Production/Stable
|
|
10
10
|
Classifier: Environment :: Web Environment
|
|
11
11
|
Classifier: Intended Audience :: Developers
|
|
12
12
|
Classifier: License :: OSI Approved :: Mozilla Public License 2.0 (MPL 2.0)
|
|
@@ -16,6 +16,7 @@ Classifier: Programming Language :: Python :: 3.9
|
|
|
16
16
|
Classifier: Programming Language :: Python :: 3.10
|
|
17
17
|
Classifier: Programming Language :: Python :: 3.11
|
|
18
18
|
Classifier: Programming Language :: Python :: 3.12
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
20
|
Classifier: Framework :: Django
|
|
20
21
|
Classifier: Framework :: Django :: 3.2
|
|
21
22
|
Classifier: Framework :: Django :: 4.0
|
|
@@ -27,13 +28,14 @@ Classifier: Topic :: Internet :: WWW/HTTP :: Dynamic Content
|
|
|
27
28
|
Classifier: Topic :: Software Development :: Libraries :: Application Frameworks
|
|
28
29
|
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
29
30
|
Requires: Django (>=3.2)
|
|
30
|
-
Requires-Python: >=3.
|
|
31
|
+
Requires-Python: >=3.9
|
|
31
32
|
Description-Content-Type: text/markdown
|
|
32
33
|
License-File: LICENSE
|
|
33
34
|
Requires-Dist: Django>=3.2
|
|
34
|
-
Requires-Dist: defusedxml>=0.
|
|
35
|
+
Requires-Dist: defusedxml>=0.7.1
|
|
35
36
|
Requires-Dist: lru_dict>=1.1.7
|
|
36
37
|
Requires-Dist: orjson>=3.9.15
|
|
38
|
+
Requires-Dist: pyproj>=3.6.1
|
|
37
39
|
Provides-Extra: tests
|
|
38
40
|
Requires-Dist: django-environ>=0.4.5; extra == "tests"
|
|
39
41
|
Requires-Dist: psycopg2-binary>=2.8.4; extra == "tests"
|
|
@@ -41,6 +43,23 @@ Requires-Dist: lxml>=4.9.1; extra == "tests"
|
|
|
41
43
|
Requires-Dist: pytest>=6.2.3; extra == "tests"
|
|
42
44
|
Requires-Dist: pytest-django>=4.1.0; extra == "tests"
|
|
43
45
|
Requires-Dist: pytest-cov>=2.11.1; extra == "tests"
|
|
46
|
+
Provides-Extra: docs
|
|
47
|
+
Requires-Dist: Django~=5.0; extra == "docs"
|
|
48
|
+
Requires-Dist: sphinxcontrib-django>=2.5; extra == "docs"
|
|
49
|
+
Requires-Dist: psycopg2-binary>=2.8.4; extra == "docs"
|
|
50
|
+
Dynamic: author
|
|
51
|
+
Dynamic: author-email
|
|
52
|
+
Dynamic: classifier
|
|
53
|
+
Dynamic: description
|
|
54
|
+
Dynamic: description-content-type
|
|
55
|
+
Dynamic: home-page
|
|
56
|
+
Dynamic: license
|
|
57
|
+
Dynamic: license-file
|
|
58
|
+
Dynamic: provides-extra
|
|
59
|
+
Dynamic: requires
|
|
60
|
+
Dynamic: requires-dist
|
|
61
|
+
Dynamic: requires-python
|
|
62
|
+
Dynamic: summary
|
|
44
63
|
|
|
45
64
|
[](https://django-gisserver.readthedocs.io/en/latest/?badge=latest)
|
|
46
65
|
[](https://github.com/Amsterdam/django-gisserver/actions/workflows/tests.yaml)
|
|
@@ -66,6 +85,12 @@ Django speaking WFS 2.0 to expose geo data.
|
|
|
66
85
|
|
|
67
86
|
For more details, see: <https://django-gisserver.readthedocs.io/>
|
|
68
87
|
|
|
88
|
+
## Test drive
|
|
89
|
+
|
|
90
|
+
* Run `docker compose up`.
|
|
91
|
+
* Open http://localhost:8000/ to see this works.
|
|
92
|
+
* Connect to http://localhost:8000/wfs/ in your GIS client (e.g. QGis) and zoom to Amsterdam.
|
|
93
|
+
* Add more data on the map using the Django admin, username and password are both "admin".
|
|
69
94
|
|
|
70
95
|
## Quickstart
|
|
71
96
|
|
|
@@ -102,12 +127,13 @@ class Restaurant(models.Model):
|
|
|
102
127
|
Write a view that exposes this model as a WFS feature:
|
|
103
128
|
|
|
104
129
|
```python
|
|
130
|
+
from gisserver.crs import CRS, CRS84, WEB_MERCATOR
|
|
105
131
|
from gisserver.features import FeatureType, ServiceDescription
|
|
106
|
-
from gisserver.geometries import CRS, WGS84
|
|
107
132
|
from gisserver.views import WFSView
|
|
108
133
|
from .models import Restaurant
|
|
109
134
|
|
|
110
|
-
|
|
135
|
+
# As example, the local coordinate system for The Netherlands
|
|
136
|
+
RD_NEW = CRS.from_string("urn:ogc:def:crs:EPSG::28992")
|
|
111
137
|
|
|
112
138
|
|
|
113
139
|
class PlacesWFSView(WFSView):
|
|
@@ -130,7 +156,7 @@ class PlacesWFSView(WFSView):
|
|
|
130
156
|
FeatureType(
|
|
131
157
|
Restaurant.objects.all(),
|
|
132
158
|
fields="__all__",
|
|
133
|
-
other_crs=[RD_NEW]
|
|
159
|
+
other_crs=[RD_NEW, CRS84, WEB_MERCATOR]
|
|
134
160
|
),
|
|
135
161
|
]
|
|
136
162
|
```
|
|
@@ -11,13 +11,22 @@ django_gisserver.egg-info/not-zip-safe
|
|
|
11
11
|
django_gisserver.egg-info/requires.txt
|
|
12
12
|
django_gisserver.egg-info/top_level.txt
|
|
13
13
|
gisserver/__init__.py
|
|
14
|
+
gisserver/compat.py
|
|
14
15
|
gisserver/conf.py
|
|
16
|
+
gisserver/crs.py
|
|
15
17
|
gisserver/db.py
|
|
16
18
|
gisserver/exceptions.py
|
|
17
19
|
gisserver/features.py
|
|
18
20
|
gisserver/geometries.py
|
|
21
|
+
gisserver/projection.py
|
|
19
22
|
gisserver/types.py
|
|
20
23
|
gisserver/views.py
|
|
24
|
+
gisserver/extensions/__init__.py
|
|
25
|
+
gisserver/extensions/functions.py
|
|
26
|
+
gisserver/extensions/queries.py
|
|
27
|
+
gisserver/management/__init__.py
|
|
28
|
+
gisserver/management/commands/__init__.py
|
|
29
|
+
gisserver/management/commands/loadgeojson.py
|
|
21
30
|
gisserver/operations/__init__.py
|
|
22
31
|
gisserver/operations/base.py
|
|
23
32
|
gisserver/operations/wfs20.py
|
|
@@ -26,36 +35,41 @@ gisserver/output/base.py
|
|
|
26
35
|
gisserver/output/csv.py
|
|
27
36
|
gisserver/output/geojson.py
|
|
28
37
|
gisserver/output/gml32.py
|
|
38
|
+
gisserver/output/iters.py
|
|
29
39
|
gisserver/output/results.py
|
|
40
|
+
gisserver/output/stored.py
|
|
30
41
|
gisserver/output/utils.py
|
|
31
42
|
gisserver/output/xmlschema.py
|
|
32
43
|
gisserver/parsers/__init__.py
|
|
33
|
-
gisserver/parsers/
|
|
34
|
-
gisserver/parsers/
|
|
44
|
+
gisserver/parsers/ast.py
|
|
45
|
+
gisserver/parsers/query.py
|
|
35
46
|
gisserver/parsers/values.py
|
|
47
|
+
gisserver/parsers/xml.py
|
|
36
48
|
gisserver/parsers/fes20/__init__.py
|
|
37
49
|
gisserver/parsers/fes20/expressions.py
|
|
38
50
|
gisserver/parsers/fes20/filters.py
|
|
39
|
-
gisserver/parsers/fes20/functions.py
|
|
40
51
|
gisserver/parsers/fes20/identifiers.py
|
|
52
|
+
gisserver/parsers/fes20/lookups.py
|
|
41
53
|
gisserver/parsers/fes20/operators.py
|
|
42
|
-
gisserver/parsers/fes20/query.py
|
|
43
54
|
gisserver/parsers/fes20/sorting.py
|
|
44
55
|
gisserver/parsers/gml/__init__.py
|
|
45
56
|
gisserver/parsers/gml/base.py
|
|
46
57
|
gisserver/parsers/gml/geometries.py
|
|
47
|
-
gisserver/
|
|
48
|
-
gisserver/
|
|
49
|
-
gisserver/
|
|
50
|
-
gisserver/
|
|
51
|
-
gisserver/
|
|
58
|
+
gisserver/parsers/ows/__init__.py
|
|
59
|
+
gisserver/parsers/ows/kvp.py
|
|
60
|
+
gisserver/parsers/ows/requests.py
|
|
61
|
+
gisserver/parsers/wfs20/__init__.py
|
|
62
|
+
gisserver/parsers/wfs20/adhoc.py
|
|
63
|
+
gisserver/parsers/wfs20/base.py
|
|
64
|
+
gisserver/parsers/wfs20/projection.py
|
|
65
|
+
gisserver/parsers/wfs20/requests.py
|
|
66
|
+
gisserver/parsers/wfs20/stored.py
|
|
52
67
|
gisserver/static/gisserver/index.css
|
|
68
|
+
gisserver/templates/gisserver/base.html
|
|
53
69
|
gisserver/templates/gisserver/index.html
|
|
54
70
|
gisserver/templates/gisserver/service_description.html
|
|
55
71
|
gisserver/templates/gisserver/wfs/feature_field.html
|
|
56
72
|
gisserver/templates/gisserver/wfs/feature_type.html
|
|
57
|
-
gisserver/templates/gisserver/wfs/2.0.0/describe_stored_queries.xml
|
|
58
73
|
gisserver/templates/gisserver/wfs/2.0.0/get_capabilities.xml
|
|
59
|
-
gisserver/templates/gisserver/wfs/2.0.0/list_stored_queries.xml
|
|
60
74
|
gisserver/templatetags/__init__.py
|
|
61
75
|
gisserver/templatetags/gisserver_tags.py
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "2.1" # follows PEP440
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
"""Compatability imports"""
|
|
2
|
+
|
|
3
|
+
import sys
|
|
4
|
+
|
|
5
|
+
import django
|
|
6
|
+
from django.conf import settings
|
|
7
|
+
from django.db import models
|
|
8
|
+
|
|
9
|
+
if (
|
|
10
|
+
"django.contrib.postgres" in settings.INSTALLED_APPS
|
|
11
|
+
or "django.contrib.postgres" in sys.modules
|
|
12
|
+
):
|
|
13
|
+
from django.contrib.postgres.fields import ArrayField
|
|
14
|
+
else:
|
|
15
|
+
ArrayField = None
|
|
16
|
+
|
|
17
|
+
GeneratedField = models.GeneratedField if django.VERSION >= (5, 0) else None
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
__all__ = (
|
|
21
|
+
"ArrayField",
|
|
22
|
+
"GeneratedField",
|
|
23
|
+
)
|
|
@@ -28,6 +28,13 @@ GISSERVER_SUPPORTED_CRS_ONLY = getattr(settings, "GISSERVER_SUPPORTED_CRS_ONLY",
|
|
|
28
28
|
# 0 = No counting, 1 = all pages, 2 = only for the first page.
|
|
29
29
|
GISSERVER_COUNT_NUMBER_MATCHED = getattr(settings, "GISSERVER_COUNT_NUMBER_MATCHED", 1)
|
|
30
30
|
|
|
31
|
+
# -- output rendering
|
|
32
|
+
|
|
33
|
+
GISSERVER_EXTRA_OUTPUT_FORMATS = getattr(settings, "GISSERVER_EXTRA_OUTPUT_FORMATS", {})
|
|
34
|
+
GISSERVER_GET_FEATURE_OUTPUT_FORMATS = getattr(
|
|
35
|
+
settings, "GISSERVER_GET_FEATURE_OUTPUT_FORMATS", {}
|
|
36
|
+
)
|
|
37
|
+
|
|
31
38
|
# -- max page size
|
|
32
39
|
|
|
33
40
|
# Allow tuning the page size without having to override code.
|