作者:贤
目录
1. 背景
SuperMap iObjects Java
是面向 GIS 应用系统开发者的组件式 GIS 开发平台,具有强大的地理数据管理、编辑、显示、分析等功能,并且其具有极强的易用性和丰富的帮助资源,适宜快速开发大型 GIS 应用系统。
本文主要介绍如何以 SuperMap iObjects Java
组件为功能基础,结合 SpringBoot 开源框架快速搭建 GIS 后台服务。
2. 环境准备
2.1. 系统环境
操作系统 | 支持 | 说明 |
---|---|---|
Windows | ✔ | Windows 平台推荐硬件配置要求:处理器: 2.00 GHz以上内存要求: 2 GB硬盘容量: 100 GB |
Linux | ✔ | Linux平台最低硬件配置要求:CPU: 1.00 GHz (x86 架构)内存: 512 MB硬盘空间: 40 GB |
2.2. 开发环境
软件 | 版本 | 下载地址 | 说明 |
---|---|---|---|
iObjects Java | 10i 及其以上版本 | iObjects Java 下载地址 | SuperMap 官方提供了 iObjects Java 组件 Maven 仓库,可直接使用 |
IDEA | 2020.3.4 及其以上版本 | IDEA 下载地址 | |
SpringBoot | 2.7.x | * | IDEA 新建 SpringBoot 项目时可直接选择需要的版本 |
Swagger | 3.0.0 | * | 在 SpringBoot 项目的 pom.xml 文件中配置 |
3. 技术栈
3.1. SuperMap iObjects Java
SuperMap iObjects Java 组件为后台服务提供专业的 GIS 功能。
3.2. SpringBoot
SpringBoot 为框架,可供开发人员快速开发 Java 后台服务。
3.3. Swagger
Swagger 是一款 RESTFUL 接口的文档在线自动生成+功能测试功能软件,SpringBoot 集成 Swagger 后可供开发人员和服务使用人员学习测试服务接口。
4. 新建 SpringBoot 项目
-
IDEA 新建 SpringBoot 项目
-
配置 Maven 和项目 Java 版本
-
配置 SpringBoot 依赖模块
5. 配置 Swagger 模块
springfox-boot-starter 是一个 SpringBoot 库,它为 Spring 应用程序提供了快速、轻松地创建 Swagger 文档的能力。Swagger 文档可以帮助开发人员更好地理解和使用 RESTful API。
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>3.0.0</version>
</dependency>
-
修改 application.properties 文件配置
由于 SpringBoot 2.7.x 版本的默认路径匹配策略是
path-pattern-matcher
,当前 SpringBoot 项目集成 Swagger 3.0.0 后,若直接运行服务程序则会抛 “Failed to start bean ‘ documentationPluginsBootstrapper ‘ ; nested exception…” 的异常,因此需要在 application.properties 文件中添加以下配置修改路径匹配策略:spring.mvc.pathmatch.matching-strategy=ant_path_matcher
6. 配置 SuperMap iObjects Java 组件
SuperMap 官方提供了 supermap-maven 仓库 (https://maven.supermap.io),仓库包含 SuperMap iServer、SuperMap iObjects 等相关 Jar 和依赖的第三方库, 通过在 pom 文件中添加 SuperMap 官方库,用户可以将开发使用到的库及其依赖直接添加到 maven 项目中,方便用户解决使用 SuperMap 官方库时遇到的依赖缺失等问题。
-
添加 SuperMap Maven 远程仓库
在 SpringBoot 项目的 pom.xml 中添加 SuperMap Maven 仓库节点。
<repositories> <repository> <id>supermap</id> <url>https://maven.supermap.io/</url> <snapshots> <enabled>true</enabled> </snapshots> <releases> <enabled>true</enabled> </releases> </repository> </repositories>
-
添加 SuperMap iObjects Java 依赖
在 SpringBoot 项目的 pom.xml 中添加
SuperMap iObjects Java
组件依赖,如下添加 com.supermap.data 的依赖。<dependency> <groupId>com.supermap</groupId> <artifactId>com.supermap.data</artifactId> <version>11.0.1-21501-98146</version> </dependency>
-
配置 iObjects Java 组件环境变量
由于
SuperMap iObjects Java
组件的核心 GIS 功能是基于 C++ 实现,再通过 JNI 调用,仅通过 Maven 添加依赖 iObjects Java 组件 jar 包会存在 C++ 依赖库缺失的情况,因此需要在开发环境机器配置 iObjects Java 组件的依赖环境。操作系统 配置环境变量 Windows 在系统环境变量 PATH 中添加 SuperMap iObjects Java 安装目录\Bin 路径 Linux export LD_LIBRARY_PATH=SuperMap iObjects Java 安装目录\Binexport PATH=$LD_LIBRARY_PATH:$PATH
7. GIS 功能实现
在已添加 iObjects Java 组件依赖的 SpringBoot 项目中,可直接在 SpringBoot 框架中基于 iObjects Java 组件提供的 GIS 核心功能直接实现项目需要的 GIS 业务功能。下面以简单的数据服务实现代码为示例。
-
新建数据服务控制器 (DataServiceController)
@Api(tags = "数据服务") @RestController @RequestMapping("/data") public class DataServiceController { }
-
打开工作空间
@Operation(summary = "打开工作空间", description = "打开文件型工作空间") @ApiImplicitParams({ @ApiImplicitParam(name = "workspacePath", value = "文件型工作空间路径", dataType = "String", dataTypeClass = String.class) }) @GetMapping("/openWorkspace") public boolean openWorkspace(String workspacePath) { if (workspace != null) { workspace.close(); workspace.dispose(); workspace = null; } File file = new File(workspacePath); String workspaceName = file.getName(); String[] splitted = workspaceName.split("\\."); workspaceName = ""; for (int i = 0; i < splitted.length - 1; i++) { workspaceName = workspaceName.concat(splitted[i]); if (i < splitted.length - 2) { workspaceName = workspaceName.concat("."); } } WorkspaceConnectionInfo workspaceConnectionInfo = new WorkspaceConnectionInfo(workspacePath); workspaceConnectionInfo.setName(workspaceName); workspace = new Workspace(); return workspace.open(workspaceConnectionInfo); }
-
获取数据源名称列表
@Operation(summary = "获取数据源列表", description = "获取当前工作空间内的数据源列表") @GetMapping("/getDatasourceNames") public ArrayList<String> getDatasourceNames() { ArrayList<String> datasourceNames = new ArrayList<>(); if (workspace != null) { Datasources datasources = workspace.getDatasources(); for (int i = 0; i < datasources.getCount(); i++) { Datasource datasource = datasources.get(i); String datasourceAlias = datasource.getAlias(); datasourceNames.add(datasourceAlias); } } return datasourceNames; }
-
获取数据集名称列表
@Operation(summary = "获取数据集名称列表", description = "根据输入的数据源名称获取数据集名称列表") @ApiImplicitParams({ @ApiImplicitParam(name = "datasourceName", value = "数据源名称", dataType = "String", dataTypeClass = String.class) }) @GetMapping("/getDatasetNames") public ArrayList<String> getDatasetNames(String datasourceName) { ArrayList<String> datasetNames = new ArrayList<>(); if (workspace != null) { Datasources datasources = workspace.getDatasources(); if (datasources.contains(datasourceName)) { Datasource datasource = datasources.get(datasourceName); Datasets datasets = datasource.getDatasets(); for (int i = 0; i < datasets.getCount(); i++) { Dataset dataset = datasets.get(i); datasetNames.add(dataset.getName()); } } } return datasetNames; }
-
获取指定数据集记录
@Operation(summary = "获取指定数据集记录", description = "根据输入的数据源名称、数据集名称获取记录") @ApiImplicitParams({ @ApiImplicitParam(name = "datasourceName", value = "数据源名称", dataType = "String", dataTypeClass = String.class), @ApiImplicitParam(name = "datasetName", value = "数据集名称", dataType = "String", dataTypeClass = String.class) }) @GetMapping("/getRecordset") public JSONArray getRecordset(String datasourceName, String datasetName) { JSONArray jsonArray = new JSONArray(); if (workspace != null) { Datasources datasources = workspace.getDatasources(); if (datasources.contains(datasourceName)) { Datasource datasource = datasources.get(datasourceName); Datasets datasets = datasource.getDatasets(); if (datasets.contains(datasetName)) { Dataset dataset = datasets.get(datasetName); if (dataset instanceof DatasetVector) { DatasetVector datasetVector = (DatasetVector) dataset; Recordset recordset = datasetVector.getRecordset(false, CursorType.STATIC); FieldInfos fieldInfos = recordset.getFieldInfos(); for (int i = 0; i < recordset.getRecordCount(); i++) { recordset.moveTo(i); JSONObject subJsonObject = new JSONObject(); for (int j = 0; j < fieldInfos.getCount(); j++) { FieldInfo fieldInfo = fieldInfos.get(j); String fieldName = fieldInfo.getName(); Object fieldValue = recordset.getFieldValue(fieldName); if (fieldInfo.isSystemField() && fieldInfo.getType() == FieldType.LONGBINARY) { fieldValue = Toolkit.GeometryToGeoJson(recordset.getGeometry()); } subJsonObject.put(fieldName, fieldValue); } jsonArray.add(subJsonObject); } recordset.close(); recordset.dispose(); } } } } return jsonArray; }
8. 总结
根据上述教程开发后,可实现如下图所示的 GIS 服务。
此外,本教程还提供了根据上述教程开发的 GIS 后台服务示例代码,也可以直接下载示例代码通过 Maven 编译后运行调试。