带有SSH隧道的Spring Data JPA到远程MySQL服务器 [英] Spring Data JPA with ssh tunnel to a remote MySQL server
问题描述
我将Spring Data JPA与Hibernate作为持久性提供程序结合使用,并与远程MySQL5 Server结合使用,以执行定期复制内部数据子集的作业.这项工作(即石英计划的Java应用程序)每天执行一次,大约需要1-3天的时间. 30秒即可完成同步).出于安全原因,我们不希望打开远程服务器以进行外部(即localhost之外)的直接连接.
I'm using Spring Data JPA with Hibernate as persistence provider in conjunction with a remote MySQL5 Server for a job that periodically replicates a subset of internal data. The job (i.e. a quartz-scheduled java application) runs once per dai and needs approx. 30seconds to complete the synchronization). For safety reasons we don't want to open the remote server for direct connections from outside (i.e. other than localhost).
我已经看到了使用Jsch通过编程方式建立ssh隧道的示例,但是找不到有关如何将Jsch与spring数据集成的任何资源.我看到的一个问题是我的某些Spring bean(即org.apache.commons.configuration.DatabaseConfiguration)是在应用程序启动时创建的,并且已经需要访问数据源.
I've seen examples with Jsch to programmatically set up an ssh tunnel, but could not finde any resources on how to integrate Jsch with spring data. One problem I'm seeing is that certain of my spring beans (i.e. org.apache.commons.configuration.DatabaseConfiguration) are created at application startup and already needs access to the datasource.
我可以在应用程序外部打开ssh隧道,但是之后它会一直打开,但是我想避免这种情况,因为我每天只需要打开30秒即可.
I could open the ssh tunnel outside of the application, but then it would be opened all the time, but I wanted to avoid that as I only need it opened 30seconds per day.
经过研究,我发现了建立ssh隧道的几种方法
After some research I found several ways to get a ssh tunnel
A)实现我自己的数据源(我扩展了org.springframework.jdbc.datasource.DriverManagerDataSource),然后使用PostContruct和Predestroy通过Jsch设置/关闭ssh隧道
A) Implementing my own DataSource (I extended org.springframework.jdbc.datasource.DriverManagerDataSource) and then used PostContruct and Predestroy to setup / close the ssh tunnel with Jsch
->问题:ssh隧道在应用程序的生命周期内保持打开状态,这不是我想要的
--> Problem: The ssh tunnel remains open for the lifetime of the application, what is not what I want
B)实现我自己的驱动程序(我扩展了com.mysql.jdbc.Driver),并在连接之前覆盖"connect"以创建ssh隧道
B) Implementing my own Driver (I extended com.mysql.jdbc.Driver) and overwrite "connect" to create the ssh tunnel before the connection
->问题:我无法关闭ssh隧道连接
--> Problem: I'm not able to close the ssh tunnel connection
欢迎提出任何建议
推荐答案
如果您的Spring配置中包含DataSource
bean,则可以创建自己的DataSource
实现,该实现在尝试建立连接之前会打开SSH隧道.使用提供的JDBC URL.例如,请考虑使用HikariDataSource
的以下配置:
If you have a DataSource
bean in your Spring configuration, you can create your own DataSource
implementation that opens an SSH tunnel before attempting to make a connection using the provided JDBC URL. As an example, consider the following configuration that uses a HikariDataSource
:
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource">
<bean class="com.zaxxer.hikari.HikariDataSource" destroy-method="close">...</bean>
</property>
</bean>
您可以扩展类HikariDataSource
以提供您自己的实现.下面的示例:
You can extend the class HikariDataSource
to provide your own implementation. An example below:
class TunneledHikariDataSource extends HikariDataSource implements InitializingBean {
private boolean createTunnel = true;
private int tunnelPort = 3306;
public void afterPropertiesSet() {
if(createTunnel) {
// 1. Extract remote host name from the JDBC URL.
// 2. Extract/infer remote tunnel port (e.g. 3306)
// from the JDBC URL.
// 3. Create a tunnel using Jsch and sample code
// at http://www.jcraft.com/jsch/examples/PortForwardingL.java.html
...
}
}
}
然后,实例化自定义类的bean实例,而不是HikariDataSource
.
Then, instantiate a bean instance for the custom class instead of HikariDataSource
.
这篇关于带有SSH隧道的Spring Data JPA到远程MySQL服务器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!