You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android中Base64转加密Zip并读取XML内容的问题求助

问题分析与解决方案

核心问题

你遇到的ZipException: Not in GZIP format错误,根源是混淆了GZIP与Zip两种完全不同的压缩格式:

  • 你的Base64字符串解码后是带密码保护的Zip文件,而非GZIP压缩包,用GZIPInputStream读取必然报错。
  • 另外,Java原生java.util.zip包不支持加密Zip的解密操作,必须依赖第三方库实现。

解决方案步骤

1. 替换Base64解码工具

避免使用com.sun.org.apache.xml.internal.security.utils.Base64这类内部API(Android环境下存在兼容性风险),改用Android系统自带的android.util.Base64或Apache Commons Codec的Base64类。

2. 使用支持加密Zip的第三方库

推荐用Zip4j(轻量易用,完美支持加密Zip的读写),以下是完整实现:

步骤1:添加依赖

在build.gradle中引入Zip4j:

dependencies {
    implementation 'net.lingala.zip4j:zip4j:2.11.5'
}

步骤2:功能实现代码

import android.util.Base64;
import net.lingala.zip4j.ZipFile;
import net.lingala.zip4j.exception.ZipException;
import net.lingala.zip4j.model.FileHeader;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.List;

public class ZipUtil {
    public static String decodeAndReadEncryptedZip(String base64Str, String password) throws IOException, ZipException {
        // 1. Base64解码为字节数组
        byte[] zipBytes = Base64.decode(base64Str, Base64.DEFAULT);
        
        // 2. 写入临时文件(Zip4j暂不支持直接处理字节流)
        File tempZip = File.createTempFile("temp", ".zip");
        tempZip.deleteOnExit();
        
        try (InputStream is = new ByteArrayInputStream(zipBytes)) {
            org.apache.commons.io.FileUtils.copyInputStreamToFile(is, tempZip);
        }
        
        // 3. 解密并读取XML内容
        StringBuilder xmlContent = new StringBuilder();
        try (ZipFile zipFile = new ZipFile(tempZip)) {
            if (zipFile.isEncrypted()) {
                zipFile.setPassword(password.toCharArray());
            }
            
            // 遍历Zip内文件(假设仅包含目标XML)
            List<FileHeader> headers = zipFile.getFileHeaders();
            for (FileHeader header : headers) {
                if (!header.isDirectory()) {
                    byte[] content = zipFile.readFile(header);
                    xmlContent.append(new String(content, StandardCharsets.UTF_8));
                }
            }
        } finally {
            tempZip.delete();
        }
        
        return xmlContent.toString();
    }
}

3. 代码说明

  • 临时文件处理:Zip4j目前无法直接从字节流读取加密Zip,因此需要将解码后的字节写入临时文件,用完自动删除。
  • 兼容性:使用Android系统自带Base64类,避免内部API带来的适配问题。
  • 异常处理:保留必要的异常抛出,方便上层调用时做错误处理。

替代方案(Apache Commons Compress)

若不想引入Zip4j,可使用Apache Commons Compress + Commons Codec组合,但实现逻辑更复杂,需手动处理加密流,推荐优先选择Zip4j。

内容的提问来源于stack exchange,提问作者Shubham Agrawal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 16:46:28