您好我想从输入流创建一个blob in hibernate,但我不知道流的长度。
Hibernate.getLobCreator(sessionFactory.getCurrentSession()).createBlob(stream, length)
如何在不知道流的长度的情况下创建一个blob?
EDIT1
在较旧的hibernate版本中可能
http://viralpatel.net/blogs/tutorial-save-get-blob-object-spring-3-mvc-hibernate/
Blob blob = Hibernate.createBlob(file.getInputStream());
EDIT2
好但是它有一个错误的实现
返回新的SerializableBlob(new BlobImpl(stream,stream.available()));
stream.available不是真正的大小
编辑3
我试过
session.doWork(new Work() {
@Override
public void execute(Connection conn) throws SQLException {
LargeObjectManager lobj = ((org.postgresql.PGConnection) conn).getLargeObjectAPI();
但是conn只是来自c3p0的NewProxyConnection。
答案 0 :(得分:3)
以下是我现在使用的
Session currentSession = getSessionFactory().getCurrentSession();
Blob blob = Hibernate.getLobCreator(currentSession).createBlob(new byte[0]);
OutputStream setBinaryStream = blob.setBinaryStream(1);
Utils.fastChannelCopy(input, setBinaryStream);
setBinaryStream.close();
答案 1 :(得分:0)
尝试传入InputStream,长度为-1:
session.getLobHelper().createBlob(stream, -1);
这适用于SQL Server 2008.似乎Hibernate将此值直接传递给JDBC驱动程序,因此根据您的数据库驱动程序,这可能会也可能不会。
注意:如果我传入不正确的流长度(包括0),我将从Hibernate获取一个DataException(来自驱动程序:“com.microsoft.sqlserver.jdbc.SQLServerException:流值不是指定的长度。指定长度为10,实际长度为13.“)。长度为-1时,它总能正常运行而不会抱怨,数据会成功保存到数据库中。
答案 2 :(得分:0)
解决方法可能是将输入流保存到文件,然后将文件读入blob。
答案 3 :(得分:0)
我理解我的回答与您的问题略有不同。但这可能会帮助其他人降落在这里。根据我的要求,我将绝对文件路径作为创建blob的输入。如果您也有类似的要求,可以使用以下代码段。
Session session = sessionFactory.getCurrentSession();
File file = new File(filePath);
Blob blob = Hibernate.getLobCreator(session).createBlob(new FileInputStream(file), file.length());
file.length()将为您提供文件的长度。
答案 4 :(得分:-1)
在Dao中更改保存方法,如下所示
@Transactional
public void save(Document document, InputStream inputStream) throws IOException {
Session session = sessionFactory.getCurrentSession();
ByteArrayOutputStream buffer = new ByteArrayOutputStream();
int nRead;
byte[] data = new byte[16384];
while ((nRead = inputStream.read(data, 0, data.length)) != -1) {
buffer.write(data, 0, nRead);
}
buffer.flush();
Blob blob = Hibernate.getLobCreator(session).createBlob(buffer.toByteArray());
document.setContent(blob);
session.save(document);
}
答案 5 :(得分:-1)
我认为,如果你将InputStream转换为字节数组,那么它就是一个goog解决方案,所以你可以使用createBlob方法,它接受一个字节数组而不是一个InputStream,并且长度作为参数。 对于转换,您可以使用Apache Commons IO中的IOUtil。
Hibernate.getLobCreator(sessionFactory.getCurrentSession()).createBlob(IOUtils.toByteArray(stream));