postgis mvt矢量切片 django drf mapboxgl

postgis mvt矢量切片 django drf mapboxgl

目录

0.前提

1.sql代码

[2.django drf后端服务代码](#2.django drf后端服务代码)

3.具体的应用(整体代码)

4.参考


0.前提

[1] 静态的矢量切片可以采用 tippecanoe 生成,nginx代理,这种数据是不更新的;

[2] 动态的矢量切片,一般采用postgis生成。基本上矢量切片80%的厂商都采用postgis,确实好用!不谈商业的。

[3] postgis矢量切片使用到的函数:ST_AsMVTST_AsMVTGeomST_TileEnvelopeST_TransformST_IntersectsST_SRID。(点击查看每个函数的介绍,都是官网文档,很详细)

[4] postgis api参考文档官网:Official Manual | PostGIS,有postgis3.0版本以上的,点击html,点击8. PostGIS Reference,即可查看矢量处理的函数。

[5] 矢量切片mvt,需要坐标为EPSG:3857,如果想用mvt这种开源的标准,就使用ST_Transform统一转换成这个坐标。然后入库的数据都设置成EPSG:4326。

1.sql代码

[1] 获取表的字段名称:(zzz替换成传入的表名)【PS:不建议动态查询将1-2结合,不好】

select column_name from information_schema.columns where table_name='zzz';

[2] 动态获取矢量切片: (1.0.0)替换成传入的z,x,y参数,zzz替换成传入的表名,geom替换成geom几何对应的字段名称。

sql 复制代码
with mvtgeom as (
select ST_AsMVTGeom(ST_Transform(geom, 3857), ST_TileEnvelope(1,0,0)) as geom, gid 
    from 
    zzz, 
    (select ST_SRID(geom) as srid from zzz where geom is not null limit 1) a
    where
      ST_Intersects(geom, ST_Transform(ST_TileEnvelope(1,0,0), srid))
)
select ST_AsMVT(mvtgeom.*, 'zzz', 4096, 'geom') as mvt from mvtgeom;

2.django drf后端服务代码

基于APIView重写get函数,再注册到urls.py中

前端访问 ip/`table_name`/`z`/`x`/`y`,eg:http://127.0.0.1:8080/getmap/zzz/2/1/1 这样就可以接收矢量切片mvt了。

python 复制代码
from django.db import connection
from rest_framework.views import APIView
from rest_framework.response import Response

class MapView(APIView):

    def get(self, request, table, z, x, y):
        
        print(table, z, x, y,)
        table_name = table  #'zzz'
        
        # 将数据库的数据导出为geojson(建议不要太大,太大用 wms服务吧、或者mvt矢量切片)
        # sql = f"""select json_build_object('type', 'FeatureCollection', 'name', '{table_name}', 'features', json_agg(ST_ASGeoJSON(t.*)::json)) from {table_name} AS t """
        
        # 获取表的字段名称 列表
        # sql = f"""select column_name from information_schema.columns where table_name='{table_name}'"""  # where后面是string 不应被转成对象变量
        # 获取表的字段名称 字符串
        # sql = f"""select array_to_string(array(select column_name from information_schema.columns where table_name='{table_name}' and column_name != 'geom'), ',');"""
        # 动态矢量切片mvt   gid字段也可替换成前端传入的字段
        geom_name = 'geom'
        sql = f"""with mvtgeom as (
                select ST_AsMVTGeom(ST_Transform({geom_name}, 3857), ST_TileEnvelope({z},{x},{y})) as geom, gid
                from 
                {table_name}, 
                (select ST_SRID({geom_name}) as srid from {table_name} where {geom_name} is not null limit 1) a
                where
                ST_Intersects({geom_name}, ST_Transform(ST_TileEnvelope({z},{x},{y}), srid))
            )
            select ST_AsMVT(mvtgeom.*, '{table_name}', 4096, 'geom') as mvt from mvtgeom;"""
                
        print(sql)
        with connection.cursor() as cursor:
            cursor.execute(sql)
            results = cursor.fetchall()

        return Response(results)

3.具体的应用(整体代码)

TODO

[1] shp、geojson前端上传,后端对数据进行校验(校验坐标系-强制4326、等),然后再采用后端代码将shp、geojson导入postgres数据库中。

[2] jwt、permission等

[3] 前端如何加jwt等信息 请求数据

4.参考

[1] 参考了这个项目的sql代码(比国内很多博客写的强太多,如果不考虑权限等,就是部署个后端、数据库,手动导入shp数据,那么直接用这个开源项目即可,前端采用mapboxgl类似的开源库加载,api访问部署后的localhost:3000即可查看 ):https://github.com/tobinbradley/dirt-simple-postgis-http-api/blob/master/routes/mvt.js

相关推荐
云和数据.ChenGuang1 小时前
Django 应用安装脚本 – 如何将应用添加到 INSTALLED_APPS 设置中 原创
数据库·django·sqlite
程序员学习随笔10 小时前
PostgreSQL技术内幕21:SysLogger日志收集器的工作原理
数据库·postgresql
秦时明月之君临天下10 小时前
PostgreSQL标识符长度限制不能超过63字节
数据库·postgresql
Amd79415 小时前
PostgreSQL 的历史
postgresql·开源软件·计算机科学·软件开发·关系型数据库·数据库技术·数据库历史
LuiChun17 小时前
Django 模板分割及多语言支持案例【需求文档】-->【实现方案】
数据库·django·sqlite
凡人的AI工具箱17 小时前
每天40分玩转Django:Django管理界面
开发语言·数据库·后端·python·django
中科院提名者17 小时前
Django连接mysql数据库报错ModuleNotFoundError: No module named ‘MySQLdb‘
数据库·mysql·django
碧水澜庭17 小时前
django中cookie与session的使用
python·django
鬼义II虎神18 小时前
将Minio设置为Django的默认Storage(django-storages)
python·django·minio·django-storages
gis分享者18 小时前
麒麟V10系统,postgres+postgis安装,保姆级教程,包含所有安装包
postgresql·安装·postgis·麒麟系统