Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/341.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 通过BLE从Android向NodeJS发送GZIP数据_Java_Android_Node.js_Base64_Zlib - Fatal编程技术网

Java 通过BLE从Android向NodeJS发送GZIP数据

Java 通过BLE从Android向NodeJS发送GZIP数据,java,android,node.js,base64,zlib,Java,Android,Node.js,Base64,Zlib,我已经在Android设备上构建了一个字符串,我需要压缩它,并通过蓝牙低能量将其发送到NodeJS应用程序,在那里需要解压缩 在Android/Java方面,我使用GZIP对其进行压缩,然后在发送之前对其进行Base64编码,如下所示: public static String compress(String str) throws IOException { byte[] blockcopy = ByteBuffer .allocate(4)

我已经在Android设备上构建了一个字符串,我需要压缩它,并通过蓝牙低能量将其发送到NodeJS应用程序,在那里需要解压缩

在Android/Java方面,我使用GZIP对其进行压缩,然后在发送之前对其进行Base64编码,如下所示:

public static String compress(String str) throws IOException {

    byte[] blockcopy = ByteBuffer
            .allocate(4)
            .order(java.nio.ByteOrder.LITTLE_ENDIAN)
            .putInt(str.length())
            .array();
    ByteArrayOutputStream os = new ByteArrayOutputStream(str.length());
    GZIPOutputStream gos = new GZIPOutputStream(os);
    gos.write(str.getBytes());
    gos.close();
    os.close();
    byte[] compressed = new byte[4 + os.toByteArray().length];
    System.arraycopy(blockcopy, 0, compressed, 0, 4);
    System.arraycopy(os.toByteArray(), 0, compressed, 4,
            os.toByteArray().length);
    return Base64.encodeToString(compressed, Base64.DEFAULT);
}
在NodeJS端,我接收它,解码Base64,然后使用
zlib
库按如下方式尝试解压缩它:

var buf = Buffer.from(raw, 'base64');
var data = zlib.gunzipSync(buf);
{ Error: incorrect header check
    at Gunzip.zlibOnError (zlib.js:153:15)
    at Gunzip._processChunk (zlib.js:411:30)
    at zlibBufferSync (zlib.js:144:38)
    at Object.gunzipSync (zlib.js:590:14)
    ...
    errno: -3, code: 'Z_DATA_ERROR' }
我已经单独测试了蓝牙通信,收集到的常规解压缩数据完全正常。我还测试了发送未压缩但以Base64编码的原始数据,这也可以解码并正常工作。但是,在尝试解压缩时,我从
zlib
库中得到以下错误:

var buf = Buffer.from(raw, 'base64');
var data = zlib.gunzipSync(buf);
{ Error: incorrect header check
    at Gunzip.zlibOnError (zlib.js:153:15)
    at Gunzip._processChunk (zlib.js:411:30)
    at zlibBufferSync (zlib.js:144:38)
    at Object.gunzipSync (zlib.js:590:14)
    ...
    errno: -3, code: 'Z_DATA_ERROR' }

我做错了什么,我该如何解决这个问题?

尝试使用Apache Commons编解码器
Base64OutputStream
,这将输出一个已经在Base64中的流。检查:

通过将这4个字节(blockcopy)添加到压缩字节数组,可以有效地修改压缩数据的标题(错误说明)。 按如下方式移除它们:

public static String compress(String str) throws IOException {

    ByteArrayOutputStream os = new ByteArrayOutputStream(str.length());
    GZIPOutputStream gos = new GZIPOutputStream(os);
    gos.write(str.getBytes());
    gos.finish();
    gos.close();
    os.close();
    return Base64.encodeToString(os.toByteArray(), Base64.DEFAULT);
}

或者在将var buf传递给zlib.gunzipSync()之前,省略其前4个字节(即blockcopy)。

为什么要对字节进行base64编码?这将使尺寸增加33%。我假设您希望最小化发送的字节数,因为您使用的是gzip。BLE库总是将字节转换为字符串,因此我希望确保编码没有损坏。Base64允许@Emilable使用一个坏的BLE库,因为GATT值在默认情况下是二进制的,以便存储任何类型的值。强制执行字符串似乎根本不正确。