简介这是PostGIS 3.3.6的源码安装包面向需要在PostgreSQL中处理地理空间数据的开发者和GIS从业者用于解决空间对象存储、空间查询、坐标转换与地理分析等场景问题。整个资源以gz压缩包形式发布大小约16.98MB包含2000个文件其中457个SQL脚本与PostGIS扩展初始化相关269个C文件和127个头文件属于核心代码164个WKT文件提供空间对象文本样例另有po多语言翻译、expected回归测试结果、shp/dbf等矢量数据文件便于对照源码理解实现细节。目前已有69人学习或下载该压缩包。通过这份源码可以完整查看PostGIS对OpenGIS规范的实现方式研究空间数据类型、空间索引、空间函数、空间关系判断、坐标参考系统转换等底层逻辑同时它也能作为离线编译安装的基础适合需要学习扩展开发或搭建本地GIS数据库环境的技术人员。1. postgis-3.3.6.tar.gz 是什么散装源码包与编译安装的真实需求拿到postgis-3.3.6.tar.gz这个源码包的时候多数人已经在发行版仓库里碰过壁了仓库自带的 PostGIS 版本太旧、和当前 PostgreSQL 不匹配、或者干脆缺了某个扩展模块。这个 tar.gz 不是一键安装包而是 PostGIS 3.3.6 的完整源代码需要自己 configure 和 make。它能解决的核心问题是在不受发行版约束的前提下把 PostGIS 装到对应版本的 PostgreSQL 上并且拿到想要的 GIS 功能集。适合三类人正在做空间数据平台选型的后端工程师需要特定 PG 版本匹配的 DBA以及在离线环境或内网部署空间数据库的运维。如果你只是想点两下鼠标装完就用这个包并不是最省事的选项但它是唯一能精确控制版本和编译参数的路径。2. 编译前的依赖准备PostGIS 3.3.6 需要哪些底库与版本匹配2.1 依赖清单GEOS、Proj、GDAL 缺一不可PostGIS 不是独立运行的程序它是嵌入 PostgreSQL 的一组扩展库。编译它之前必须先准备好底层空间运算库。常见做法是装齐这四个GEOS几何运算核心、Proj坐标投影、GDAL栅格和多种格式读写、LibXML2GML/KML 解析。其中 GEOS 管的是ST_Intersects、ST_Buffer这类空间分析算子Proj 管的是坐标系转换GDAL 管的是栅格和矢量文件导入。缺了任何一个configure 都会提前中断。我一般会在编译前用系统包管理器装这些依赖。Debian/Ubuntu 系的命令是sudo apt-get install -y \ libgeos-dev \ libproj-dev \ libgdal-dev \ libxml2-dev \ postgresql-server-dev-14这段命令的关键是最后的postgresql-server-dev-14它的版本号必须和你的 PostgreSQL 主版本一致。如果你用的是 PostgreSQL 15就把 14 改成 15。这个包提供pg_config工具PostGIS 编译时必须靠它确定头文件路径。缺少它configure 会直接报PostgreSQL backend headers are not found。装完依赖后可以用pkg-config验证pkg-config --modversion geos pkg-config --modversion proj pkg-config --modversion gdal如果有版本号输出说明底库已经就绪。如果没有回到上一步检查包名是否装对。2.2 PostgreSQL 版本匹配3.3.6 能配合的 PG 版本PostGIS 3.3.6 不是所有 PostgreSQL 版本都支持。它官方适配的版本区间和当时发布的 PostgreSQL 版本有关但实践里更常见的问题是你手里的 PG 版本太新或太旧导致扩展控制文件的requires条件不满足。比如 PostgreSQL 16 刚发布时早期 PostGIS 3.3 版本还没有适配它编译能过但CREATE EXTENSION postgis会报语义错误。这种情况只有升级 PostGIS 到 3.4 以上或者换用兼容的 PG 版本。建议先确认你的 PG 主版本然后对照 PostGIS 的 release notes。常见部署里 PostgreSQL 13、14、15 用 3.3.6 都是稳妥的。如果拿不准直接在 PostgreSQL 中执行SHOW server_version;然后用查询到的版本号去查找对应分支。不要盲目猜这是 postgis 安装失败 里最容易忽略的一类原因——不是编译器问题而是 PG 和 PostGIS 的版本契约没谈拢。2.3 检查环境用 pg_config 验证编译路径在解压源码之前先确认pg_config指向的 PostgreSQL 实例是不是你要装的那个。很多机器上装了多个 PG 版本PATH里先遇到的pg_config可能不是目标版本。执行which pg_config pg_config --version pg_config --includedir-serverincludedir-server是 PostgreSQL 服务端头文件所在目录如果这个目录不存在说明你没装postgresql-server-dev包。另外要注意configure 时--with-pgconfig参数必须指向目标 PG 的pg_config而不是随便一个。我遇到过一台机器同时有 PostgreSQL 12 和 14默认pg_config指向 12结果 PostGIS 编译完装到了 12 的扩展目录后续在 14 的数据库里执行CREATE EXTENSION一直找不到文件。先检查这个能省下后面一整轮排查。3. 解压 configure 与编译从 tar.gz 到可安装文件的关键步骤3.1 解压与进入源码目录拿到postgis-3.3.6.tar.gz后先做完整性校验再解压。官方习惯是附一个SHA256SUMS文件你可以这样核对sha256sum postgis-3.3.6.tar.gz如果校验值和你下载源给出的不一致说明文件损坏或被篡改解压编译大概率会翻车。确认没问题后tar -xzf postgis-3.3.6.tar.gz cd postgis-3.3.6解压后会看到configure、Makefile.in、postgis等目录。postgis目录是核心代码extensions里是postgis、postgis_topology等扩展的 SQL 定义。这里要养成一个习惯编译之前先扫一眼README里的系统要求尤其是版本号。PostGIS 每次发布都会更新依赖的最低版本3.3.6 对 GEOS、Proj、GDAL 都有明确要求。3.2 configure 参数--with-pgconfig 等必调项进入源码目录后最关键的步骤是配置编译参数。PostGIS 的configure不是无脑./configure --prefix/usr/local就完事它需要知道 PostgreSQL 的位置、GEOS/Proj/GDAL 的位置。常见做法是显式指定./configure \ --with-pgconfig/usr/lib/postgresql/14/bin/pg_config \ --with-geosconfig/usr/bin/geos-config \ --with-gdalconfig/usr/bin/gdal-config \ --with-projdir/usr/share/proj \ --prefix/usr/local--with-pgconfig指向 PostgreSQL 的pg_config可执行文件这个路径决定 PostGIS 把扩展安装到哪个 PG 实例。--with-geosconfig和--with-gdalconfig分别指定 GEOS 和 GDAL 的配置文件路径。--with-projdir指定 Proj 数据目录通常和proj安装位置一致。如果这些路径漏配configure 会尝试在默认路径里找找不到就报错。参数结束后仔细看屏幕输出的摘要比如PostgreSQL version: 14、GEOS version: 3.11确认每一项都正确。如果只想使用默认的 PostgreSQL 安装可以只写./configure --prefix/usr/local但那样在一个多版本 PostgreSQL 共存的环境里非常危险。我一般会每次都写清楚--with-pgconfig避免装错实例。3.3 make 与 make install并行编译与权限处理配置成功后进入编译环节。这里可以用多核并行加速make -j4-j4表示用 4 个并行任务如果你的服务器 CPU 核数多可以适当加大。但要注意如果编译过程中报错不要只看最后几行。PostGIS 是由 C 和 C 混合编写的错误提示往往不在底部而是混在大量输出里。建议先重新单独执行一次make不带-j拿到干净的错误信息再定位。编译时间取决于机器通常在 5 到 20 分钟之间。编译没有报错后用make install安装sudo make install这里为什么要sudo因为扩展文件要写入 PostgreSQL 的安装目录比如/usr/lib/postgresql/14/lib和/usr/share/postgresql/14/extension。普通用户没有写权限。如果之前指定过--prefix安装路径会在make install时打印出来比如/usr/lib/postgresql/14/lib/postgis-3.3.so。看到这个文件生成说明核心库安装成功。4. 数据库端启用扩展CREATE EXTENSION 的流程与 PostgreSQL 侧配置4.1 创建扩展前置动作PostGIS 在 PG 中的安装路径编译安装完成后需要到 PostgreSQL 里建立扩展。但这一步之前要确认好数据库。PostGIS 是数据库级别的扩展不是集群级别的——你需要对每个要用空间功能的库单独执行CREATE EXTENSION。常见做法是先在 PostgreSQL 中切换到目标数据库sudo -u postgres psql -d mygisdbmygisdb是你准备存储空间数据的库。如果没有先创建CREATE DATABASE mygisdb;连接到数据库后查看 PostGIS 扩展是否已经出现在可用列表里SELECT * FROM pg_available_extensions WHERE name LIKE postgis%;这条 SQL 会列出 PostgreSQL 已经扫描到的 PostGIS 扩展及其版本号。如果这里能看到3.3.6说明扩展文件安装路径正确如果空表说明make install的路径和当前数据库的pg_config路径不对应回到第 3 章的路径检查。4.2 CREATE EXTENSION postgis 的权限要求执行创建扩展的命令很简单CREATE EXTENSION postgis;但这行命令有隐性要求执行者必须是超级用户或者被授予了CREATEROLE和CREATE权限。PostGIS 安装时会向pg_extension表写入控制信息并创建一组新的 SQL 函数、数据类型和类型转换。如果没有超级用户权限通常会报permission denied to create extension。有时候 DBA 只给了ALL PRIVILEGES也没用因为CREATE EXTENSION要求数据库所有者权限这个很玄学。我的建议是在初始部署时直接用postgres超级用户执行创建扩展完成后再把权限收窄给业务用户。不要在业务库第一次建扩展时就尝试用普通角色否则会被权限问题缠住。创建完可以验证SELECT postgis_version();输出应该包含3.3.6。如果这个函数报错说明扩展没有完整安装检查第 3 章的编译参数。4.3 常用 GUC 参数与首次空间查询PostGIS 3.3.6 安装后不需要像别的插件那样重启 PostgreSQL但需要确保search_path包含public或postgis架构否则ST_*函数可能找不到。常见做法是在连接时设置SET search_path public, postgis, topology;如果你把扩展安装到了单独的 schema比如CREATE EXTENSION postgis SCHEMA postgis;这里就要把postgis放在search_path里。我习惯用第二个参数指定 schema这样业务表和空间函数分开权限管理更清晰。第一个空间查询可以这样跑SELECT ST_GeomFromText(POINT(116.4 39.9), 4326);如果返回类型是geometry说明空间类型和函数已经正常工作。接着验证空间索引CREATE TABLE buildings ( id serial PRIMARY KEY, geom geometry(Point, 4326) ); CREATE INDEX buildings_geom_idx ON buildings USING GIST (geom);GIST 索引是 PostGIS 空间查询加速的根基建立之后ST_DWithin、ST_Intersects这类查询才有性能保证。没有这个索引小数据量看不出问题大数据量直接把人卡到崩溃。5. 避坑PostGIS 3.3.6 安装失败的典型场景与排查路径5.1 现象configure 报错找不到 GEOS现象执行./configure时输出里出现configure: error: could not find geos-config或者提示cannot find libgeos_c.h。原因GEOS 的开发包没安装或者装了但geos-config不在PATH里。PostGIS 不是直接找 GEOS 的库文件而是通过geos-config这个工具获取编译参数。发行版通常会把它放在/usr/bin/geos-config。如果只是装了libgeos-dev但PATH不对configure 还是会找不到。解决先确认包是否安装which geos-config或dpkg -L libgeos-dev | grep geos-config。如果没装sudo apt-get install -y libgeos-dev。如果装了但路径不在默认位置在 configure 命令里显式加上--with-geosconfig/usr/local/bin/geos-config。不要因为报错提示去网上乱找补丁绝大多数情况就是路径问题。5.2 现象make 过程中出现语法错误现象make跑到一半输出大量error: xxx was not declared in this scope甚至直接卡在某个头文件上。原因PostGIS 3.3.6 对 C 标准有要求如果默认编译器太旧比如 GCC 4.8部分模板和多态代码会编译不过。另外-j4并行编译时内存不足也会导致中间文件错乱报出一些莫名其妙的语法错误。解决先检查编译器版本gcc --version和g --version。如果版本低于 7升级 GCC。如果编译器版本正常试试不带-j重新编一次看是否还有同样的错误。我遇到过一次服务器内存只有 1GBmake -j8直接把内存撑爆重复编译时产生了残缺的.o文件。这种情况先make clean再用make -j2编译就能过去。这属于血泪经验别高估服务器的承受能力。5.3 现象CREATE EXTENSION 提示文件不存在现象执行CREATE EXTENSION postgis;时PostgreSQL 报错extension postgis is not available但pg_available_extensions里能看到名称。原因扩展控制文件.control存在但对应的 SQL 文件或动态库文件没有安装。PostgreSQL 在CREATE EXTENSION时会读取/usr/share/postgresql/版本/extension/postgis.control然后寻找同目录下postgis--3.3.6.sql和postgis.so。如果make install时pg_config指向了另一个 PostgreSQL 版本这些文件就会落到错误目录。解决检查你自己数据库的配置路径psql -c SHOW data_directory;然后看扩展目录是否正确。最常见做法是用--with-pgconfig强制指定版本后重新编译安装。不要手动画葫芦去复制文件那样版本容易错乱以后升级会踩更多坑。5.4 现象升级时旧版本残留导致冲突现象之前装过 PostGIS 2.5 或 3.0后来在同一个库里执行CREATE EXTENSION postgis报错extension postgis already exists或者升级报错type geometry already exists。原因旧版本已经在数据库里初始化了数据类型和函数新版本的 SQL 脚本会尝试再次创建同名对象数据库不允许重复定义。解决生产环境不能随意DROP EXTENSION因为会删除所有空间数据。正确路径是用ALTER EXTENSION postgis UPDATE TO 3.3.6;。但如果直接更新失败说明旧版本缺少升级脚本。PostGIS 官方提供的升级路径是从旧版本一层一层升上去比如2.5到3.0到3.3。如果你是从 2.5 直接版跳到 3.3需要先安装中间版本再继续升。这个步骤不能跳跳了就会因函数签名不匹配而翻车。5.5 现象空间索引没生效查询奇慢无比现象POSTGIS 安装成功数据也能查但ST_DWithin执行时间很长EXPLAIN显示Seq Scan而不是Index Scan。原因PostGIS 的 GIST 索引是建立在几何列上的如果表的geom字段没有建立索引或者查询条件里对geom做了函数封装索引就失效。最常见的模糊操作是WHERE ST_Intersects(ST_Transform(geom, 4326), target_geom)对列做函数计算GIST 无法利用。解决对几何列建立 GIST 索引并尽量在查询时保持列裸露。如果你经常做ST_Transform考虑直接使用统一的坐标系存储或者创建表达式索引CREATE INDEX buildings_geom_transformed_idx ON buildings USING GIST (ST_Transform(geom, 4326));但这样索引体积会膨胀写入变慢。我一般优先保证源数据坐标系统一把转换放在应用层不让索引背锅。6. 验证与进阶用 PostGIS 3.3.6 跑通真实空间查询并做一次调优安装完成只是起点我离开前会做一轮完整验证确保不是能建扩展但用不起来。下面这段 SQL 模拟了一个 5 公里范围内的兴趣点查询EXPLAIN ANALYZE SELECT b.id FROM buildings b WHERE ST_DWithin( b.geom, ST_SetSRID(ST_MakePoint(116.4, 39.9), 4326), 0.05 );执行计划里如果出现Bitmap Heap Scan和Index Scan using buildings_geom_idx说明 GIST 正确参与。0.05的单位是度约等于 5 公里这个数值在高纬度地区会有偏差但用于索引验证足够。如果出现Seq Scan回第 5.5 节查索引。验证通过后我会用一个进阶技巧调整work_mem来降低 GIST 索引扫描的 I/O。对于大范围空间查询PostGIS 会批量读取索引页默认的work_mem太低会导致额外排序。常见做法是在会话或事务级调整SET LOCAL work_mem 256MB;在生产环境直接改全局work_mem风险很大所以只在慢查询会话里临时调整。这个参数不是玄学空间索引的访问模式天然比其他 B-tree 更吃内存给足它效果立竿见影。我的习惯是每次编译 PostGIS 后都保留当时用的 configure 参数到一份postgis_build.sh脚本放在/usr/local/src里。下次遇到问题直接跑一遍脚本重新编译省去回忆参数的时间。有时候版本依赖会真的把人逼疯但参数写下来至少能排除一半的变量。postgis-3.3.6.tar.gz这个包本身不复杂复杂的是它嵌在 PostgreSQL 生态里的那些隐性约束。希望帮到你。本文还有配套的精品资源点击获取