如何在Fuse Osgi环境中将验证查询,testonborrow,validationQueryTimeout属性传递给sqlserver数据源?我们正在使用osgi服务公开Microsoft SQLServer数据源。现在,我们传递数据源名称,用户,密码,端口号和服务器名称作为属性来实例化SQLServerDataSource。我们如何通过类似于Apache Commons dbcp的验证查询,testonborrow,testWhileIdle,testOnBorrow等属性?我们看到了连接问题,并通过将validationqueryquery等传递给Commons dbcp进行了处理,并希望对SQLServer Datasource进行同样的处理。感谢任何帮助吗? 这是我们如何实例化SQLServer数据源并将其作为OSGI服务公开的示例。
<bean id="abcd" class="com.microsoft.sqlserver.jdbc.SQLServerDataSource">
<property name="databaseName" value="datasourcename" />
<property name="user" value="user" />
<property name="password" value="password" />
<property name="portNumber" value="portNumber" />
<property name="serverName" value="serverName" />
</bean>
<!-- Opening Datasource as osgi service -->
<service interface="javax.sql.DataSource" ref="abcd">
<service-properties>
<entry key="osgi.jndi.service.name" value="jdbc/abcd" />
</service-properties>
</service>
答案 0 :(得分:1)
以下是典型示例,该示例使用您使用com.microsoft.sqlserver.jdbc.SQLServerDataSource
配置的非XA数据源:
<?xml version="1.0"?>
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.osgi.org/xmlns/blueprint/v1.0.0 https://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd">
<!--
This Blueprint XML shows the _deployment_ method for data source configuration.
With this method, it is not required to use pax-jdbc bundles at all. Instead both database-specific
and generic data sources are declared as Blueprint beans.
We need:
- SQL Server driver bundle
- mvn:org.apache.commons/commons-pool2/2.5.0 bundle
- mvn:org.apache.commons/commons-dbcp2/2.1.1 bundle
This Blueprint XML can be directly dropped to ${karaf.home}/deploy or archived in typical /OSGI-INF/blueprint
directory and installed as normal bundle.
-->
<!--
Database-specific, non-pooling, non-enlisting javax.sql.XADataSource
-->
<bean id="sqlServerDS" class="com.microsoft.sqlserver.jdbc.SQLServerDataSource">
<property name="databaseName" value="datasourcename" />
<property name="user" value="user" />
<property name="password" value="password" />
<property name="portNumber" value="portNumber" />
<property name="serverName" value="serverName" />
</bean>
<!--
Non database-specific, generic, pooling, non-XA factory for javax.sql.DataSource instances
-->
<bean id="dataSourceConnectionFactory" class="org.apache.commons.dbcp2.DataSourceConnectionFactory">
<!-- pass database-specific javax.sql.DataSource -->
<argument ref="sqlServerDS" />
</bean>
<!--
Non database-specific factory for org.apache.commons.dbcp2.PoolableConnection objects
-->
<bean id="poolableConnectionFactory" class="org.apache.commons.dbcp2.PoolableConnectionFactory">
<argument index="0" ref="dataSourceConnectionFactory" />
<!-- JMX Name - not needed -->
<argument index="1">
<null />
</argument>
<property name="maxConnLifetimeMillis" value="30000" />
<!-- set your validation query here: -->
<property name="validationQuery" value="select schema_name, schema_owner from information_schema.schemata" />
<!-- in seconds -->
<property name="validationQueryTimeout" value="2" />
</bean>
<!--
Pooling configuration
-->
<bean id="poolConfig" class="org.apache.commons.pool2.impl.GenericObjectPoolConfig">
<property name="minIdle" value="2" />
<property name="maxTotal" value="10" />
<property name="testOnBorrow" value="true" />
</bean>
<!--
Non database-specific pool of objects provided by PoolableConnectionFactory
-->
<bean id="pool" class="org.apache.commons.pool2.impl.GenericObjectPool">
<argument index="0" ref="poolableConnectionFactory" />
<argument index="1" ref="poolConfig" />
</bean>
<!--
And findally non database-specific, generic, pooling javax.sql.DataSource
-->
<bean id="dataSource" class="org.apache.commons.dbcp2.PoolingDataSource">
<argument ref="pool" />
</bean>
<!--
Expose datasource to use by application code (like Camel, Spring, ...)
-->
<service interface="javax.sql.DataSource" ref="dataSource">
<service-properties>
<entry key="osgi.jndi.service.name" value="jdbc/ds" />
</service-properties>
</service>
</blueprint>
我不确定com.microsoft.sqlserver.jdbc.SQLServerDataSource
是否实现javax.sql.XADataSource
-在这种情况下,这会更容易,因为您可以使用org.apache.commons.dbcp2.managed.BasicManagedDataSource
并按照需要配置它:
<bean id="pool" class="org.apache.commons.dbcp2.managed.BasicManagedDataSource">
<property name="xaDataSourceInstance" ref="sqlServerDS" />
<property name="transactionManager" ref="tm" />
<property name="minIdle" value="3" />
<property name="maxTotal" value="10" />
<property name="validationQuery" value="select schema_name, schema_owner from information_schema.schemata" />
</bean>
但是在这种情况下,sqlServerDS
应该是javax.sql.XADataSource
的实例。
编辑:我看到这里仍然描述了问题:https://issues.apache.org/jira/browse/ARIES-960
个人最好创建一个这样的对象(对不起,我使用PostgreSQL):
package com.example;
import javax.sql.DataSource;
public class DataSourceFactory {
public DataSource create() {
// Database-specific, non-pooling, non-enlisting javax.sql.XADataSource
org.postgresql.ds.PGSimpleDataSource postgresqlDs = new org.postgresql.ds.PGSimpleDataSource();
postgresqlDs.setUrl("jdbc:postgresql://localhost:5432/db");
postgresqlDs.setUser("user");
postgresqlDs.setPassword("password");
postgresqlDs.setCurrentSchema("schema");
postgresqlDs.setConnectTimeout(5);
// Non database-specific, generic, pooling, non-XA factory for javax.sql.DataSource instances
org.apache.commons.dbcp2.DataSourceConnectionFactory dataSourceConnectionFactory
= new org.apache.commons.dbcp2.DataSourceConnectionFactory(postgresqlDs);
// Non database-specific factory for org.apache.commons.dbcp2.PoolableConnection objects
org.apache.commons.dbcp2.PoolableConnectionFactory poolableConnectionFactory
= new org.apache.commons.dbcp2.PoolableConnectionFactory(dataSourceConnectionFactory, null);
poolableConnectionFactory.setMaxConnLifetimeMillis(30000);
poolableConnectionFactory.setValidationQuery("select schema_name, schema_owner from information_schema.schemata");
poolableConnectionFactory.setValidationQueryTimeout(2);
// Pooling configuration
org.apache.commons.pool2.impl.GenericObjectPoolConfig poolConfig
= new org.apache.commons.pool2.impl.GenericObjectPoolConfig();
poolConfig.setMinIdle(2);
poolConfig.setMaxTotal(10);
poolConfig.setTestOnBorrow(true);
// Non database-specific pool of objects provided by PoolableConnectionFactory
org.apache.commons.pool2.impl.GenericObjectPool<org.apache.commons.dbcp2.PoolableConnection> pool
= new org.apache.commons.pool2.impl.GenericObjectPool<>(poolableConnectionFactory, poolConfig);
// And finally non database-specific, generic, pooling javax.sql.DataSource
org.apache.commons.dbcp2.PoolingDataSource<org.apache.commons.dbcp2.PoolableConnection> dataSource
= new org.apache.commons.dbcp2.PoolingDataSource<>(pool);
return dataSource;
}
}
使用这样更简单的蓝图:
<bean id="factory" class="com.example.DataSourceFactory">
<!-- You can configure properties for your factory here -->
</bean>
<bean id="dataSource" factory-ref="factory" factory-method="create" />
<service interface="javax.sql.DataSource" ref="dataSource">
<service-properties>
<entry key="osgi.jndi.service.name" value="jdbc/ds" />
</service-properties>
</service>