update main file
This commit is contained in:
parent
1b7f6ab5ea
commit
b4fa7e123b
130
main.py
130
main.py
|
|
@ -10,7 +10,9 @@ from qgis.core import (
|
||||||
QgsVectorLayerExporter,
|
QgsVectorLayerExporter,
|
||||||
QgsDataSourceUri,
|
QgsDataSourceUri,
|
||||||
QgsProviderRegistry,
|
QgsProviderRegistry,
|
||||||
QgsCoordinateReferenceSystem
|
QgsCoordinateReferenceSystem,
|
||||||
|
QgsWkbTypes,
|
||||||
|
QgsGeometry
|
||||||
)
|
)
|
||||||
from qgis.PyQt.QtCore import QByteArray
|
from qgis.PyQt.QtCore import QByteArray
|
||||||
from config import HOST,PORT,DB,USER,PWD,SCHEMA,GEOM_COL
|
from config import HOST,PORT,DB,USER,PWD,SCHEMA,GEOM_COL
|
||||||
|
|
@ -43,17 +45,38 @@ def clean_table(table_name: str):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
from pydantic import BaseModel
|
||||||
|
|
||||||
@app.post("/process/{table_name}")
|
class ProcessRequest(BaseModel):
|
||||||
def process_table(table_name: str, background: BackgroundTasks):
|
table_name: str
|
||||||
job_id = uuid4().hex
|
job_id: str
|
||||||
background.add_task(run_clean_table, table_name, job_id)
|
|
||||||
|
@app.post("/process")
|
||||||
|
def process_table(
|
||||||
|
payload: ProcessRequest,
|
||||||
|
background: BackgroundTasks
|
||||||
|
):
|
||||||
|
background.add_task(
|
||||||
|
run_clean_table,
|
||||||
|
payload.table_name,
|
||||||
|
payload.job_id
|
||||||
|
)
|
||||||
return {
|
return {
|
||||||
"status": "ACCEPTED",
|
"status": "ACCEPTED",
|
||||||
"job_id": job_id,
|
"job_id": payload.job_id,
|
||||||
"table": table_name
|
"table": payload.table_name
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# @app.post("/process/{table_name}")
|
||||||
|
# def process_table(table_name: str, background: BackgroundTasks):
|
||||||
|
# job_id = uuid4().hex
|
||||||
|
# background.add_task(run_clean_table, table_name, job_id)
|
||||||
|
# return {
|
||||||
|
# "status": "ACCEPTED",
|
||||||
|
# "job_id": job_id,
|
||||||
|
# "table": table_name
|
||||||
|
# }
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def run_clean_table(table_name: str, job_id: str):
|
def run_clean_table(table_name: str, job_id: str):
|
||||||
|
|
@ -80,7 +103,7 @@ def run_clean_table(table_name: str, job_id: str):
|
||||||
}
|
}
|
||||||
|
|
||||||
requests.post(
|
requests.post(
|
||||||
"http://localhost:8000/jobs/callback",
|
"http://localhost:8000/dataset/jobs/callback",
|
||||||
json=callback_payload
|
json=callback_payload
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -102,6 +125,81 @@ def to_python(v):
|
||||||
# Fallback
|
# Fallback
|
||||||
return v
|
return v
|
||||||
|
|
||||||
|
|
||||||
|
# def get_postgis_geom_type(layer):
|
||||||
|
# for f in layer.getFeatures():
|
||||||
|
# g = f.geometry()
|
||||||
|
# if g.isMultipart():
|
||||||
|
# return QgsWkbTypes.displayString(g.wkbType()).upper()
|
||||||
|
# else:
|
||||||
|
# base = QgsWkbTypes.displayString(g.wkbType()).upper()
|
||||||
|
# if "POINT" in base:
|
||||||
|
# return "MULTIPOINT"
|
||||||
|
# if "LINESTRING" in base:
|
||||||
|
# return "MULTILINESTRING"
|
||||||
|
# if "POLYGON" in base:
|
||||||
|
# return "MULTIPOLYGON"
|
||||||
|
# return "GEOMETRY"
|
||||||
|
|
||||||
|
def get_postgis_geom_type(layer):
|
||||||
|
has_z = False
|
||||||
|
has_m = False
|
||||||
|
base_type = None # polygon / linestring / point
|
||||||
|
is_multi = False
|
||||||
|
|
||||||
|
for f in layer.getFeatures():
|
||||||
|
g = f.geometry()
|
||||||
|
if g.isEmpty():
|
||||||
|
continue
|
||||||
|
|
||||||
|
wkb = g.wkbType()
|
||||||
|
|
||||||
|
# Detect Z & M
|
||||||
|
if QgsWkbTypes.hasZ(wkb):
|
||||||
|
has_z = True
|
||||||
|
if QgsWkbTypes.hasM(wkb):
|
||||||
|
has_m = True
|
||||||
|
|
||||||
|
# Detect MULTI
|
||||||
|
if QgsWkbTypes.isMultiType(wkb):
|
||||||
|
is_multi = True
|
||||||
|
|
||||||
|
# Detect base type (polygon / line / point)
|
||||||
|
geom_type = QgsWkbTypes.geometryType(wkb)
|
||||||
|
base_type = geom_type # polygon=2, line=1, point=0
|
||||||
|
|
||||||
|
if base_type is None:
|
||||||
|
return "GEOMETRY"
|
||||||
|
|
||||||
|
# Convert base_type to PostGIS string
|
||||||
|
if base_type == QgsWkbTypes.PointGeometry:
|
||||||
|
base = "POINT"
|
||||||
|
elif base_type == QgsWkbTypes.LineGeometry:
|
||||||
|
base = "LINESTRING"
|
||||||
|
elif base_type == QgsWkbTypes.PolygonGeometry:
|
||||||
|
base = "POLYGON"
|
||||||
|
else:
|
||||||
|
base = "GEOMETRY"
|
||||||
|
|
||||||
|
# Force MULTI
|
||||||
|
if base != "GEOMETRY":
|
||||||
|
base = "MULTI" + base
|
||||||
|
|
||||||
|
# Add dimensionality
|
||||||
|
if has_z and has_m:
|
||||||
|
base += "ZM"
|
||||||
|
elif has_z:
|
||||||
|
base += "Z"
|
||||||
|
elif has_m:
|
||||||
|
base += "M"
|
||||||
|
|
||||||
|
return base
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def save_to_postgis(layer, table_name):
|
def save_to_postgis(layer, table_name):
|
||||||
host = HOST
|
host = HOST
|
||||||
port = PORT
|
port = PORT
|
||||||
|
|
@ -126,14 +224,13 @@ def save_to_postgis(layer, table_name):
|
||||||
|
|
||||||
# DROP TABLE
|
# DROP TABLE
|
||||||
cur.execute(f'DROP TABLE IF EXISTS "{schema}"."{table_name}" CASCADE')
|
cur.execute(f'DROP TABLE IF EXISTS "{schema}"."{table_name}" CASCADE')
|
||||||
|
print(f'Drop table {table_name}')
|
||||||
|
|
||||||
# CREATE TABLE
|
|
||||||
field_defs = []
|
field_defs = []
|
||||||
for f in fields:
|
for f in fields:
|
||||||
if f.name() == geom_col:
|
if f.name() == geom_col:
|
||||||
continue
|
continue
|
||||||
|
|
||||||
# type mapping
|
|
||||||
t = f.typeName().lower()
|
t = f.typeName().lower()
|
||||||
if "int" in t:
|
if "int" in t:
|
||||||
pg_type = "INTEGER"
|
pg_type = "INTEGER"
|
||||||
|
|
@ -145,12 +242,15 @@ def save_to_postgis(layer, table_name):
|
||||||
col = f.name().replace(" ", "_")
|
col = f.name().replace(" ", "_")
|
||||||
field_defs.append(f'"{col}" {pg_type}')
|
field_defs.append(f'"{col}" {pg_type}')
|
||||||
|
|
||||||
# geometry column
|
# AUTODETECT 2D/3D geometry
|
||||||
field_defs.append(f'"{geom_col}" geometry(MultiPolygon,{srid})')
|
pg_geom_type = get_postgis_geom_type(layer)
|
||||||
|
print("get type")
|
||||||
|
field_defs.append(f'"{geom_col}" geometry({pg_geom_type},{srid})')
|
||||||
create_sql = f'CREATE TABLE "{schema}"."{table_name}" ({",".join(field_defs)});'
|
create_sql = f'CREATE TABLE "{schema}"."{table_name}" ({",".join(field_defs)});'
|
||||||
cur.execute(create_sql)
|
cur.execute(create_sql)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
# Prepare INSERT
|
# Prepare INSERT
|
||||||
attribute_columns = [
|
attribute_columns = [
|
||||||
f'"{f.name().replace(" ", "_")}"'
|
f'"{f.name().replace(" ", "_")}"'
|
||||||
|
|
@ -177,6 +277,8 @@ def save_to_postgis(layer, table_name):
|
||||||
|
|
||||||
geom = feat.geometry()
|
geom = feat.geometry()
|
||||||
wkb_bytes = geom.asWkb()
|
wkb_bytes = geom.asWkb()
|
||||||
|
# geom_2d = QgsGeometry.fromWkt(geom.asWkt())
|
||||||
|
# wkb_bytes = geom_2d.asWkb()
|
||||||
if isinstance(wkb_bytes, QByteArray):
|
if isinstance(wkb_bytes, QByteArray):
|
||||||
wkb_bytes = bytes(wkb_bytes)
|
wkb_bytes = bytes(wkb_bytes)
|
||||||
|
|
||||||
|
|
@ -190,5 +292,3 @@ def save_to_postgis(layer, table_name):
|
||||||
|
|
||||||
print(f"[DB] Inserted features: {count}")
|
print(f"[DB] Inserted features: {count}")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user