getOutputStream() has already been called for this response


 

錯誤日志里偶爾會有getOutputStream() has already been called for this response這個錯誤

最近發現了高概率復現條件,所以順手解決了一下:

 

首先根據這個錯誤關鍵信息,得知是錯誤產生原因是response.getWriter()和response.getOutputStream()等接口在調用時發生了資源占用

然而事實上在這個項目中並沒有使用response.getWriter()和response.getOutputStream(),那么就需要更深入的去查找錯誤的原因

首先高概率復現條件是在進行redis操作的時候,這兩個接口是進行流輸出的接口,根據關鍵字查找,從redis相關操作中發現了一行序列化操作有進行流相關的操作。

復制代碼
    public static byte[] serialize(Object object) throws Exception {
        ObjectOutputStream oos = null;
        ByteArrayOutputStream baos = null;
        try {
            // 序列化
            baos = new ByteArrayOutputStream();
            oos = new ObjectOutputStream(baos);
            oos.writeObject(object);
            byte[] bytes = baos.toByteArray();
            return bytes;
        } catch (Exception e) {
            throw e;
        }
    }
復制代碼

八成就是這里沒有close導致的bug了。再往深了看:

其中ByteArrayOutputStream用於捕獲內存緩沖區的數據,轉換成字節數組,但有趣的是對一個ByteArrayOutputStream進行close()操作沒有任何效果,而且這樣寫不會產生重復關閉導致的Exception。

ObjectOutputStream用於進行序列化,這個沒有close應該就是罪魁禍首了,但保險起見,還是兩個操作都加上Close()

修改后代碼如下:

復制代碼
public static byte[] serialize(Object object) throws Exception {
        ObjectOutputStream oos = null;
        ByteArrayOutputStream baos = null;
        try {
            // 序列化
            baos = new ByteArrayOutputStream();
            oos = new ObjectOutputStream(baos);
            oos.writeObject(object);
            byte[] bytes = baos.toByteArray();
oss.close(); baos.close(); return bytes; } catch (Exception e) { throw e; } finally { if(oos != null){ oos.close(); } if(baos != null){ baos.close(); } } }
復制代碼

問題解決!

https://www.cnblogs.com/Orange42/p/6168803.html

 

https://stackoverflow.com/questions/1776142/getoutputstream-has-already-been-called-for-this-response

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM