Compare commits
8
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3b47e41bbe | ||
|
|
1a9595598e | ||
|
|
4bbdb96bcd | ||
|
|
aa6166e652 | ||
|
|
12b52d0468 | ||
|
|
cbd7b84889 | ||
|
|
28cfc75121 | ||
|
|
cee02ae935 |
@@ -1,4 +1,10 @@
|
|||||||
---
|
---
|
||||||
|
Version 26.5.3-unstable:
|
||||||
|
---
|
||||||
|
Version 26.5.2-unstable:
|
||||||
|
---
|
||||||
|
Version 26.5.1-unstable:
|
||||||
|
---
|
||||||
Version 26.4.6-unstable:
|
Version 26.4.6-unstable:
|
||||||
---
|
---
|
||||||
Version 26.4.5-unstable:
|
Version 26.4.5-unstable:
|
||||||
|
|||||||
@@ -146,6 +146,9 @@ def _wfs_get_gml(url: str, typename: str, extra_params: dict) -> Optional[bytes]
|
|||||||
GET-Requests mit ``BBOX=``-KVP-Parameter oder ResourceId-``FILTER`` (nur
|
GET-Requests mit ``BBOX=``-KVP-Parameter oder ResourceId-``FILTER`` (nur
|
||||||
``xmlns:fes``, kein GML) werden dagegen akzeptiert.
|
``xmlns:fes``, kein GML) werden dagegen akzeptiert.
|
||||||
|
|
||||||
|
**Proxy-Unterstützung:** Verwendet ``QgsBlockingNetworkRequest``, das automatisch
|
||||||
|
die in QGIS konfigurierten Proxy-Einstellungen berücksichtigt.
|
||||||
|
|
||||||
Parameters
|
Parameters
|
||||||
----------
|
----------
|
||||||
url :
|
url :
|
||||||
@@ -161,10 +164,10 @@ def _wfs_get_gml(url: str, typename: str, extra_params: dict) -> Optional[bytes]
|
|||||||
bytes | None
|
bytes | None
|
||||||
Rohe GML-Antwort oder ``None`` bei Fehler.
|
Rohe GML-Antwort oder ``None`` bei Fehler.
|
||||||
"""
|
"""
|
||||||
import urllib.request
|
|
||||||
import urllib.parse
|
import urllib.parse
|
||||||
import urllib.error
|
from qgis.core import QgsMessageLog, Qgis, QgsBlockingNetworkRequest
|
||||||
from qgis.core import QgsMessageLog, Qgis
|
from qgis.PyQt.QtNetwork import QNetworkRequest
|
||||||
|
from qgis.PyQt.QtCore import QUrl
|
||||||
|
|
||||||
params = {
|
params = {
|
||||||
'SERVICE': 'WFS',
|
'SERVICE': 'WFS',
|
||||||
@@ -177,26 +180,34 @@ def _wfs_get_gml(url: str, typename: str, extra_params: dict) -> Optional[bytes]
|
|||||||
|
|
||||||
full_url = url + '?' + urllib.parse.urlencode(params)
|
full_url = url + '?' + urllib.parse.urlencode(params)
|
||||||
|
|
||||||
try:
|
req = QNetworkRequest(QUrl(full_url))
|
||||||
with urllib.request.urlopen(full_url, timeout=120) as resp:
|
req.setTransferTimeout(120_000)
|
||||||
gml_bytes = resp.read()
|
blocker = QgsBlockingNetworkRequest()
|
||||||
except urllib.error.HTTPError as exc:
|
err = blocker.get(req)
|
||||||
body_preview = exc.read(200).decode('utf-8', errors='replace')
|
|
||||||
|
if err != QgsBlockingNetworkRequest.ErrorCode.NoError:
|
||||||
|
msg = blocker.errorMessage()
|
||||||
QgsMessageLog.logMessage(
|
QgsMessageLog.logMessage(
|
||||||
f"WFS GET HTTP {exc.code} ({typename}): {exc.reason}\n"
|
f"WFS GET fehlgeschlagen ({typename}): {msg}\nURL: {full_url[:300]}",
|
||||||
|
"sn_verfahrensgebiet",
|
||||||
|
Qgis.MessageLevel.Critical,
|
||||||
|
)
|
||||||
|
warning("WFS GET", f"Netzwerk-/Proxy-Fehler: {msg}", duration=10)
|
||||||
|
return None
|
||||||
|
|
||||||
|
reply = blocker.reply()
|
||||||
|
http_status = reply.attribute(QNetworkRequest.Attribute.HttpStatusCodeAttribute)
|
||||||
|
gml_bytes = bytes(reply.content())
|
||||||
|
|
||||||
|
if http_status is not None and http_status >= 400:
|
||||||
|
body_preview = gml_bytes[:200].decode('utf-8', errors='replace')
|
||||||
|
QgsMessageLog.logMessage(
|
||||||
|
f"WFS GET HTTP {http_status} ({typename})\n"
|
||||||
f"URL: {full_url[:300]}\nAntwort: {body_preview}",
|
f"URL: {full_url[:300]}\nAntwort: {body_preview}",
|
||||||
"sn_verfahrensgebiet",
|
"sn_verfahrensgebiet",
|
||||||
Qgis.MessageLevel.Critical,
|
Qgis.MessageLevel.Critical,
|
||||||
)
|
)
|
||||||
warning("WFS GET", f"HTTP {exc.code}: {exc.reason}", duration=10)
|
warning("WFS GET", f"HTTP {http_status}", duration=10)
|
||||||
return None
|
|
||||||
except Exception as exc:
|
|
||||||
QgsMessageLog.logMessage(
|
|
||||||
f"WFS GET fehlgeschlagen ({typename}): {exc}\nURL: {full_url[:300]}",
|
|
||||||
"sn_verfahrensgebiet",
|
|
||||||
Qgis.MessageLevel.Critical,
|
|
||||||
)
|
|
||||||
warning("WFS GET", f"Netzwerkfehler: {exc}", duration=10)
|
|
||||||
return None
|
return None
|
||||||
|
|
||||||
if not gml_bytes:
|
if not gml_bytes:
|
||||||
@@ -477,11 +488,7 @@ def _lade_grenzpunkte_als_dict(
|
|||||||
)
|
)
|
||||||
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, GRENZPUNKT_TYPENAME, {'FILTER': filter_xml})
|
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, GRENZPUNKT_TYPENAME, {'FILTER': filter_xml})
|
||||||
if not _gml_bytes:
|
if not _gml_bytes:
|
||||||
warning(
|
return {}, []
|
||||||
"Grenzpunkte (Diagnose)",
|
|
||||||
f"Batch {i + 1}/{anzahl_batches}: GET-Anfrage fehlgeschlagen – Batch wird übersprungen.",
|
|
||||||
duration=4,
|
|
||||||
)
|
|
||||||
else:
|
else:
|
||||||
tmp = _parse_alkis_gml_memory_layer(_gml_bytes, "AX_Grenzpunkt", "_TmpGP", geom_prop=None)
|
tmp = _parse_alkis_gml_memory_layer(_gml_bytes, "AX_Grenzpunkt", "_TmpGP", geom_prop=None)
|
||||||
if not tmp:
|
if not tmp:
|
||||||
@@ -704,9 +711,12 @@ def _lade_gemarkung_extents_mit_puffer(
|
|||||||
return extents
|
return extents
|
||||||
|
|
||||||
|
|
||||||
def _wfs_hits_count(url: str, typename: str, extra_params: dict) -> int:
|
def _wfs_hits_count(url: str, typename: str, extra_params: dict) -> Optional[int]:
|
||||||
"""Fragt die Anzahl der Features per ``resultType=hits`` ab.
|
"""Fragt die Anzahl der Features per ``resultType=hits`` ab.
|
||||||
|
|
||||||
|
**Proxy-Unterstützung:** Verwendet ``QgsBlockingNetworkRequest``, das automatisch
|
||||||
|
die in QGIS konfigurierten Proxy-Einstellungen berücksichtigt.
|
||||||
|
|
||||||
Parameters
|
Parameters
|
||||||
----------
|
----------
|
||||||
url :
|
url :
|
||||||
@@ -714,17 +724,21 @@ def _wfs_hits_count(url: str, typename: str, extra_params: dict) -> int:
|
|||||||
typename :
|
typename :
|
||||||
Vollqualifizierter Feature-Typ.
|
Vollqualifizierter Feature-Typ.
|
||||||
extra_params :
|
extra_params :
|
||||||
Zus\u00e4tzliche KVP-Parameter (z.B. ``{'BBOX': '...'}``).
|
Zusätzliche KVP-Parameter (z.B. ``{'BBOX': '...'}``).
|
||||||
|
|
||||||
Returns
|
Returns
|
||||||
-------
|
-------
|
||||||
int
|
Optional[int]
|
||||||
Anzahl der Features oder ``-1`` wenn nicht ermittelbar.
|
Anzahl der Features,
|
||||||
|
``-1`` wenn der Server antwortete aber ``numberMatched='unknown'`` lieferte
|
||||||
|
(gültiger WFS-Fallback, kein Fehler), oder
|
||||||
|
``None`` bei Netzwerk-/Proxy-Fehler (Aufrufer soll abbrechen).
|
||||||
"""
|
"""
|
||||||
import urllib.request
|
|
||||||
import urllib.parse
|
import urllib.parse
|
||||||
import urllib.error
|
|
||||||
import xml.etree.ElementTree as ET
|
import xml.etree.ElementTree as ET
|
||||||
|
from qgis.core import QgsMessageLog, Qgis, QgsBlockingNetworkRequest
|
||||||
|
from qgis.PyQt.QtNetwork import QNetworkRequest
|
||||||
|
from qgis.PyQt.QtCore import QUrl
|
||||||
|
|
||||||
params = {
|
params = {
|
||||||
'SERVICE': 'WFS',
|
'SERVICE': 'WFS',
|
||||||
@@ -736,11 +750,22 @@ def _wfs_hits_count(url: str, typename: str, extra_params: dict) -> int:
|
|||||||
params.update(extra_params)
|
params.update(extra_params)
|
||||||
|
|
||||||
full_url = url + '?' + urllib.parse.urlencode(params)
|
full_url = url + '?' + urllib.parse.urlencode(params)
|
||||||
try:
|
|
||||||
with urllib.request.urlopen(full_url, timeout=30) as resp:
|
req = QNetworkRequest(QUrl(full_url))
|
||||||
gml_bytes = resp.read()
|
req.setTransferTimeout(30_000)
|
||||||
except Exception:
|
blocker = QgsBlockingNetworkRequest()
|
||||||
return -1
|
err = blocker.get(req)
|
||||||
|
|
||||||
|
if err != QgsBlockingNetworkRequest.ErrorCode.NoError:
|
||||||
|
msg = blocker.errorMessage()
|
||||||
|
QgsMessageLog.logMessage(
|
||||||
|
f"WFS Hits-Abfrage fehlgeschlagen ({typename}): {msg}\nURL: {full_url[:300]}",
|
||||||
|
"sn_verfahrensgebiet",
|
||||||
|
Qgis.MessageLevel.Critical,
|
||||||
|
)
|
||||||
|
return None
|
||||||
|
|
||||||
|
gml_bytes = bytes(blocker.reply().content())
|
||||||
|
|
||||||
try:
|
try:
|
||||||
root = ET.fromstring(gml_bytes)
|
root = ET.fromstring(gml_bytes)
|
||||||
@@ -796,12 +821,7 @@ def _lade_punktort_ta_batches_per_gemarkung(
|
|||||||
)
|
)
|
||||||
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': _punktort_ta_bbox_param(bbox)})
|
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': _punktort_ta_bbox_param(bbox)})
|
||||||
if not _gml_bytes:
|
if not _gml_bytes:
|
||||||
warning(
|
return None
|
||||||
"Grenzpunkte (Diagnose)",
|
|
||||||
f"Gemarkung {_gemarkungsnummer}: GET-Anfrage fehlgeschlagen – wird übersprungen.",
|
|
||||||
duration=4,
|
|
||||||
)
|
|
||||||
continue
|
|
||||||
tmp = _parse_alkis_gml_memory_layer(_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True)
|
tmp = _parse_alkis_gml_memory_layer(_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True)
|
||||||
if not tmp:
|
if not tmp:
|
||||||
warning(
|
warning(
|
||||||
@@ -997,6 +1017,8 @@ def lade_punktort_ta(
|
|||||||
|
|
||||||
bbox_param = _punktort_ta_bbox_param(bbox)
|
bbox_param = _punktort_ta_bbox_param(bbox)
|
||||||
n_hits = _wfs_hits_count(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': bbox_param})
|
n_hits = _wfs_hits_count(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': bbox_param})
|
||||||
|
if n_hits is None:
|
||||||
|
return None
|
||||||
n_batches = max(1, math.ceil(n_hits / _BBOX_BATCH)) if n_hits > 0 else 1
|
n_batches = max(1, math.ceil(n_hits / _BBOX_BATCH)) if n_hits > 0 else 1
|
||||||
|
|
||||||
info(
|
info(
|
||||||
@@ -1022,13 +1044,7 @@ def lade_punktort_ta(
|
|||||||
|
|
||||||
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, extra)
|
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, extra)
|
||||||
if not _gml_bytes:
|
if not _gml_bytes:
|
||||||
warning(
|
return None
|
||||||
"Grenzpunkte (Diagnose)",
|
|
||||||
f"Gemarkung {gemarkungsnummer} Batch {b_idx + 1}: "
|
|
||||||
f"GET-Anfrage fehlgeschlagen – übersprungen.",
|
|
||||||
duration=4,
|
|
||||||
)
|
|
||||||
continue
|
|
||||||
|
|
||||||
tmp = _parse_alkis_gml_memory_layer(
|
tmp = _parse_alkis_gml_memory_layer(
|
||||||
_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True
|
_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True
|
||||||
@@ -1343,6 +1359,8 @@ def grenzpunkte_gemarkungsweise(
|
|||||||
for gemarkungsnummer, bbox in extents.items():
|
for gemarkungsnummer, bbox in extents.items():
|
||||||
bbox_param = _punktort_ta_bbox_param(bbox)
|
bbox_param = _punktort_ta_bbox_param(bbox)
|
||||||
n_hits = _wfs_hits_count(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': bbox_param})
|
n_hits = _wfs_hits_count(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, {'BBOX': bbox_param})
|
||||||
|
if n_hits is None:
|
||||||
|
return None
|
||||||
hits_pro_gemarkung[gemarkungsnummer] = n_hits
|
hits_pro_gemarkung[gemarkungsnummer] = n_hits
|
||||||
batches = max(1, math.ceil(n_hits / _BBOX_BATCH)) if n_hits > 0 else 1
|
batches = max(1, math.ceil(n_hits / _BBOX_BATCH)) if n_hits > 0 else 1
|
||||||
n_pta_batches_gesamt += batches
|
n_pta_batches_gesamt += batches
|
||||||
@@ -1413,13 +1431,7 @@ def grenzpunkte_gemarkungsweise(
|
|||||||
|
|
||||||
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, extra)
|
_gml_bytes = _wfs_get_gml(ALKIS_SF_URL, PUNKTORT_TA_TYPENAME, extra)
|
||||||
if not _gml_bytes:
|
if not _gml_bytes:
|
||||||
warning(
|
return None
|
||||||
"Grenzpunkte (Diagnose)",
|
|
||||||
f"Gemarkung {gemarkungsnummer} Batch {b_idx + 1}: "
|
|
||||||
f"GET-Anfrage fehlgeschlagen – Batch wird übersprungen.",
|
|
||||||
duration=6,
|
|
||||||
)
|
|
||||||
continue
|
|
||||||
|
|
||||||
tmp = _parse_alkis_gml_memory_layer(
|
tmp = _parse_alkis_gml_memory_layer(
|
||||||
_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True
|
_gml_bytes, "AX_PunktortTA", "_TmpPTA", geom_prop="position", extract_qualitaet=True
|
||||||
|
|||||||
@@ -61,7 +61,7 @@ KATEGORIE_GROSS = ">3cm"
|
|||||||
KATEGORIE_UNBEKANNT = "unbekannt"
|
KATEGORIE_UNBEKANNT = "unbekannt"
|
||||||
|
|
||||||
#: Maximaler Abstand (m) eines Punktes vom Umring, um als „auf dem Umring" zu gelten.
|
#: Maximaler Abstand (m) eines Punktes vom Umring, um als „auf dem Umring" zu gelten.
|
||||||
UMRING_TOLERANZ_M: float = 0.1
|
UMRING_TOLERANZ_M: float = 0.01
|
||||||
|
|
||||||
#: Grenzwert für ``qualitaetsangaben_ax_dqpunktort_genauigkeitsstufe`` (3-cm-Schwelle).
|
#: Grenzwert für ``qualitaetsangaben_ax_dqpunktort_genauigkeitsstufe`` (3-cm-Schwelle).
|
||||||
GENAUIGKEIT_GRENZWERT: int = 2100
|
GENAUIGKEIT_GRENZWERT: int = 2100
|
||||||
|
|||||||
@@ -488,6 +488,17 @@ def verfahrensgebiet_alkis_komplett(
|
|||||||
if punktort_layer is None:
|
if punktort_layer is None:
|
||||||
detail_progress.close()
|
detail_progress.close()
|
||||||
abgeschlossen = True
|
abgeschlossen = True
|
||||||
|
if not detail_progress.is_canceled():
|
||||||
|
QMessageBox.critical(
|
||||||
|
tab_widget,
|
||||||
|
"WFS-Fehler",
|
||||||
|
"Die Grenzpunktdaten (PunktortTA) konnten nicht geladen werden.\n\n"
|
||||||
|
"Mögliche Ursache: Netzwerk- oder Proxy-Fehler.\n"
|
||||||
|
"Bitte prüfen Sie die QGIS-Proxy-Einstellungen "
|
||||||
|
"(Einstellungen -> Optionen -> Netzwerk) und den Log-Eintrag "
|
||||||
|
"unter Ansicht -> Bedienfelder -> Protokollnachrichten "
|
||||||
|
"(Kategorie 'sn_verfahrensgebiet').",
|
||||||
|
)
|
||||||
return enriched_layer, flst_layer, alkis_vg_layer, vg_status
|
return enriched_layer, flst_layer, alkis_vg_layer, vg_status
|
||||||
|
|
||||||
# Schritte 2…Ende: Knickpunktprüfung
|
# Schritte 2…Ende: Knickpunktprüfung
|
||||||
|
|||||||
+1
-1
@@ -1,5 +1,5 @@
|
|||||||
[general]
|
[general]
|
||||||
version=26.4.6-unstable
|
version=26.5.3-unstable
|
||||||
name=LNO Sachsen | Verfahrensgebiet
|
name=LNO Sachsen | Verfahrensgebiet
|
||||||
description=Plugin zum Erzeugen eines Objektes "Verfahrensgebiet"
|
description=Plugin zum Erzeugen eines Objektes "Verfahrensgebiet"
|
||||||
author=Daniel Helbig, Michael Otto
|
author=Daniel Helbig, Michael Otto
|
||||||
|
|||||||
+12
-3
@@ -487,10 +487,19 @@ class WorkingTab(QWidget):
|
|||||||
if joined_layer and joined_layer.isValid():
|
if joined_layer and joined_layer.isValid():
|
||||||
iface.mapCanvas().refresh()
|
iface.mapCanvas().refresh()
|
||||||
self.setze_haken(self.haken_grenz, True)
|
self.setze_haken(self.haken_grenz, True)
|
||||||
success(
|
QMessageBox.information(
|
||||||
"Grenzpunkte",
|
self,
|
||||||
|
"Grenzpunkte geladen",
|
||||||
f"Grenzpunkte erfolgreich geladen ({joined_layer.featureCount()} Objekte).",
|
f"Grenzpunkte erfolgreich geladen ({joined_layer.featureCount()} Objekte).",
|
||||||
duration=5,
|
)
|
||||||
|
elif joined_layer is None:
|
||||||
|
error(
|
||||||
|
"Grenzpunkte",
|
||||||
|
"Laden fehlgeschlagen – WFS- oder Netzwerkfehler. "
|
||||||
|
"Details unter Ansicht -> Bedienfelder -> Protokollnachrichten "
|
||||||
|
"(Kategorie 'sn_verfahrensgebiet'). "
|
||||||
|
"Bitte prüfen Sie ggf. die Proxy-Einstellungen.",
|
||||||
|
duration=0,
|
||||||
)
|
)
|
||||||
finally:
|
finally:
|
||||||
self._set_busy(self.btn_grenz_alkis, False, "Grenzpunkte aus ALKIS laden")
|
self._set_busy(self.btn_grenz_alkis, False, "Grenzpunkte aus ALKIS laden")
|
||||||
|
|||||||
Reference in New Issue
Block a user