Skip to content

JDBC 数据存储 ​

相关源文件:

介绍 ​

JDBC 数据存储提供了一个框架,用于通过 JDBC API 访问存储在关系数据库中的地理空间数据。这些数据存储在 GeoTools Feature API 和各种数据库系统之间架起了桥梁,允许应用程序使用空间数据而无需理解每个数据库的特定 SQL 方言或空间扩展。

本页涵盖了 GeoTools 中 JDBC 数据存储的架构和功能,重点介绍了它们如何连接到数据库、处理空间数据类型以及提供对数据库表的 feature 级访问。有关特定文件格式的信息,请参阅 格式支持。

架构 ​

JDBC 数据存储架构遵循模块化设计,通过通用 API 实现连接到不同数据库系统。核心组件包括:

SVG
100%

中心类 JDBCDataStore 为 JDBC 源实现了 DataStore 接口。它将数据库特定操作委托给适当的 SQLDialect 实现。feature 访问通过 JDBCFeatureSource(只读)和 JDBCFeatureStore(读写)类提供。

SQL 方言 ​

SQL 方言系统是一个关键抽象,允许 JDBC 数据存储与不同数据库系统一起工作。每个方言实现处理其目标数据库的特定 SQL 语法和功能,尤其是对于空间操作。

SVG
100%

每个方言负责:

  1. 在数据库和 JTS 之间转换几何对象
  2. 将 SQL 类型映射到 Java 类型
  3. 将 GeoTools filters 转换为 SQL WHERE 子句
  4. 处理数据库特定的空间函数

类型映射 ​

JDBC 数据存储提供了在 SQL 数据类型和 Java 对象之间转换的类型映射系统。SQL 方言确定如何处理这些映射,定义标准映射和任何数据库特定类型。

基本 SQLDialect 类中定义的标准类型映射包括:

SQL 类型Java 类型
VARCHAR、CHAR、LONGVARCHARString
BIT、BOOLEANBoolean
SMALLINT、TINYINTShort
INTEGERInteger
BIGINTLong
REALFloat
DOUBLE、FLOATDouble
DECIMAL、NUMERICBigDecimal
DATEjava.sql.Date
TIMEjava.sql.Time
TIMESTAMPjava.sql.Timestamp
BLOB、BINARYbyte[]

每个方言可以使用数据库特定类型扩展这些映射:

  • PostGIS 将 geometry 和 geography 列映射到 JTS 几何类型
  • Oracle 将 SDO_GEOMETRY 列映射到 JTS 几何类型
  • PostgreSQL/PostGIS 支持 JSON 和 JSONB 列类型

Feature 访问 ​

JDBC 数据存储提供基于 Feature 的 API,用于访问关系数据库中的数据。读取 features 的典型过程流程包括:

SVG
100%

写入 features 时,过程使用 JDBCFeatureStore 方法,如 addFeatures()、modifyFeatures() 和 removeFeatures()。

feature 类型(模式)从数据库元数据构建,检测几何列并从数据库配置适当的坐标参考系统信息。

Filter 转换 ​

JDBC 数据存储的关键功能之一是将 GeoTools filters 转换为 SQL WHERE 子句。这允许应用程序使用标准的 GeoTools Filter API,同时利用数据库特定的索引和优化。

filter 转换过程由 FilterToSQL 类及其数据库特定子类处理。这些类实现访问者模式,将不同的 filter 类型转换为适当的 SQL 语法。

SVG
100%

支持的 filter 类型包括:

  • 比较 filters(等于、大于等)
  • 逻辑 filters(AND、OR、NOT)
  • 空间 filters(BBOX、Intersects、Contains 等)
  • 属性存在 filters(PropertyIsNull)
  • 字符串匹配 filters(PropertyIsLike)
  • 时间 filters(Before、After、During)

对于空间 filters,每个方言转换为适当的数据库特定函数:

  • PostGIS: ST_Intersects、ST_Contains 等
  • Oracle: 带有适当掩码的 SDO_RELATE

高级功能 ​

主键和外键 ​

JDBC 数据存储处理主键以启用 feature 识别和编辑。主键从数据库元数据自动检测,或可以手动配置。PrimaryKeyFinder 接口提供识别主键的策略,具有基于元数据和启发式方法的实现。

默认情况下,主键列不在 feature 类型中公开,但可以使用 setExposePrimaryKeyColumns(true) 方法更改此设置。

虚拟表 ​

JDBC 数据存储支持虚拟表,这是在数据存储内而不是在数据库中定义的 SQL 视图。虚拟表允许将复杂查询或连接封装为单个 feature 类型。

VirtualTable vt = new VirtualTable("view_name", "SELECT * FROM base_table WHERE condition");
dataStore.createVirtualTable(vt);

批操作 ​

为了在插入多个 features 时获得更好的性能,JDBC 数据存储支持批操作。批量大小可以使用 setBatchInsertSize(int) 方法配置。

