How can I configure TCP keepAliveTimeout for DB2's JDBC Driver? - java

This page suggests I can tune the keepAliveTimeout value manually for DB2 with JDBC.
This list of driver properties that I've found doesn't mention this setting.
This other list of JDBC and SQLJ propeties mentions the keepAliveTimeOutsetting. However, it also says
Unless otherwise noted, all properties are in com.ibm.db2.jcc.DB2BaseDataSource.
How do I do that? As I understand it, these settings are distinct from the DB2 connect string settings, otherwise the aforementioned list would also mention the currentSchema setting.
Yet another page suggests I need a file called db2dsdriver.cfg but this does not seem to be applicable to JDBC according to this list.
How do I actually configure keepAliveTimeout for JDBC and check that it's active and set to whatever I've configured?

I see that you must specify keepAliveTimeout=0 in connection string and if you use 0 as value jdbc does't use internal value but it will use the operating systema value for interval time.
I found that here:
https://www.ibm.com/support/pages/keepalive-parameters-jdbc-driver
https://www.ibm.com/support/pages/tcpip-keepalive-settings-and-related-db2-registry-variables

Related

Getting connection error from Flyway command line with DB2 drivers

We are in the process of upgrading our database version from DB2 11.1.3 to DB2 11.5.6. We have been using Flyway for 4 years for migrating our code. The version we are using is 5.1.3 and it is working well, except it throws a warning the DB2 11.5 is not supported.
I have downloaded and tried to use Flyway 7.13.0 and 7.15.0 in our process but they both throw the following error
ERROR: Unable to obtain connection from database (jdbc:db2://VAN-FCALLANDER:50000/TMLCLCUR:retrieveMessagesFromServerOnGetMessage=true;) for user 'TMWIN': [jcc][10214][10050][4.29.24] java.util.Properties object passed to java.sql.Driver.connect() cannot be overridden by URL: jdbc:db2://VAN-FCALLANDER:50000/TMLCLCUR:retrieveMessagesFromServerOnGetMessage=true;. ERRORCODE=-4461, SQLSTATE=42815
----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
SQL State : 42815
Error Code : -4461
Message : [jcc][10214][10050][4.29.24] java.util.Properties object passed to java.sql.Driver.connect() cannot be overridden by URL: jdbc:db2://VAN-FCALLANDER:50000/TMLCLCUR:retrieveMessagesFromServerOnGetMessage=true;. ERRORCODE=-4461, SQLSTATE=42815
Caused by: com.ibm.db2.jcc.am.SqlSyntaxErrorException: [jcc][10214][10050][4.29.24] java.util.Properties object passed to java.sql.Driver.connect() cannot be overridden by URL: jdbc:db2://VAN-FCALLANDER:50000/TMLCLCUR:retrieveMessagesFromServerOnGetMessage=true;. ERRORCODE=-4461, SQLSTATE=42815
According to IBM, the error being returned is from the way the parameter is set by Flyway. https://www.ibm.com/docs/en/db2/11.5?topic=errors-errorcode-4461
I have tried using both the 11.1 (type3) driver and the 11.5 (type4) driver and both are throwing the same message.
Any idea how to get around this without updating the actual Flyway code the way IBM suggests?
Looks like the Flyway code may need some change.
Check their issues page and open a ticket if a ticket does not already exist there.
Otherwise there are possible workarounds for now.
In your specific case, the attribute appended to the URL triggers the exception so you can try:
(1) Change the flyway.url to remove :retrieveMessagesFromServerOnGetMessage=true
(2) Change the flyway config to supply this property via the fltway.jdbcProperties (or equivalent method) if that is enabled in your flyway version: flyway.jdbcProperties.retrieveMessagesFromServerOnGetMessage=true . See docs
https://flywaydb.org/documentation/configuration/parameters/jdbcProperties
or
(3) externally configure the connection property that you need via the IBM db2dsdriver.cfg. See the IBM Db2 documentation for details. The idea is that you can put all (or some of) the Data Source Name details and parameters into an XML file (db2dsdriver.cfg) and the Db2 driver will parse that at runtime to carry out your instructions.
or
(4) remove the property from the URL and suffer the absence of detailed messages on errors until the flyway code gets fixed.

Oracle 19c JDBC (Instant client basiclite) driver Issue

I working on upgrade the oracle jdbc driver from 11g (ojdbc6.jar) to 19c (ojdbc8.jar) in my java application, driver used is Instant Client (instantclient-basiclite-nt-19.11) with JRE1.8.0_271. After change to 19c, my application keep hit "ORA-02396: exceeded maximum idle time, please connect again" or "ORA-03113: end-of-file" error.
In oracle database properties, there are some limitation set, Idle-Time = 2 minutes and Connection-Time = 10 minutes. But I will not do any change on database because this may cause high CPU if many users are using the application at the same time.
In Java application, connection is stored in connection pool, I put the logging and can see that connection is closed and return to connection pool after finish execute. But when I run the application again after 2 minutes, the oracle error raised.
If I switch back to 11g, I don't get such error and application is working fine after 2 minutes. No change in code.
Is this BUG in latest oracle driver? I saw there is UCP.jar (Universal Connection Pool) package available in 19c but not in 11g, is it I have implement this? and how?
Your problem has nothing to do with the driver but with a database profile setting that limits the maximum allowed idle_time. Normally this is done to get rid of forgotten sessions.
You can check this using
select a.username,b.profile,b.RESOURCE_NAME,b.LIMIT from dba_users a, dba_profiles b where b.resource_name='IDLE_TIME' and a.profile=b.profile;
find which profile is used for your user and see if your dba is willing to change the limit.
if this happens to be the default profile it could be changed to unlimited by
ALTER PROFILE DEFAULT LIMIT IDLE_TIME UNLIMITED;
but it might be better to create a custom profile for your user.
If the IDLE_TIME limit can not be changed, run a query every once and a while, like select 'keep me alive from dual;
This also prevents closure by firewalls.

Nifi-1.0.0 and Crate.IO

Crate database offers a jdbc driver through which I should be able to connect to Crate from Nifi using DBCPConnectionPool controller service. So I did that, I get a connection, the ConvertJSONToSQL processor is able to get the columns from the Crate database but when I get to the PUTSql processor I get the following error:
FlowFileHandlingException: transfer relationship not specified
The thing is that I have a SUCCESS, FAILURE, RETRY relationship defined. It just throws a ProcessException in the onTrigger() method.
Any ideas how can I make it work ?
As soon as the jdbc driver is compatible it should work, but ...
I believe this is a bug in PutSQL that is hiding an issue either in the JDBC configuration, SQL statement, or something else. Using the standalone JDBC driver with valid SQL INSERT statements, I was able to PutSQL working with Crate.
Can you double-check your connection information and SQL statement(s)? Also if you can reproduce and want to share the SQL and/or connection info (JDBC URL, e.g.), please feel free, it could help get to the bottom of the PutSQL bug that is hiding another issue.

MySQL TINYINT(1) mysteriously mapped to Java type Integer

I'm stuck in a huge and old project (j2sdk 1.4.2, Tomcat 4.1.29, MySQL 5.0.51a) that I need to install a new development environment for at work.
I've got a MySQL DB that is accessed by my Tomcat, which treats request from my Java application. In that DB, some tables contain boolean values that are needed by my application.
So, in the application, a prepared statement is made, parameters are added to it, then the request is launched and the result set of this request is stored inside of a custom SQLResult object (that is part of a custom framework made by my company, can't do anything 'bout that - though, it is quite similar to a classic java.sql.ResultSet object).
Here's the problem: when the java application request some data that are stored in the DB as TINYINT(1), those data are returned to the java application as java.lang.Integer, not java.lang.Boolean, as I would like to.
Note: the JDBC connector version used by the Tomcat server is mysql-connector-java-3.0.11-stable.
What I tested so far (without result):
upgrade/downgrade the MySQL connector
added tinyInt1isBit=<true/1> as the end of my connection string
upgrade/downgrade the MySQL DB, always with the same data dump I have been given along the source code
plenty other things I couldn't even remember, because I tested so much things :-/
I'm pretty sure now that the problem comes from the MySQL JDBC connector used by the Tomcat server. Thus, when I changed the version of the connector, nothing else was working anymore (meaning, couldn't even connect a user).
Any ideas?
EDIT: I forgot to precise that, in another part of the java application, request for data stored as DECIMAL are returned as java.lang.String! This is also a major problem I have to solve, but I think the two are linked to the same cause.
From Connector/J documentation
MySQL Type Name: TINYINT
Return value of GetColumnClassName: TINYINT
Returned as Java Class: java.lang.Boolean if the configuration property tinyInt1isBit is set to true (the default) and the storage size is 1, or java.lang.Integer if not.
Please note: or java.lang.Integer if not. Check the property tinyInt1isBit and possibly change it.
If you already did it try to restart the mysql server.
So, after a complete week of work, I managed to found the solution. Beware, that was kind of stupid.
I was right when I thought the MySQL connector was the source of my problems. I decided to retry everything I tried until today to solve the situation, and so I slightly upgraded the connector (from v3.0.11 to v3.1.14). Then I re-launched the problematic DB requests and noticed an ERROR log I didn't see before in my Tomcat logs: the DB name specified was not correct (something like myDB\?autoReconnect=true...). Indeed, a \ had been wrongfully inserted before the connection arguments part.
I removed the guilty \ from the connection string, relaunched my Tomcat, and... tadaaa! My problems were solved!
However, I did test with the old MySQL connector (v3.0.11) and it still returns TINYINT(1) as java.lang.Integer and DECIMAL as java.lang.String. So I guess the client upgraded its MySQL connector on its production Tomcat without warning me.
Anyway, thank you all for your suggestions. Guess I'll read server logs more carefully when I debug in the future :-)

