Camel Karaf (OSGI Blueprint) SQL datasource

659 views Asked by At

Hi Guys I'm having some issues with my datasource in Karaf 4.3.6 (recent upgrade) I'm hoping someone could shed some light on what I'm doing wrong here.

Before the upgrade

Karaf had the below services (org.osgi.service.jdbc.DataSourceFactory):

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = com.microsoft.sqlserver.mssql-jdbc-native
 osgi.jdbc.driver.version = 6.2.2.jre8
 service.bundleid = 46
 service.id = 219
 service.scope = singleton
Provided by :
 Microsoft JDBC Driver for SQL Server (46)

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = Microsoft JDBC Driver for SQL Server
 osgi.jdbc.driver.version = 7.4
 service.bundleid = 47
 service.id = 223
 service.scope = singleton
Provided by :
 Microsoft JDBC Driver for SQL Server (47)

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = mssql
 service.bundleid = 157
 service.id = 252
 service.scope = singleton
Provided by :
 OPS4J Pax JDBC MSSQL Driver Adapter (157)
Used by:
 example-project(173)
 OPS4J Pax JDBC Config (38)

My project blueprint contained the below:

    <bean id="sqlComponent" class="org.apache.camel.component.sql.SqlComponent">
    <property name="dataSource" ref="exampleSQLServerDataSource"/>
</bean>

<service id="c1SQLDataSource" interface="javax.sql.DataSource" ref="exampleSQLServerDataSource">
    <service-properties>
        <entry key="osgi.jndi.service.name" value="exSQLDataSource"/>
    </service-properties>
</service>

<bean id="exampleSQLServerDataSource" factory-ref="sqlServerDataSourceFactory" factory-method="createDataSource">
  <argument>
    <props>
      <prop key="databaseName">${ex.db.dbname}</prop>
      <prop key="user">${ex.db.user}</prop>
      <prop key="password">${ex.db.password}</prop>
      <prop key="portNumber">${ex.db.port}</prop>
      <prop key="serverName">${ex.db.host}</prop>
    </props>
  </argument>
</bean>

<reference id="sqlServerDataSourceFactory" interface="org.osgi.service.jdbc.DataSourceFactory" filter="(objectClass=org.osgi.service.jdbc.DataSourceFactory)(osgi.jdbc.driver.name=mssql)"/>

With this configuration my project worked fine on install / i could use the camel-sql component with my datasource.

After the upgrade

Changes to karaf depensancys meant that the mssql factory was no longer available (even when starting the feature for pax-jdbc-mssql)

Karaf had the below services (org.osgi.service.jdbc.DataSourceFactory):

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = com.microsoft.sqlserver.mssql-jdbc-native
 osgi.jdbc.driver.version = 6.2.2.jre8
 service.bundleid = 54
 service.id = 214
 service.scope = singleton
Provided by :
 Microsoft JDBC Driver for SQL Server (54)

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = Microsoft JDBC Driver for SQL Server
 osgi.jdbc.driver.version = 9.2
 service.bundleid = 55
 service.id = 371
 service.scope = singleton
Provided by :
 Microsoft JDBC Driver for SQL Server (55)

[org.osgi.service.jdbc.DataSourceFactory]
-----------------------------------------
 osgi.jdbc.driver.class = com.microsoft.sqlserver.jdbc.SQLServerDriver
 osgi.jdbc.driver.name = Microsoft JDBC Driver for SQL Server
 osgi.jdbc.driver.version = 9.4
 service.bundleid = 282
 service.id = 370
 service.scope = singleton
Provided by :
 Microsoft JDBC Driver for SQL Server (282)

My project blueprint containes the below:

I modified my blueprint.xml to use one of the other connections available in jdbc:ds-factories but i am seeing the below error complaining of missing requirements on install

<bean id="sqlComponent" class="org.apache.camel.component.sql.SqlComponent">
    <property name="dataSource" ref="exampleSQLServerDataSource"/>
</bean>

