构建并安装 PostgreSQL 扩展模块
PostgreSQL 对扩展模块构建程序施加了一些正式约束;这些说明内容假设模块是为 PGXS 构建系统编写的。在公开提供的扩展模块中,PGXS 用途广泛。
类 Unix 平台
PGXS 起源于类 Unix 系统,在那里使用起来非常简单。解压缩扩展模块存档,在生成的目录中运行以下命令
make PG_CONFIG=path_to_postgresql_installation/bin/pg_config make PG_CONFIG=path_to_postgresql_installation/bin/pg_config install
你可以省略PG_CONFIG覆盖,如果正在运行类型 pg_config在 shell 中会找到正确的 PostgreSQL 安装位置。在现有 PostgreSQL 安装目录的所有权范围内,第二个命令通常需要 root 特权。这些说明也适用于使用 MinGW 或 Cygwin 编译器为 Windows 进行构建时。但是,这些 Windows 配置有特殊需求,测试范围比大多数都小;预料会出现更多构建问题。
一个常见的错误是在 'make' 之前在命令行上指定 PG_CONFIG=...,这是不起作用的,因为该值会被 Makefile 的内部工作覆盖。
带有 Microsoft Visual Studio 的 Windows
PostgreSQL 项目分发了使用 Microsoft Visual Studio 工具集构建的 Windows 二进制文件,你自己也可以构建类似的二进制文件。此类构建不兼容且不包含 PGXS 基础架构。
Visual Studio 的 PostgreSQL 构建系统本身包含用于构建 core PostgreSQL 发行版contrib子目录中所发现的扩展模块。在 Windows 上构建第三方模块的一种方法需要利用构建流程。另一种方法要求为扩展创建你自己的 Visual Studio 项目。
使用 Visual Studio 项目文件进行构建
通过创建项目文件,使用 Visual Studio 构建扩展不会特别困难。你必须
- 创建项目
- 添加扩展源作为.c文件
- 针对每个函数都有PG_FUNCTION_INFO_V1,即它要作为 C 扩展函数导出,在PGDLLEXPORT之前Datum返回值。
- 编辑项目属性以
- 编译一个 DLL
- 使用纯 C 编译
- 禁用 C++ 异常
- 生成一个发行版
- 设置包含路径,添加
- include\server\port\win32_msvc
- include\server\port\win32
- include\server
- include
- 设置库路径,添加 PostgreSQLlibdir
- 添加postgres.lib到库链接列表中
- 在 C 预处理程序定义中添加WIN32(在较新版本中可能不需要)
详细说明此过程的文章
故障排除
失败定义WIN32原因
9.3\include\server\pg_config_os.h(207): error C2011: 'timezone' : 'struct' type redefinition 1> c:\program files\postgresql\9.3\include\server\pg_config_os.h(207) : see declaration of 'timezone' 1>c:\program files\postgresql\9.3\include\server\pg_config_os.h(216): error C2011: 'itimerval' : 'struct' type redefinition 1> c:\program files\postgresql\9.3\include\server\pg_config_os.h(216) : see declaration of 'itimerval'
失败添加PGDLLEXPORT将导致 PostgreSQL 无法创建函数,抱怨即使它显然存在,也无法在库中找到该函数。
失败添加postgres.lib将引发链接错误,但可能对你认为没有使用的函数产生影响。PostgreSQL API 中的许多“函数”,如elog是宏,它们会执行大量工作,然后调用不同名称的基础函数。
在contrib在一个构建树中
首先 [https://postgresql.ac.cn/docs/current/static/install-windows-full.html 建立一个可运行的 PostgreSQL 构建]。
如果模块最终将在其他已编译的 PostgreSQL 二进制文件中运行,例如官方二进制文件,则你的构建应该尽可能紧密地遵循官方构建。理想情况下,它将在 PostgreSQL 版本中完全匹配,config.pl选择和依赖库构建。在实践中,安排确切的匹配是非常费力的,而简单的模块无需此类工作也能运行。当模块本身引用特定依赖项时,更紧密的匹配会变得很重要。例如,要构建一个调用 libxml2 的模块,构建时使用的 libxml2 版本应与运行时使用的版本非常相似。对于不使用 libxml2 的模块,你通常可以通过在构建时禁用 xml 支持来解决此问题config.pl与运行时二进制配置无关。
在建立一个正常工作的构建后,通过将其解压的源目录移到contribPostgreSQL 源树的子目录中来引入所需的扩展模块。下次运行构建命令时,PostgreSQL 构建系统会注意到新目录并尝试构建它。安装命令同样会获取任何添加的模块。一个典型的模块会在lib, share/extension中创建文件,有时也会在symbols安装根目录的子目录中,其中所有此类文件的文件名前面都有模块名称作为前缀。运行安装之后,你可以从本地安装目录树中提取这些适用于模块的文件,并将它们合并到其他需要它们的安装中。
PostgreSQL 的 Visual Studio 构建系统通过试探性解析Makefile来处理扩展模块,该文件适用于 PGXS。对于简单的模块,这会正常工作。对于其他模块,您必须修改src/tools/msvc/Mkvcbuild.pm来满足该模块的需求,超出构建系统所能发现的需求。受影响的模块包括任何引用核心 DLL 之外的其他 DLL 的模块,而这些核心 DLL 则用于所有 PostgreSQL 代码。对于受影响的模块,请寻找类似contrib模块并调整其在Mkvcbuild.pm中的特殊处理,以针对当前的第三方模块。
PostgreSQL 将受益于在此领域开发更流畅的进程,类似于 PGXS 进程。
装有 MinGW 的 Windows
如果您构建并使用适用于 MinGW 的 postgres 发行版,并且在您的 Windows 电脑上安装了某种类型的 msys/mingw,那么您可以使用传统 Unix 风格的 make 进行构建,例如
make PG_CONFIG=C:\installs\postgres95_installed\usr\local\pgsql\bin\pg_config.exe make install PG_CONFIG=C:\installs\postgres95_installed\usr\local\pgsql\bin\pg_config.exe