事务 ​

事务通过 GeoTools Transaction API 处理,其中 JDBC 事务管理数据库连接。这允许原子操作和不同事务上下文之间的隔离。

聚合函数 ​

通过访问者模式支持数据库端聚合。SumVisitor、CountVisitor、MaxVisitor 等访问者在可能时转换为 SQL 聚合函数:

访问者SQL 函数
CountVisitorCOUNT
SumVisitorSUM
MinVisitorMIN
MaxVisitorMAX
AverageVisitorAVG
StandardDeviationVisitorSTDDEV_POP
UniqueVisitorDISTINCT

数据库特定实现 ​

PostGIS ​

PostGIS JDBC 数据存储提供对带有 PostGIS 扩展的 PostgreSQL 数据库中空间数据的访问。它支持:

  • 所有标准 PostGIS 几何类型
  • 曲线几何形状(CircularString、CompoundCurve)
  • Geography 类型(大地测量坐标)
  • 使用 PostgreSQL/PostGIS && 操作符的空间索引
  • JSON 和 JSONB 列类型
  • 高级 PostGIS 特定函数

Oracle Spatial ​

Oracle JDBC 数据存储提供对使用 Oracle Spatial 的 Oracle 数据库中空间数据的访问。它支持:

  • Oracle SDO_GEOMETRY 类型
  • 大地测量几何形状(大地测量坐标系统)
  • 使用 SDO_FILTER 和 SDO_RELATE 的空间索引
  • SDO_NN(最近邻)查询
  • JSON 列类型

配置 ​

JDBC 数据存储通常配置为到数据库的连接和适当的方言。基本配置参数包括:

参数描述
dataSource用于数据库连接的 JDBC DataSource
dialect数据库的 SQLDialect 实现
databaseSchema限制表的架构名称
fetchSize每个数据库查询获取的行数
exposePrimaryKeyColumns是否在 feature 类型中包含主键列

配置示例:

DataSource dataSource = DataSourceUtil.setupDataSource(
    "jdbc:postgresql://localhost/database", "org.postgresql.Driver",
    "username", "password");

JDBCDataStore dataStore = new JDBCDataStore();
dataStore.setDataSource(dataSource);
dataStore.setSQLDialect(new PostGISDialect(dataStore));
dataStore.setDatabaseSchema("public");
dataStore.setFetchSize(1000);

性能考虑 ​

几个配置选项影响 JDBC 数据存储性能:

  1. Fetch 大小: 控制每次数据库往返检索的行数。默认为 1000。

    dataStore.setFetchSize(2000);
  2. 批插入大小: 控制在单个批操作中插入多少 features。默认为 1。

    dataStore.setBatchInsertSize(100);
  3. 连接池: JDBC 数据存储受益于连接池,通常由 DataSource 实现。

  4. 空间索引: 确保数据库表具有适当的空间索引,以获得空间查询的最佳性能。

  5. 松散 BBOX: 某些方言支持"松散 BBOX"模式,该模式仅使用 BBOX 查询的空间索引,提高性能。

    ((PostGISDialect)dataStore.getSQLDialect()).setLooseBBOXEnabled(true);

创建自定义方言 ​

为了支持新的数据库系统,开发者可以通过扩展 BasicSQLDialect 或 PreparedStatementSQLDialect 创建自定义 SQL 方言。要实现的关键方法包括:

  1. encodeGeometryColumn() - 在 SQL 中编码几何列
  2. decodeGeometryValue() - 将数据库几何转换为 JTS
  3. encodeGeometryValue() - 将 JTS 几何转换为数据库格式
  4. registerSqlTypeToClassMappings() - 定义 SQL 到 Java 类型映射
  5. createFilterToSQL() - 创建自定义 filter-to-SQL 转换器

方言还必须处理主键检测和任何数据库特定的空间操作。

测试 JDBC 实现 ​

GeoTools 为测试 JDBC 数据存储实现提供了框架,包括离线单元测试和连接到实际数据库的在线集成测试。

在线测试使用用户 ~/.geotools 目录中的夹具文件指定连接参数。这些测试在正常构建期间跳过,但可以针对特定数据库执行以进行集成测试。

测试框架包括:

  • JDBCTestSetup 用于配置测试数据库
  • JDBCTestSupport 作为测试用例的基类
  • OnlineTestCase 用于在测试中管理数据库连接

总结 ​

JDBC 数据存储为访问关系数据库中的空间数据提供了强大且灵活的方式。通过在通用 API 后面抽象数据库特定细节,它们允许 GeoTools 应用程序使用相同代码与不同数据库系统一起工作。方言系统实现了对数据库特定空间操作的支持,而类型映射系统处理 SQL 和 Java 类型之间的转换。

此架构使 JDBC 数据存储成为需要访问存储在企业数据库系统(如 PostgreSQL/PostGIS、Oracle Spatial 等)中的地理空间数据的 GeoTools 应用程序的基本组件。