<service id="c1SQLDataSource" interface="javax.sql.DataSource" ref="exampleSQLServerDataSource">
    <service-properties>
        <entry key="osgi.jndi.service.name" value="exSQLDataSource"/>
    </service-properties>
</service>

<bean id="exampleSQLServerDataSource" factory-ref="sqlServerDataSourceFactory" factory-method="createDataSource">
  <argument>
    <props>
      <prop key="databaseName">${ex.db.dbname}</prop>
      <prop key="user">${ex.db.user}</prop>
      <prop key="password">${ex.db.password}</prop>
      <prop key="portNumber">${ex.db.port}</prop>
      <prop key="serverName">${ex.db.host}</prop>
    </props>
  </argument>
</bean>

<reference id="sqlServerDataSourceFactory" interface="org.osgi.service.jdbc.DataSourceFactory" filter="(osgi.jdbc.driver.class=com.microsoft.sqlserver.jdbc.SQLServerDriver)(osgi.jdbc.driver.name=Microsoft JDBC Driver for SQL Server)(osgi.jdbc.driver.version=9.4)"/>

Seeing this error on install

karaf@root()> feature:install example-project
org.apache.felix.resolver.reason.ReasonException: Unable to resolve root: missing requirement [root] osgi.identity; osgi.identity=example-project; type=karaf.feature; version="[0.1.4.SNAPSHOT,0.1.4.SNAPSHOT]"; filter:="(&(osgi.identity=example-project)(type=karaf.feature)(version>=0.1.4.SNAPSHOT)(version<=0.1.4.SNAPSHOT))" [caused by: Unable to resolve example-project/0.1.4.SNAPSHOT: missing requirement [example-project/0.1.4.SNAPSHOT] osgi.identity; osgi.identity=com.example.example.project; type=osgi.bundle; version="[0.1.4.SNAPSHOT,0.1.4.SNAPSHOT]"; resolution:=mandatory [caused by: Unable to resolve com.example.example.project/0.1.4.SNAPSHOT: missing requirement [com.example.example.project/0.1.4.SNAPSHOT] osgi.service; effective:=active; filter:="(&(objectClass=org.osgi.service.jdbc.DataSourceFactory)(osgi.jdbc.driver.class=com.microsoft.sqlserver.jdbc.SQLServerDriver)(osgi.jdbc.driver.name=Microsoft JDBC Driver for SQL Server)(osgi.jdbc.driver.version=9.4))"]]
        at org.apache.felix.resolver.Candidates$MissingRequirementError.toException(Candidates.java:1341)
        at org.apache.felix.resolver.ResolverImpl.doResolve(ResolverImpl.java:433)
        at org.apache.felix.resolver.ResolverImpl.resolve(ResolverImpl.java:420)
        at org.apache.felix.resolver.ResolverImpl.resolve(ResolverImpl.java:374)
        at org.apache.karaf.features.internal.region.SubsystemResolver.resolve(SubsystemResolver.java:257)
        at org.apache.karaf.features.internal.service.Deployer.deploy(Deployer.java:399)
        at org.apache.karaf.features.internal.service.FeaturesServiceImpl.doProvision(FeaturesServiceImpl.java:1069)
        at org.apache.karaf.features.internal.service.FeaturesServiceImpl.lambda$doProvisionInThread$13(FeaturesServiceImpl.java:1004)
        at java.util.concurrent.FutureTask.run(FutureTask.java:266)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
        at java.lang.Thread.run(Thread.java:748)
Caused by: org.apache.felix.resolver.reason.ReasonException: Unable to resolve example-project/0.1.4.SNAPSHOT: missing requirement [example-project/0.1.4.SNAPSHOT] osgi.identity; osgi.identity=com.example.example.project; type=osgi.bundle; version="[0.1.4.SNAPSHOT,0.1.4.SNAPSHOT]"; resolution:=mandatory [caused by: Unable to resolve com.example.example.project/0.1.4.SNAPSHOT: missing requirement [com.example.example.project/0.1.4.SNAPSHOT] osgi.service; effective:=active; filter:="(&(objectClass=org.osgi.service.jdbc.DataSourceFactory)(osgi.jdbc.driver.class=com.microsoft.sqlserver.jdbc.SQLServerDriver)(osgi.jdbc.driver.name=Microsoft JDBC Driver for SQL Server)(osgi.jdbc.driver.version=9.4))"]
        at org.apache.felix.resolver.Candidates$MissingRequirementError.toException(Candidates.java:1341)
        ... 12 more
