Невозможно прочитать файл xlsx, сохраненный в базе данных postgres (как bytea), используя Apache POI - PullRequest
2 голосов
/ 07 сентября 2011

Я использую apache POI для чтения файла xlsx и загрузки данных в базу данных.Я должен сделать эту работу в планировщике (по расписанию), работающем на Jboss.Поскольку планировщик работает на сервере, отличном от того, который был загружен, я использую тип данных postgres bytea для сохранения файла в базе данных, используя следующий код.getPrimaryKey () + "';");

FilePathAssociation filePathAssociation = fileAttachment.getFilePathAssociation();

if ( filePathAssociation != null )

{

File blobFile = new File( filePathAssociation.getPhysicalFilePath() );
   FileInputStream fis = new FileInputStream( blobFile );
   ps.setBinaryStream( 1, fis, (int)blobFile.length() );
   ps.executeUpdate();
   ps.close();
   fis.close();
}

Работает нормально, файл сохраняется в базе данных.

Но при чтении файла на сервере используйте код ниже

ResultSet rs =
                        stmt.executeQuery( "SELECT tk_filecolumnname FROM tk_tablename WHERE primarykey = '"
                            + fileAttachment.getPrimaryKey() + "';" );
                    if ( rs != null && rs.next() )
                    {
                        InputStream fileInputStream = rs.getBinaryStream( 1 );
                        Workbook workbook = WorkbookFactory.create( fileInputStream ); // apache POI code to read a xlsx file.
                        rs.close();
                        return file;
                    }

Выдает ошибку ниже,

java.lang.IllegalArgumentException: Your InputStream was neither an OLE2 stream, nor an OOXML stream

Я знаю, что для чтения файла xlsx POI необходим поток, поддерживаемый OOXML.Но почему метод

ResultSet.getBinaryStream()

не возвращает тот же поток ввода, который был сохранен при создании файла.

Пожалуйста, помогите или поделитесь своими знаниями.

спасибо, Амит.

Ответы [ 4 ]

1 голос
/ 08 сентября 2011

1.Вы можете использовать Postgres 9.0.в Postgres 9.0 по умолчанию для bytea используется hex.простой setByte в подготовленном выражении не сработает.Обходной путь - отредактировать postgresql.conf </p> <p>bytea_output = 'escape'

. Обновление драйвера jdbc также может исправить это, но не пытался.

2.try с использованием oid.это для хранения больших файлов в вашей базе данных.Вы можете найти больше информации здесь.http://jdbc.postgresql.org/documentation/80/binary-data.html

Java API можно найти http://jdbc.postgresql.org/documentation/publicapi/org/postgresql/largeobject/LargeObjectManager.html

1 голос
/ 07 сентября 2011

Выполните следующие действия:

1) Утверждение, что ваш код правильно читает книгу из файла (просто откройте FileInputStream).

2) Когда ваш код работает с файлами, а не с потоком из базы данных, это может быть связано с тем, как библиотека обрабатывает поток. Вы можете попробовать сохранить весь поток во временный файл, что дает вам дополнительное преимущество, вы можете быстрее освободить соединение с БД.

0 голосов
/ 13 января 2015

Убедитесь, что ваш classpath не фильтруется Maven. Этот пост решил ту же проблему: https://stackoverflow.com/a/13969688/704246

0 голосов
/ 04 сентября 2014

У меня была та же проблема (предложенные изменения на уровне конфигурации PostgreSQL или выбор нового драйвера не работали), и теперь я просто решил ее, обернув входной поток, считываемый из БД PostgreSQL, в буферный входной поток с помощью

import org.apache.commons.io.IOUtils;

IOUtils.toBufferedInputStream(file.getBinaryStream()));

Надеюсь, это поможет!

С уважением,

Нико Виттенбек

...