How to find data which is causing Oracle JDBC: underflow in double - java

I am getting following error
Caused by: java.lang.IllegalArgumentException: Underflow
at oracle.jdbc.driver.OraclePreparedStatement.setDoubleInternal(OraclePreparedStatement.java:6604)
~[ojdbc7-12.1.0.2.0-p0.jar:12.1.0.2.0]
at oracle.jdbc.driver.OraclePreparedStatement.setDouble(OraclePreparedStatement.java:6574)
~[ojdbc7-12.1.0.2.0-p0.jar:12.1.0.2.0]*
This happens when one of the double value in my data object is null/illegal. This happens when session.flush being called. The problem is my data object have composition of other data object and N number of collection elements.
It's difficult to find which double data member is giving the issue.
I have enabled the persistence log and not able to see the query being formed for update statement.
Don't have anything on log except the above line. I have put breakpoints on all the get member functions. The exception didnt happen when session.update is getting called. It happens when session.flush being called. Also sometimes I get session time out as I have huge number of data elements. So debugging all the data elements was bit difficult.
How to find which member is giving the issue ?

Do you use something like Hibernate? You could enable debug or trace log to show the sql-statements that are generated.
It turns out even Oracle JDBC has log that can be enabled:
From https://stackoverflow.com/a/40491028/66207 :
Place the trace-enabled ojdbc jar file in your classpath. Quote from
the linked Oracle page: "To get log output, you must use the debug
JAR files, which are indicated with a "_g" in the file name, like
ojdbc5_g.jar or ojdbc6_g.jar." My Oracle 11g installation contained
Create a logging.properties file as described on the linked Oracle
page, and adjust the logging levels to your needs. Example:
.level=SEVERE oracle.jdbc.level=FINEST
oracle.jdbc.handlers=java.util.logging.FileHandler
java.util.logging.FileHandler.level=FINEST
java.util.logging.FileHandler.pattern=jdbc.log
java.util.logging.FileHandler.count=1
java.util.logging.FileHandler.formatter=java.util.logging.SimpleFormatter
Add the JVM properties "-Doracle.jdbc.Trace=true
-Djava.util.logging.config.file=logging.properties" to the java startup command for your JDBC application.
The JDBC application should now produce a file named jdbc.log which should contain the desired information. In some cases it can be necessary to specify the full path to the logging.properties file.
Or the Hibernate Solution from https://stackoverflow.com/a/1713464/66207 :
You need to enable [logging][2] for the the following categories:
org.hibernate.SQL - set to debug to log all SQL DML statements as they are executed
org.hibernate.type - set to trace to log all JDBC parameters
So a log4j configuration could look like:
# logs the SQL statements
log4j.logger.org.hibernate.SQL=debug
# Logs the JDBC parameters passed to a query
log4j.logger.org.hibernate.type=trace
The first is equivalent to hibernate.show_sql=true legacy [property][1], the second prints the bound parameters among other things.

I was able to print the persistence log after enabling the following property :
sessionFactory-> cacheAccess->SessionFactory->jdbcservices->sqlStatementLogger->logToStdOut --> set this to TRUE.
Now the logs were printed and I was able to see the data which was causing the issue.

Related

JPA HIBERNATE : Cannot get a connection as the driver manager is not properly initialized [duplicate]

