JPA UUID mapping for Oracle ORA-01465: invalid hex number - java

While this mapping works in MySQL on saving objects:
#Id
private String id;
on Oracle it throws: ORA-01465: invalid hex number when I am saving my object.
This is how I create id: UUID.randomUUID().toString()
My app must support both MySQL 5 and Oracle 12. So I can add only some mysql / oracle specific adapters / extensions that could be easily turned off while switching from one db to another. I cannot change JPA entities code if that would mean binding them to specific database. It must work on both databases.
What could I do so that it wouldn't break the application while switching from one MySQL to Oracle ?

Just remove '-' from UUID.randomUUID().toString()
For example,
UUID.randomUUID().toString().replaceAll("-","")

Related

Store a big String in database?

What is the best way to store a a big String in SQL server Database.
I'm using varchar(8000) but I get this exception while persisting my Object using Hibernate :
>Caused by: com.microsoft.sqlserver.jdbc.SQLServerException: String or binary data would be truncated.
Which version of SQL Server are you using? If the version is above 2005 Use VARCHAR(MAX). If the version is before 2005 you can use TEXT
When you want to store a very big string on SQL Server you can use:
varchar(max)
Well as I can see the tag of hibernate you need the tag of #Lob for storing super large objects.
Specifies that a persistent property or field should be persisted as a
large object to a database-supported large objec
Example:
#Lob #Basic(fetch=LAZY)
#Column(name="REPORT")
protected String report;
From Hibernate Docs.

Oracle NUMBER(precision,scale) in HSQLDB

In a unit test I am trying to generate a table in an in-mem HSQLDB, the table contains a column with the definition: #Column(name = "xxx", columnDefinition="NUMBER(10,0) default 0"). NUMBER is not recognized by HSQLDB (version 2.3.3), so I have added a script running this statement first: CREATE TYPE NUMBER AS NUMERIC;. Now it seems to recognize NUMBER, but I get the error unexpected token: ( instead. I cannot edit the column definition, so wow do I correctly map Oracle NUMBER(10,0) to NUMERIC? If I remove the precision and scale from NUMBER it seems to work.
You do not need to define the NUMBER type, as it is supported by HSQLDB.
HSQLDB supports Oracle syntax in one of its compatibility modes. Run this statement to enable it:
SET DATABASE SQL SYNTAX ORA TRUE

Oracle schema validator

I'm using Oracle DB in my application
My Application allow the user to create schema and for that reason
I want to do some validation before my application is set up..
for example I want to make sure that the user didn't create table with long column name
(There is limitation in Oracle for max 30 bytes table and column name)
I holding Dialect object in my validation function ,
Is it possible using the dialect object to find out that the user input (in my example column name)
is not correct - (because the column name size is more than 30 bytes..)
please assist,
Thanks,
Jhon.
I found out how to do it ..
I declared new object of class : java.sql.DatabaseMetaData
in This class there is getMaxColumnNameLength() method which return the limit for each DB
(for example in oracle that method return 30)
and now I can do my validation!
Thanks anyway :)
John.

Getting nearly double the length when reading byte[] from postgres with jpa

I have an Image class that has a byte[] to contain the actual image data. I'm able to upload and insert the image just fine in my webapp. When I attempt to display the image after reading it from JPA the length of my byte[] is always either 2x-1 or 2x-2, where x is the length of the bytea field in postgres 9. Obviously the browser won't display the image saying it's corrupted. I could use some help figuring out why I'm getting (about) twice what I expect. Here's the mapping of my image class. Using eclipselink with JPA 2 hitting postgres 9 on a mac.
When I select from the database with
select *, length(bytes) from image;
I get a length of 9765. In a breakpoint in my controller the byte[] length is 19529 which is one byte shy of twice what's in the database.
#Entity
#Table( name = "image" )
#SequenceGenerator( name = "IMAGE_SEQ_GEN", sequenceName = "IMAGE_SEQUENCE" )
public class Image
extends DataObjectAbstract<Long>
{
#Id
#GeneratedValue( strategy = GenerationType.SEQUENCE, generator = "IMAGE_SEQ_GEN" )
private Long key;
#Column( name="content_type" )
private String contentType;
#Lob
#Basic( optional=false )
#Column( name="bytes" )
private byte[] bytes;
// constructor and getters and setters
}
pgadmin shows me the following for the image table
CREATE TABLE image
(
"key" bigint NOT NULL,
bytes bytea,
content_type character varying(255),
"version" integer,
CONSTRAINT image_pkey PRIMARY KEY (key)
)
WITH (
OIDS=FALSE
);
The "bytea_output = escape" is just a workaround, Postgres 8.0 changed the bytea encoding to hex.
Use a current JDBC driver since 9.0-dev800 (9.0 Build 801 is up-to-date currently) and the problem will be solved.
In PostgreSQL 9 byte[] is sent to client using hex encoding.
If this is reason for error you have to find update for JPA.
Or you may change config of DB server but previous is better.
Supplementary answer for GlassFish 3.x users (principles may apply to other app servers)
You may be inadvertently using an old PostgreSQL JDBC driver. You can test this by injecting a DataSource somewhere (e.g. an EJB) and executing the following on it:
System.out.println(ds.getConnection().getMetaData().getDriverVersion());
In my case, it was 8.3 which was unexpected since I was deploying with 9.1 drivers.
To find out where this was coming from:
System.out.println(Class.forName("org.postgresql.Driver").getProtectionDomain().getCodeSource().getLocation());
As it turned out for me, it was in the lib directory of my GlassFish domain. I'm not sure how it got there - GlassFish certainly doesn't ship that way - so I just removed it and the problem went away.
Try looking at the data you're getting. It may give you a clue as to what's happening.
Check whether you have an old postgresql jar. I faced the same problem, and found both 8.3 postgresql jar and a 9.1 postgresql jar in my lib. After remove 8.3 postgresql, byte[] works fine.

The best way to import(merge)-export java db database

I have let's say two pc's.PC-a and PC-b which both have the same application installed with java db support.I want from time to time to copy the data from the database on PC-a to database to PC-b and vice-versa so the two PC's to have the same data all the time.
Is there an already implemented API in the database layer for this(i.e 1.export-backup database from PC-a 2.import-merge databases to PC-b) or i have to do this in the sql layer(manually)?
As you mention in the comments that you want to "merge" the databases, this sounds like you need to write custom code to do this, as presumably there could be conficts - the same key in both, but with different details against it, for example.
In short: You can't do this without some work on your side. SalesLogix fixed this problem by giving everything a site code, so here's how your table looked:
Customer:
SiteCode varchar,
CustomerID varchar,
....
primary key(siteCode, CustomerID)
So now you would take your databases, and match up each record by primary key. Where there are conflicts you would have to provide a report to the end-user, on what data was different.
Say machine1:
SiteCode|CustomerID|CustName |phone |email
1 XXX |0001 |Customer1 |555.555.1212 |darth#example.com
and on machine2:
SiteCode|CustomerID|CustName |phone |email
2 XXY |0001 |customer2 |555.555.1213 |darth#nowhere.com
3 XXX |0001 |customer1 |555.555.1212 |darth#nowhere.com
When performing a resolution:
Record 1 and 3 are in conflict, because the PK matches, but the data doesnt (email is different).
Record 2 is unique, and can freely exist in both databases.
There is NO way to do this automatically without error or data corruption or referential integrity issues.
I guess you are using Java DB (aka Derby) - in which case, assuming you just can't use a single instance, you can do a backup/restore.
Why dont you have the database on one pc. and have all other pc's request data from the host pc

Categories