新濠天地 > 编程网新闻 > 新濠天地所以转化对象时候会失败,inputStream读取

原标题:新濠天地所以转化对象时候会失败,inputStream读取

浏览次数:51 时间:2019-09-24

我们项目利用report 报表效用,然后在加载xxxx.jasper文件时候报的invalid stream header: EFBFBDEF 的荒谬

错误格局

public JasperPrint fill(InputStream inputStream, Map<String, Object> parameters)throws JRException{

   @Test
    public void testDeserializeTest() throws IOException, ClassNotFoundException {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        ObjectOutputStream oos = new ObjectOutputStream(baos);
        BigInteger bi = new BigInteger("0");
        oos.writeObject(bi);
        String str = baos.toString();
        System.out.println(str);
        ObjectInputStream ois = new ObjectInputStream(
                new BufferedInputStream(new ByteArrayInputStream(str.getBytes())));
        Object obj = ois.readObject();
        assertEquals(obj.getClass().getName(), "java.math.BigInteger");
        assertEquals(((BigInteger) obj).intValue(), 0);
    }

JasperReport jasperReport = (JasperReport) JXC90Loader.loadObject(inputStream); //这里出错

不错方法

*return fill(jasperReport, parameters);
}*

 @Test
    public void testDeserialize() throws IOException, ClassNotFoundException {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        ObjectOutputStream oos = new ObjectOutputStream(baos);
        BigInteger bi = new BigInteger("0");
        oos.writeObject(bi);
        byte[] str = baos.toByteArray();
        ObjectInputStream ois = new ObjectInputStream(new BufferedInputStream(new ByteArrayInputStream(str)));
        Object obj = ois.readObject();
        assertNotNull(obj);
        assertEquals(obj.getClass().getName(), "java.math.BigInteger");
        assertEquals(((BigInteger) obj).intValue(), 0);
    }

钉住源码首借使上面出错,百思不得其解,网络说过多都以意识字符被改换了以关于ObjectOutputStream不也许辨认该字符数组所以抛出了java.io.StreamCorruptedException: invalid stream header: EFBFBDEF,然而笔者那几个跟字符串无妨。inputStream读取的是二进制文件,怎么可能出现这些题目。

由来是出于:

    ObjectInputStream in = new ObjectInputStream(inputStream);

将字 ByteArrayOutputStream对象调用为toString转为为字符串时,会将 ObjectOutputStream对象放置在指标流尾部的前七个字节(0xac)(0xed)连串化为五个“?”

突发性看到那篇小说技巧够化解

当以此字符串使用getByte()时会将八个“?”变为(0x3f )(0x3f) 。但是那七个字符并不构成有效的对象流头。所以转化对象时候会倒闭。

驷不及舌是跟mavenresource 标签有关系,maven 打包时候,已经把二进制文件给毁掉了,导致失败

测量检验代码 单元测验不能够输出结果这里用main测量试验

<resources>
<resource>
<targetPath>${project.build.directory}/classes</targetPath><directory>src/main/resources</directory><filtering>true</filtering></resource>
</resources>

 

在maven 网址过滤的时候

 1 public static void main(String[] args) throws IOException {
 2         ByteArrayOutputStream baos = new ByteArrayOutputStream();
 3         ObjectOutputStream oos = new ObjectOutputStream(baos);
 4         String s = "111";
 5         oos.writeObject(s);
 6         String str = baos.toString(); 
 7         byte[] baStr = baos.toByteArray();
 8         byte[] gbStr = str.getBytes();
 9         byte[] testStr = baStr;
10         StringBuffer sb = new StringBuffer();
11         for (int i = 0; i < testStr.length; i++) {
12             sb.append(Integer.toBinaryString(testStr[i]) + " ");
13         }
14         System.out.println(sb.toString());
15     }

警告:绝不过滤富含图像等二进制内容的文本!那很恐怕会形成出口损坏。若是你同期具有文本文件和二进制文件作为能源,则须要表明八个互斥的能源集。第三个财富集定义要过滤的文件,另四个财富集定义要维持不变的文书。

 