I am trying to configure hibernate(5.3.3 Final) with tomcat (8.5) and mysql (v.8.0.12). When I launch my HibernateTest.java (very simple code from tutorial, no problem here) with the hibernate.connection.url set as ‘jdbc:mysql://localhost:3306/sakila’ I am encountering the following error:
Caused by: java.sql.SQLException: The server time zone value 'Paris, Madrid
(heure d?été)' is unrecognized or represents more than one time zone. You
must configure either the server or JDBC driver (via the serverTimezone
configuration property) to use a more specifc time zone value if you want to
utilize time zone support.
MySQL is currently set on the ‘SYSTEM’ timezone for the global and the session (mysql> select ##global.time_zone, ##session.time_zone). And my system timezone is indeed Paris/Madrid.
In my hibernate.cfg.xml file, when I write the connection url :
jdbc:mysql://localhost:3306/sakila?useJDBCCompliantTimezoneShift=true;useLegacyDatetimeCode=false;serverTimezone=UTC;
The error is :
com.mysql.cj.exceptions.WrongArgumentException: Malformed database URL, failed to parse the connection string near '=false;serverTimezone=UTC;'.
It is not the problem mentioned in the stackoverflow post ‘issues with mysql server timezone and jdbc connection’, because the ‘&’ is refused by eclipse, see screenshot attached of the hibernate.cfg.xml file :
[The reference to entity "useLegacyDatetimeCode" must end with the delimiter ';']
1
It is not an invisible character between 'mysql:' and '//localhost' as mentioned in the stackoverflow post ‘Malformed database URL, failed to parse the main URL sections’.
I’ve tried to work the problem around by setting via MySql Workbench the option for the local time (default-time-zone = '+02:00') which fits with the summer time for Madrid/Paris (my case here). It doesn’t change a thing.
Any idea? Do I have to configure it somewhere else?
Thank you for your help, I've been on this one for 3 days now, without success.
You need to escape the &:
jdbc:mysql://localhost:3306/sakila?useSSL=false&serverTimezone=UTC
See more here: https://docs.jboss.org/exojcr/1.12.13-GA/developer/en-US/html/ch-db-configuration-hibernate.html
I've finally came across a solution.
As it looked that neither ';' nor '&' would do the trick to add more than one parameter, I took out all the parameters, and tried only one parameter :
jdbc:mysql://localhost:3306/sakila?serverTimezone=UTC
And it did the trick, I no longer have problems with this.
The following URL produced the error: jdbc:mysql://localhost:3306/db?useLegacyDatetimeCode=false&serverTimezone=CET
This worked for me:
replace & by &.

Rolling back a Postgres database using Liquibase in Java

I'm trying to roll back the changes to a postgres table inbetween component tests so each one has a clean db to work with.
I'm using liquibase to set up postgres (the changelog xml to describe the setup and then the liquibase-core Kotlin/Java library to apply it). I'm also using Hibernate to interact with postgres directly. The test framework I'm using is Kotest, using the beforeXXX methods to make sure all the setup happens before the tests run. The database is set up once before everything runs and the idea is to rollback after each test.
From looking in the docs I've found tagDatabase and rollback seem to be what I need, however when running them they don't seem to actually roll anything back.
The code is roughly as follows (this is just test code to see if it works at all, mind - code would ideally be segmented as I descirbed above):
// 1 - (Pre-all-tests) Postgres Setup
liquibase = Liquibase(
"/db/changelog/changelog-master.xml",
ClassLoaderResourceAccessor(),
DatabaseFactory.getInstance().findCorrectDatabaseImplementation(JdbcConnection(connection))
)
liquibase.update(Contexts(), LabelExpression())
liquibase.tag("initialised")
// 2 - Something is inserted
val newEntity = ThingEntity()
entityManager.persist(
entity
)
entityManager.transaction.commit()
entityManager.clear()
// 3 - Cleanup
liquibase.rollback("initialised", Contexts())
// 4 - Fetching
entityManager.find(ThingEntity::class.java, id)
Thing is, after running liquibase.rollback the newEntity I persisted earlier is still present. The tag has dissapeared - if I run the doesTagExist method it returns true and then false after the rollback so the tag is being removed at least.
Given I'm clearing the entity manager after the commit I don't think it's because it's being cached and as I said the tag is being removed - just not the data.
Can anyone tell my why the actual transactions (i.e. the persist) aren't being erased?
Thanks!
Looks like you are using liquibase in a wrong way. What you are trying to have (rollback of data that is added in unit-test) is something close to what is described here: Rollback transaction after #Test
And when you are asking liquibase to rollback to some tag it just executes rollback scripts (if any provided) for changesets that were applied after changeset with tag: https://docs.liquibase.com/commands/community/rollbackbytag.html

Neo4J REST API Call Error - Error reading as JSON ''

this is a newo4j rest api call related error - from my java code I'm making a REST API call to a remote Neo4J Database by passing query and parameters, the query being executed is as below
*MERGE (s:Sequence {name:'CommentSequence'}) ON CREATE SET s.current = 1 ON MATCH SET s.current=s.current+1 WITH s.current as sequenceCounter MERGE (cmnt01:Comment {text: {text}, datetime:{datetime}, type:{type}}) SET cmnt01.id = sequenceCounter WITH cmnt01 MATCH (g:Game {game_id:{gameid}}),(b:Block {block_id:{bid}, game_id:{gameid}}),(u:User {email_id:{emailid}}) MERGE (b)-[:COMMENT]->(cmnt01)<-[:COMMENT]-(u)*
Basically this query is generating a sequence number at run time and sets the 'CommentId' property of the Comment Node as this Sequence number before attaching the comment node to a Game's block i.e. For every comment added by the user I'm adding a sequence number as it's id.
This is working for almost 90% of the cases but there are couple of cases in a day when it fails with below error
ERROR com.exectestret.dao.BaseGraphDAO - Query execution error:**Error reading as JSON ''**
Why does the Neo4J Query not return any proper error code ? It just says error reading as JSON ''.
Neo4J Version is
Neo4j Community Edition 2.2.1
Thanks,
Deepesh
It gets HTML back and can't read it as JSON, but should output the failure HTML can you check the log output for that and share it too?
Also check your graph.db/messages.log and data/log/console.log for any error messages.

db already exists with different case other

i try to read data from a MongoDB. and i have a problem:
Exception in thread "main" com.mongodb.MongoException: db already exists with different case other
the exeption throws from here:
DBCursor cur[] = new DBCursor[cursorSize];
...
cur[i].hasNext() // Exeption
what is the problem?
the version of Mongo is 2.10.1
This error indicates that you are trying to create a database that differs by case only from a database name that already exists. For example, if you already have a database called "test", you will get this error trying to create "Test", "TEST", or other variations of upper or lower case for the existing name.
The database name is used in naming the data extent files, so clashes in name could cause Bad Things to happen on case-insensitive file systems.
The MongoDB manual has further details on Naming Restrictions, including case sensitivity and restrictions specific to different operating systems.
The useful part of the error message appears to have been omitted in the question description, but what you should see as part of this message is the name of the existing database as well as the new name that is being rejected.
The corresponding MongoDB 2.4 server code snippet is:
ss << "db already exists with different case other: [" << duplicate << "] me [" << _name << "]";
I think Stennie has very well defined and explained why you might be getting this error. However, in my case, I encountered an interesting case which you or others may also encounter. I had the the database called "HDB" but when I added my user to system.users collection with "db":"hdb" (lower case). So, I spent an hour or so trying to see what could have gone wrong while I was able to login. So, if you get this error make sure you did not accidentally add your user with lower/different case for db name. To confirm this.
1.Log in as the admin/default account run
db.system.users.find().pretty();
and then look for the user name that is getting this error along with the "db" in that json object and compare it against actual database you have.
Run
show dbs;
compare the db you see in step one against the name of db that you see in this step. (the command will show you all the databses you have but clearly you should only be concerned with the ones that you use/see in step one).

Why I cannot debug a DatabaseMetaData?

I've a strange situation with a little application in Java using a JDBC-OBDC. I'm inspecting a Database using the DatabaseMetaData Class. When I execute the program, everything works without anyproblem. But when I want to debug to see the values inside the Resulset containing the DatabaseMetaData a java.sql.SQLException is thrown only if I put a breakpoint within the while. Here's my code:
DatabaseMetaData patrol = con.getMetaData();
ResultSet answer = patrol.getTables(null, null, null, null);
while(answer.next()) {
if (answer.wasNull() == false) {
tableNamesAsOne = tableNamesAsOne + answer.getString("TABLE_NAME") + " ";
}
}
answer.close();
Why I cannot put my breakpoint in this section of code??
This is the printStackTrace.
Exception in thread "main" java.sql.SQLException: No data found
at sun.jdbc.odbc.JdbcOdbc.standardError(Unknown Source)
at sun.jdbc.odbc.JdbcOdbc.SQLGetDataString(Unknown Source)
at sun.jdbc.odbc.JdbcOdbcResultSet.getDataString(Unknown Source)
at sun.jdbc.odbc.JdbcOdbcResultSet.getString(Unknown Source)
at sun.jdbc.odbc.JdbcOdbcResultSet.getString(Unknown Source)
at Snooper.inspect(Snooper.java:56)
at Snooper.<init>(Snooper.java:26)
at Snooper.createAndShowGUI(Snooper.java:112)
at Snooper.main(Snooper.java:125)
Line Snooper.java:56 in my code refers to
tableNamesAsOne = tableNamesAsOne + answer.getString("TABLE_NAME") + " ";
Thanks.
I have installed SQL Server to reproduce your problem and verify it.
Short explanation
You must read the values ONLY ONCE and in the ORDER they appear in the SELECT. JdbcOdbc sucks. While debugging, you're reading them multiple times.
Long explanation
What you are doing is inspecting a stateful object in the debugger, which leads to dynamic results.
In this case it's the sun.jdbc.odbc.JdbcOdbcResultSet and executing the expression resultSet.getString(...) multiple times. The first time, it will work (in case your breakpoint suspends the Thread before the resultSet is asked). Then, the second time you (or your debugger) inspects the value of the expression again, the getString() method is called again and this method changes the internal state of the ResultSet object.
Although the method's name suggests it's a simple getter, it's not. It does more than that. It may actually retrieve the data from the database, change its internal position counters etc. You cannot execute the getter methods multiple times.
The ODBC Driver is a very bad thing and of low quality. Expect strange behavior and other dragons. You can get some debug information by enabling JdbcOdbc Tracing. That is done by setting a LogWriter on the DriverManager, before the JdbcOdbc-Bridge is activated:
java.sql.DriverManager.setLogWriter(new PrintWriter(System.out));
Then, you will get verbose debugging output of the JdbcOdbc-Driver like the following. It may help you to debug the problem you have. When debugging, just ensure to store the data retrieved from the ResultSet objects in local objects, so you can inspect them multiple times in the debugger.
DriverManager.getConnection("jdbc:odbc:testdbodbc")
JdbcOdbcDriver class loaded
registerDriver: driver[className=sun.jdbc.odbc.JdbcOdbcDriver,sun.jdbc.odbc.JdbcOdbcDriver#7b479feb]
DriverManager.initialize: jdbc.drivers = null
JDBC DriverManager initialized
trying driver[className=sun.jdbc.odbc.JdbcOdbcDriver,sun.jdbc.odbc.JdbcOdbcDriver#7b479feb]
*Driver.connect (jdbc:odbc:testdbodbc)
JDBC to ODBC Bridge: Checking security
No SecurityManager present, assuming trusted application/applet
JDBC to ODBC Bridge 2.0001
Current Date/Time: Wed Jan 26 00:31:27 CET 2011
Loading JdbcOdbc library
Allocating Environment handle (SQLAllocEnv)
hEnv=115724512
Allocating Connection handle (SQLAllocConnect)
hDbc=116219184
Connecting (SQLDriverConnect), hDbc=116219184, szConnStrIn=DSN=testdbodbc
RETCODE = 1
WARNING - Generating SQLWarning...
SQLWarning: reason([Microsoft][ODBC SQL Server Driver][SQL Server]Changed database context to 'master'.) SQLState(01000) vendor code(5701)
SQLWarning: reason([Microsoft][ODBC SQL Server Driver][SQL Server]Changed language setting to us_english.) SQLState(01000) vendor code(5703)
*Connection.getMetaData
*DatabaseMetaData.getDriverName
Get connection info string (SQLGetInfo), hDbc=116219184, fInfoType=6, len=300
SQLSRV32.DLL
*DatabaseMetaData.getDriverVersion
Get connection info string (SQLGetInfo), hDbc=116219184, fInfoType=7, len=300
06.01.7600
*DatabaseMetaData.getDriverName
Get connection info string (SQLGetInfo), hDbc=116219184, fInfoType=6, len=300
SQLSRV32.DLL
Driver name: JDBC-ODBC Bridge (SQLSRV32.DLL)
*DatabaseMetaData.getDriverVersion
P.S. And this was the reproduced exception, including line numbers of the Sun code for JDK 1.6.0_22. As you can see in the first line, this is what is printed out on the console when I inspected the getString() method.
Get string data (SQLGetData), hStmt=108067024, column=3, maxLen=257
RETCODE = 100
ERROR - No data found
java.sql.SQLException: No data found
at sun.jdbc.odbc.JdbcOdbc.standardError(JdbcOdbc.java:7138)
at sun.jdbc.odbc.JdbcOdbc.SQLGetDataString(JdbcOdbc.java:3907)
at sun.jdbc.odbc.JdbcOdbcResultSet.getDataString(JdbcOdbcResultSet.java:5698)
at sun.jdbc.odbc.JdbcOdbcResultSet.getString(JdbcOdbcResultSet.java:354)
at sun.jdbc.odbc.JdbcOdbcResultSet.getString(JdbcOdbcResultSet.java:411)
at sandbox.DatabaseMetadataTest.testDBMetadata(DatabaseMetadataTest.java:27)
Yeah, the debugger runs in a different thread than the metadata obtained by con.getMetaData();... so, you know, it's a different transaction with a different metadata.
Well, ok, that would be my 1st guess. I have not looked into Obdc driver source code to confirm.
Edit:
thanks for mhaller excellent remark a made a 2nd look/guess: you call wasNull() prematurely, it has meaning after some get operation of the ResultSet. Copy from javadoc
* Note that you must first call one of the getter methods
* on a column to try to read its value and then call
* the method <code>wasNull</code> to see if the value read was
* SQL <code>NULL</code>.
phew, me sucks tonight!

Categories

Resources