Caused by: org.apache.felix.resolver.reason.ReasonException: Unable to resolve com.example.example.project/0.1.4.SNAPSHOT: missing requirement [com.example.example.project/0.1.4.SNAPSHOT] osgi.service; effective:=active; filter:="(&(objectClass=org.osgi.service.jdbc.DataSourceFactory)(osgi.jdbc.driver.class=com.microsoft.sqlserver.jdbc.SQLServerDriver)(osgi.jdbc.driver.name=Microsoft JDBC Driver for SQL Server)(osgi.jdbc.driver.version=9.4))"
        at org.apache.felix.resolver.Candidates$MissingRequirementError.toException(Candidates.java:1341)
        ... 13 more
Error executing command: Unable to resolve root: missing requirement [root] osgi.identity; osgi.identity=example-project; type=karaf.feature; version="[0.1.4.SNAPSHOT,0.1.4.SNAPSHOT]"; filter:="(&(osgi.identity=example-project)(type=karaf.feature)(version>=0.1.4.SNAPSHOT)(version<=0.1.4.SNAPSHOT))" [caused by: Unable to resolve example-project/0.1.4.SNAPSHOT: missing requirement [example-project/0.1.4.SNAPSHOT] osgi.identity; osgi.identity=com.example.example.project; type=osgi.bundle; version="[0.1.4.SNAPSHOT,0.1.4.SNAPSHOT]"; resolution:=mandatory [caused by: Unable to resolve com.example.example.project/0.1.4.SNAPSHOT: missing requirement [com.example.example.project/0.1.4.SNAPSHOT] osgi.service; effective:=active; filter:="(&(objectClass=org.osgi.service.jdbc.DataSourceFactory)(osgi.jdbc.driver.class=com.microsoft.sqlserver.jdbc.SQLServerDriver)(osgi.jdbc.driver.name=Microsoft JDBC Driver for SQL Server)(osgi.jdbc.driver.version=9.4))"]]

POM

The maven-bundle-plugin definition from my pom.xml file

    <plugin>
        <groupId>org.apache.felix</groupId>
        <artifactId>maven-bundle-plugin</artifactId>
        <extensions>true</extensions>
        <configuration>
            <instructions>
                <Import-Package>
                    javax.jms;version="[2.0,3)",
                    org.xmlsoap.schemas.soap.envelope,
                    com.example.example.services.amqp.*,
                    *
                </Import-Package>
            </instructions>
        </configuration>
    </plugin>
1

There are 1 answers

2
Pasi Österman On

If I am reading the error message correctly, your Karaf is for some reason missing SQLServerDataSourceFactory service that should be provided by sqlserver activator when the bundle starts.

If you're upgrading from Apache Karaf version 4.2.x to 4.3.6 it could be that the version of the mssql-jdbc/9.4.0.jre8 bundle which the pax-jdbc-mssql feature installs could be incompatible with Java 11.

Apache Karaf 4.3.x supports JDK 11+ where as 4.2.x is for JDK 8, 9 and 10. There's handy table on Apache karafs downloads page that shows which version supports what. Mail about JDK 8 support with 4.3.x

Since the feature pax-jdbc-mssql only contains mssql-jdbc bundle and pax-jdbc-spec feature you could try to install them separately using jre11 version of mssql-jdbc bundle.

Example:

feature:install pax-jdbc-spec
bundle:install mvn:com.microsoft.sqlserver/mssql-jdbc/9.4.1.jre11

Since the version 9.4.1 has some vulnerabilities you could also try to upgrade to the newer 10.2.0.jre11 version if possible.