以下则尚未难点

1.一旦将6行的str直接打字与印刷在页面上 则显得如下结果

<resources>            <resource>                <targetPath>${project.build.directory}/classes</targetPath>                <directory>src/main/resources</directory>                <filtering>true</filtering>                <excludes>                    <exclude>**/*.jasper</exclude>                    <exclude>**/*.jrxml</exclude>                </excludes>            </resource>            <resource>                <targetPath>${project.build.directory}/classes</targetPath>                <directory>src/main/resources</directory>                <filtering>false</filtering>                <includes>                    <include>**/*.jasper</include>                    <include>**/*.jrxml</include>                </includes>            </resource>
</resources>

新濠天地 1

 2.将第9行赋予baStr 则获得的二进制首两位值为

11111111111111111111111110101100(0xac) 11111111111111111111111111101101(0xed)

3.将第9行赋予gbStr 则赢得的二进制首两位值为

11111111111111111111111111101111(0xef) 11111111111111111111111110111111(0xbf)

(由于字符集和俄文原来的文章者不均等所以剖析出来的结果也不一致样)

发觉字符被改变了以关于ObjectOutputStream不可能识别该字符数组所以抛出了java.io.StreamCorruptedException: invalid stream header: EFBFBDEF

 

故此作者建议:

1.使用 toByteArray()代替toString() ,使用 ByteArrayInputStream(byte [])构造函数。

2.选用base64转变为字符串

注:LZ出现这么些主题素材是因为在maven打包项目标时候再度编写翻译了项目中的二进制文件进而破坏了二进制文件的完整性。所以该文件不恐怕反系列化。

附:maven打包跳过二进制文件

<plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-resources-plugin</artifactId>
                <configuration>
                    <!-- 防止二进制文件被编译 -->
                    <nonFilteredFileExtensions>
                        <nonFilteredFileExtension>dat</nonFilteredFileExtension>
                        <nonFilteredFileExtension>swf</nonFilteredFileExtension>
                        <nonFilteredFileExtension>xml</nonFilteredFileExtension>
                    </nonFilteredFileExtensions>
                </configuration>
            </plugin>
</plugins>

 

 斯洛伐克语原来的文章:

The provided test code serializes an object to a ByteArrayOutputStream, converts the generated byte array into a string using the ByteArrayOutputStream.toString() method, converts the string back into a byte array using the String.getBytes() method, and then attempts to deserialize the object from the byte array using a ByteArrayInputStream. This procedure will in most cases fail because of the transformations that take place within ByteArrayOutputStream.toString() and String.getBytes(): in order to convert the contained sequence of bytes into a string, ByteArrayOutputStream.toString() decodes the bytes according to the default charset in effect; similarly, in order to convert the string back into a sequence of bytes, String.getBytes() encodes the characters according to the default charset. Converting bytes into characters and back again according to a given charset is generally not an identity-preserving operation. As the javadoc for the String(byte[], int, int) constructor (which is called by ByteArrayOutputStream.toString()) states, "the behavior ... when the given bytes are not valid in the default charset is unspecified". In the test case provided, the first two bytes of the serialization stream, 0xac and 0xed (see java.io.ObjectStreamConstants.STREAM_MAGIC), both get mapped to the character '?' since they are not valid in the default charset (ISO646-US in the JDK I'm running). The two '?' characters are then mapped back to the byte sequence 0x3f 0x3f in the reconstructed data stream, which do not constitute a valid header. The solution, from the perspective of the test case, is to use ByteArrayOutputStream.toByteArray() instead of toString(), which will yield the raw byte sequence; this can then be fed directly to the ByteArrayInputStream(byte[]) constructor.

初稿地址

本文由新濠天地发布于编程网新闻,转载请注明出处:新濠天地所以转化对象时候会失败,inputStream读取

关键词:

上一篇:没有了

下一篇:步步领先,了解了题目大意就好解决了