Search code examples
hibernatejpasybasesap-asejconnect

Cannot store binary files with JPA and Sybase ASE


A user should be able to change the contents of an entity which contains a byte array, mapped to an image column in the DB. Please note that I cannot use LOB functionality, since Sybase does not support it.

When when I try to persist or merge the entity, only entities containing text/plain data are stored normally, while files of other types, like .pdf or .odt make the DB throw:

 java.sql.SQLException: JZ0SM: jConnect could not execute a stored procedure because there was a problem sending the parameter(s). This problem was likely caused because the server does not support a specific datatype, or because jConnect did not request support for that datatype at connect time.
Try setting the JCONNECT_VERSION connection property to a higher value. Or, if possible, try sending your procedure execution command as a language statement.

Hibernate logs a normal update immediately before the exception, and I am definitely not executing any stored procedures, so I'm not sure what stored procedure the error refers to. I have tried the same with native queries, but anded up with the same error.

16:08:04,776 INFO Hibernate: update KVS_MIPO_DOWNLOAD_FILE set creatorName=?, data=?, referencePeriod=? where id=?

I have checked the version of my jconn4 driver and have added JCONNECT_VERSION=7.0 to my connection string in the datasource. No effect.

Searching the web did not yield any related issues. The Sybase support page simply lists the erorr and offers no further assistance.

I am using Sybase ASE 15.7.0, JPA 2 over Hibernate 4.0.1.Final, running on JBoss 7.1.1 on a Suse 12.2 machine.

The entity:

@Entity
@DiscriminatorValue("file")
@Table(name = "KVS_MIPO_DOWNLOAD_FILE")
public class DownloadFile extends DownloadResource {

    @Column(nullable = false)
    private String creatorName;

    @Basic(fetch = FetchType.LAZY)
    private byte[] data = new byte[0];

    private String referencePeriod;

    ...

    public byte[] getData() {
        if (data != null) {
            return data.clone();
        }
        return new byte[0];
    }

    public void setData(final byte[] data) {
        if (data == null) {
            this.data = null;
            return;
        }
        this.data = data.clone();
    }

The table DDL:

create table KVS_MIPO_DOWNLOAD_FILE (
    referencePeriod           varchar(255)                 null  ,
    creatorName               varchar(255)             not null  ,
    id                        int                      not null  ,
    data                      image                        null   
)

Thank you.

EDIT: this question started out as a JSF/JPA/Sybase question. Through tests I can exclude JSF as the source of the error, so I removed the JSF parts.


Solution

  • Turns out the reason for the error was a bug in the 7.0 version of jConnect. I have updated to 7.07 and the issue was solved.