网上有关Springboot集成SAP有各种各样的说法,我这里提供一个我调通的方案。如下pom配置,sapjco3.dll 放在"%JAVA_HOME%\bin\",否则报nested exception is java.lang.NoClassDefFoundError: Could not initialize class com.sap.conn.jco.JCo,服务器部署时也是这样放置,
sapjco3.dll和sapjco3.jar放在resources\lib下

XML
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.demo</groupId>
<artifactId>OPM</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<groupId>com.demo</groupId>
<artifactId>open-manager</artifactId>
<packaging>jar</packaging>
<name>open-manager</name>
<description>open-manager</description>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>com.demo</groupId>
<artifactId>common</artifactId>
<!--不加版本无法引用-->
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>com.sapjco3</groupId>
<artifactId>sapjco</artifactId>
<version>3.0</version>
<scope>system</scope>
<systemPath>${pom.basedir}/src/main/resources/lib/sapjco3.jar</systemPath>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
</dependencies>
<profiles>
<!-- 本地环境 -->
<profile>
<id>local</id>
<properties>
<spring.profiles.active>local</spring.profiles.active>
</properties>
<activation>
<activeByDefault>true</activeByDefault>
</activation>
</profile>
<!-- 开发环境 -->
<profile>
<id>dev</id>
<properties>
<spring.profiles.active>dev</spring.profiles.active>
</properties>
</profile>
<!-- 生产环境 -->
<profile>
<id>prod</id>
<properties>
<spring.profiles.active>prod</spring.profiles.active>
</properties>
</profile>
</profiles>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
<configuration>
<!--为false,取消本地的system的jar打入-->
<includeSystemScope>true</includeSystemScope>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-resources-plugin</artifactId>
<version>3.3.0</version>
</plugin>
</plugins>
<resources>
<resource>
<directory>src/main/webapp</directory>
</resource>
<resource>
<directory>src/main/resources</directory>
<!-- true表示利用占位符进行替换 -->
<filtering>true</filtering>
<includes>
<!--Maven 资源过滤是为文本文件设计的(如属性文件、XML 等)-->
<include>**/*.properties</include>
<include>application.yml</include>
<!-- ${spring.profiles.active}就是我们指定的环境,会被替换掉 -->
<include>application-${spring.profiles.active}.yml</include>
<include>**/*.xml</include>
<include>**/*.html</include>
<include>**/*.json</include>
<include>webapp/</include>
</includes>
<excludes>
<!-- 排除目录 -->
<exclude>lib/**</exclude>
<exclude>**/*.jar</exclude>
<exclude>**/*.dll</exclude> <!--sapjco3.dll "%JAVA_HOME%\bin\"-->
<exclude>**/*.jks</exclude>
<exclude>**/*.png</exclude>
</excludes>
</resource>
<!-- 新增:单独处理二进制文件(不进行过滤) -->
<resource>
<directory>src/main/resources/lib</directory>
<filtering>false</filtering>
<targetPath>BOOT-INF/lib</targetPath> <!-- 关键修改 -->
<includes>
<include>sapjco3.jar</include>
</includes>
</resource>
<!-- 处理其他资源 -->
<resource>
<directory>src/main/resources</directory>
<filtering>false</filtering>
<targetPath>BOOT-INF/classes</targetPath>
<excludes>
<exclude>lib/**</exclude> <!-- 排除已单独处理的 lib 目录 -->
</excludes>
<includes>
<include>**/*.jks</include>
<include>**/*.png</include>
</includes>
</resource>
</resources>
</build>
</project>
java
package com.demo.openmanager.sap;
import com.demo.common.util.StringUtils;
import com.sap.conn.jco.JCoDestination;
import com.sap.conn.jco.JCoDestinationManager;
import com.sap.conn.jco.JCoException;
import com.sap.conn.jco.ext.DestinationDataProvider;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Properties;
@Slf4j
public class XpJco {
@Value("${sap.host}")
private String SAP_HOST;
@Value("${sap.client}")
private String SAP_CLIENT;
@Value("${sap.sysno}")
private String SAP_SYS_NO;
@Value("${sap.user}")
private String SAP_USER;
@Value("${sap.pass}")
private String SAP_PASS;
@Value("${sap.lang}")
private String SAP_LANG;
@Value("${sap.poolCapacity}")
private String SAP_POOL_CAPACITY;
@Value("${sap.peakLimit}")
private String SAP_PEAK_LIMIT;
@Value("${sap.jcoSaprouter}")
private String SAP_JCO_SAPROUTER;
public synchronized JCoDestination getJCoDestination(String filename) {
JCoDestination destination = null;
try {
destination = JCoDestinationManager.getDestination(filename);
} catch (JCoException e) {
e.printStackTrace();
}
return destination;
}
private static boolean creatSapPros(String filename, String host, String sysno, String client, String user, String pass,
String lang, String pool_capacity, String peak_limit, String JCO_SAPROUTER) {
Properties pros = new Properties();
boolean iscreate = false;
pros.clear(); // 先清空
pros.setProperty(DestinationDataProvider.JCO_ASHOST, host);
pros.setProperty(DestinationDataProvider.JCO_SYSNR, sysno);
pros.setProperty(DestinationDataProvider.JCO_CLIENT, client);
pros.setProperty(DestinationDataProvider.JCO_USER, user);
pros.setProperty(DestinationDataProvider.JCO_PASSWD, pass);
pros.setProperty(DestinationDataProvider.JCO_LANG, lang);
pros.setProperty(DestinationDataProvider.JCO_POOL_CAPACITY, pool_capacity);
pros.setProperty(DestinationDataProvider.JCO_PEAK_LIMIT, peak_limit);
if (StringUtils.isNoneBlank(JCO_SAPROUTER)) {
pros.setProperty(DestinationDataProvider.JCO_SAPROUTER, JCO_SAPROUTER);
}
iscreate = createFiles(filename, pros);
if (iscreate) {
return true;
} else {
return false;
}
}
/**
* @param filename
* @return
*/
private static boolean isFileExist(String filename) {
File file = new File(filename + ".jcoDestination");
log.info("JCO path:" + file.getPath());
log.info("JCO AbsolutePath:" + file.getAbsolutePath());
// 最后会放在Q:\IdeaWork\OPM\tz02_ywk_jco.jcoDestination
// 环境上是放在启动jar包所在同级目录
return file.exists();
}
/**
* @param filename
* @param pros
* @return
*/
private static boolean createFiles(String filename, Properties pros) {
File file = new File(filename + ".jcoDestination");
FileOutputStream fos = null;
if (!file.exists()) {
try {
log.info("********* 正在写入文件 **********");
fos = new FileOutputStream(file, false);
pros.store(fos, "Author: ljb");
fos.close();
return true;
} catch (FileNotFoundException e) {
log.info("-------- 找不到文件! ---------");
e.printStackTrace();
return false;
} catch (IOException e) {
log.info("-------- 内容写入失败! ---------");
e.printStackTrace();
return false;
} finally {
try {
fos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
} else {
return false;
}
}
public synchronized JCoDestination getJCoDestination() {
boolean isexist = false; // 判断文件是否存在
boolean isCreate = false; // 创建pro文件
JCoDestination destination;
String filename = "tz02_ywk_jco";
isexist = XpJco.isFileExist(filename);
log.info("-- 获取JCoDestination isexist==" + isexist);
if (isexist == true) {
try {
destination = JCoDestinationManager.getDestination(filename);
return destination;
} catch (JCoException e) {
log.info("-- 获取JCoDestination失敗! --");
e.printStackTrace();
return null;
}
} else {
isCreate = XpJco.creatSapPros(filename, SAP_HOST, SAP_SYS_NO, SAP_CLIENT, SAP_USER, SAP_PASS, SAP_PASS,
SAP_POOL_CAPACITY, SAP_PEAK_LIMIT, SAP_JCO_SAPROUTER);
if (isCreate == true) {
try {
destination = JCoDestinationManager.getDestination(filename);
log.info("获取JCoDestination!成功");
return destination;
} catch (JCoException e) {
log.info("无法获取JCoDestination!");
e.printStackTrace();
return null;
}
} else { // 如果文件不存在
return null;
}
}
}
}