InputStream закрывает и проблемы с сонаром - PullRequest
1 голос
/ 26 апреля 2019

У меня есть следующий код, чтобы открыть ZIP-файл, который содержит несколько файлов и извлекает информацию из каждого файла:

public static void unzipFile(InputStream zippedFile) throws IOException {
  try (ZipInputStream zipInputStream = new ZipInputStream(zippedFile)) {
    for (ZipEntry zipEntry = zipInputStream.getNextEntry(); zipEntry != null; zipEntry = zipInputStream.getNextEntry()) {
      BufferedReader reader = new BufferedReader(new InputStreamReader(new BoundedInputStream(zipInputStream, 1024)));
      //Extract info procedure...
    } 
  }
}

В итоге я выбираю каждый файл из ZIP-файла и открываю его с помощьюBufferedReader чтобы прочитать информацию с него.Я также использую BoundedInputStream (org.apache.commons.io.input.BoundedInputStream), чтобы ограничить размер буфера и избежать нежелательных огромных строк в файлах.

Это работает, как и ожидалось, однако я получаю предупреждение на Sonar:

Use try-with-resources or close this "BufferedReader" in a "finally" clause.

Я просто не могу закрыть (или использовать try-with-resources , как я делал в начале метода) создаваемые мной BufferedReaders - если я вызываю метод close,ZipInputStream закроется.И ZipInputStream уже находится под try-with-resources ...

Это уведомление гидролокатора помечено как критическое, но я считаю, что оно является ложным срабатыванием.Интересно, не могли бы вы уточнить для меня - я прав или я должен поступить иначе?Я не хочу оставлять утечки ресурсов в коде, поскольку этот метод будет вызываться несколько раз, и утечка может привести к серьезному повреждению.

Ответы [ 2 ]

1 голос
/ 26 апреля 2019

Благодаря ответам здесь я мог бы решить свою проблему следующим образом:

BoundedInputStream boundedInputStream = new BoundedInputStream(zipInputStream, MAX_LINE_SIZE_BYTES);
boundedInputStream.setPropagateClose(false);

try(BufferedReader reader = new BufferedReader(new InputStreamReader(boundedInputStream))) { ...

С помощью boundedInputStream.setPropagateClose(false); я могу закрыть BufferedReader, не закрывая zipInputStream.

1 голос
/ 26 апреля 2019

Сонарное уведомление верно в том смысле, что технически существует утечка ресурсов, которая со временем может поглотить ресурсы (см. сборка мусора и классы ввода-вывода ). Чтобы не закрывать базовый ZipInputStream, рассмотрите возможность передачи ZipEntry в BoundedInputStream в цикле for согласно следующему вопросу SO: чтение файлов в zip-файле . Таким образом, когда BufferedReader закрыт, BoundedInputStream закрыт, а не ZipInputStream.

...