Mar*_*urg 4 java sftp gzip jsch
(这是x-post到Jsch邮件列表BTW).我正在从数据库中读取数据并将其作为byte [](用于跨中间件组件传输).
从那个字节[]我知道如何使用GZIPOutputStream类在本地文件系统上创建一个gzip压缩文件.我想要做的是使用JSch SFTP方法在远程文件系统上创建一个gzip压缩文件.
我已经解压缩了数据的byte []并将其作为InputStream传递给JSch库,以便SFTP到远程文件目录(作为.gz文件).但是,传递的文件具有意外的EOF并且不能被"枪杀"
gunzip:GlobalIssuer.xml.gz:意外的文件结束
提醒我没有传输一个字节[],它是.gz文件的内容,它是数据库记录的内容
(相对)SSCCE如下:
byte[] content = "Content".getBytes();
// It does work (I promise!) returns a 'gzipped' byte[]
byte[] gzippedContent = gzipContent(content);
ByteArrayInputStream bais = new ByteArrayInputStream(gzippedContent);
channelSftp.put(bais, "Content.txt.gz");
Run Code Online (Sandbox Code Playgroud)
gzipContent方法:
private byte[] gzipContent(byte[] content)
{
ByteArrayInputStream in = new ByteArrayInputStream(content);
// Create stream to compress data and write it to the to file.
GZIPOutputStream gzipOutputStream = null;
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
try
{
gzipOutputStream = new GZIPOutputStream(byteArrayOutputStream);
byte[] buffer = new byte[4096];
int bytes_read;
while ((bytes_read = in.read(buffer)) != END_OF_FILE)
{
gzipOutputStream.write(buffer, 0, bytes_read);
}
// Return the gzipped content
return byteArrayOutputStream.toByteArray();
}
catch (IOException e)
{
// Altered from original to make this a SSCCE
// Don't write exception handling like this at home!
System.err.println("Unable to gzip content" + e.getMessage());
return null;
}
/*
* Lots of closing streams with exception handling below.
* I *think* I'm closing off streams in the right order
* It's not triggering any of the System.err.println calls in any case
* Of course System.err.println is bad, but this is a SSCCE
*/
finally
{
try
{
if (in != null)
{
in.close();
}
}
catch (IOException e)
{
System.err.println("Was unable to close the Inputstream for gzipping, be aware of mem leak.");
}
try
{
if (byteArrayOutputStream != null)
{
byteArrayOutputStream.close();
if (gzipOutputStream != null)
{
gzipOutputStream.close();
}
}
}
catch (IOException e)
{
System.err.println("Was unable to close the OutputStream(s) for gzipping, be aware of mem leak.");
}
}
}
Run Code Online (Sandbox Code Playgroud)
原始内容("内容")以字节为单位:
0x750x6E0x630x6F0x6D0x700x720x650x730x730x650x640x430x6F0x6E0x740x650x6E0x74
Run Code Online (Sandbox Code Playgroud)
gzip压缩内容("内容")以字节为单位:
0x1F0x8B0x080x000x000x000x000x000x000x00
Run Code Online (Sandbox Code Playgroud)
或者替代地:
1f8b 0800 0000 0000 0000
Run Code Online (Sandbox Code Playgroud)
使用GZIPOutputStream和FileOutputStream写入本地文件系统的等效gzip压缩内容.
1f8b 0800 0000 0000 0000 2bcd 4bce cf2d ..........+ÍKÎÏ-
284a 2d2e 4e4d 71ce cf2b 49cd 2b01 00f8 (J-.NMqÎÏ+IÍ+..ø
3987 5f13 0000 00 9._....
Run Code Online (Sandbox Code Playgroud)
我想我看到了问题.虽然内容是正确gzip压缩的,但我没有创建gzip文件所需的校验和后缀(如果你在本地文件系统上执行此操作,GZIPOutputStream会与FileOutputStream一起执行).所以基本上我错过了这个:
2bcd 4bce cf2d ..........+ÍKÎÏ-
284a 2d2e 4e4d 71ce cf2b 49cd 2b01 00f8 (J-.NMqÎÏ+IÍ+..ø
3987 5f13 0000 00 9._....
Run Code Online (Sandbox Code Playgroud)
我无法在Jsch库中看到一个可以解决问题的方法 - 这意味着我认为我缺少一些基本点.
看起来你的问题在于使用GZipOutputStream和ByteArrayOutputStream,并且与JSch完全无关.
GZipOutputStream正在使用(通过其超类,DeflatorOutputStream)一个Deflator来完成实际的工作.允许此平减器缓冲它认为合适的任何数量的数据,直到您使用其finish()方法(通过流finish()或close())来表示压缩文件已完成.然后,它还将gzip包含校验和的页脚写入目标输出.
我觉得你的问题可以通过移动来解决getByteArray你的后close()级联,或添加finish()之前.
| 归档时间: |
|
| 查看次数: |
2914 次 |
| 最近记录: |