Oracle error messages

I'm curious about something... is it possible for an Oracle 11 instance to be configured so that it does not return any ORA-?????? error messages?
I've issued many invalid queries where I've misspelled column names, table names... things where I would expect an ORA error message.
Say for security purposes say if a stray java stack trace got exposed to a browser could you force oracle to always show the same bogus error message in the stack trace?
I always get this one:java.sql.SQLException: IO Error: Size Data Unit (SDU) mismatch
I've googled that error up and down, and I do not have any connection or database configuration issues at all! I get it on a per-query basis.
Not a direct solution but I was having the same problem with the SDU mismatch masking the real error. I found a link (http://www.rajivnarula.com/blog/2013/03/13/table-not-found-or-error-not-found/) that gave an indirect way to expose the error:
I tried swapping the JDBC driver with the older ojdbc14.jar and voila
! The real error was exposed : Good old
ORA-00942 (table or view does not exist)
Once I put the table in- everything works fine- with ojdbc14.jar as
well ojdbc6.jar
Obviously a pain but useful until someone posts a way to get the underlying error with the newer driver...
Basically your setup is not correct. Either on the client or on the server or on both the sdu size has been set and they do not match between client and server. The sdu size can be set on the client in
the sqlnet.ora file or
in the connect descriptor
On the server it can be set with
in the sqlnet.ora file
the dispatchers init.ora parameter
or the listener.ora file.
If you are still not convinced, trace the tns traffic to verify this. Client side tracing can be enabled by adding the following settings to the sqlnet.ora file:
trace_level_client = 10
trace_unique_client = on
trace_file_client = sqlnet.trc
trace_directory_client = <path_to_trace_dir>
Server side settings can be enabled with the following settings:
trace_level_server = 10
trace_file_server = server.trc
trace_directory_server = <path_to_trace_dir>
If level 10 is not sufficient, set the level to 16. This will create a trace file that you can analyze.
You can try to upgrade the Oracle 11g JDBC driver to a version greater than 11.2.0.3.0, as described here
There is another chance whether the table in the query exists in the database or not. Check for table name in the query or try whether you are trying for Oracle Database using mysql driver

Categories

Resources