Отреагировать на длину содержимого выходного потока? - PullRequest
8 голосов
/ 18 ноября 2009

Я пишу в выходной поток различными способами.Как я могу, прежде чем закрыть его, узнать длину содержимого выходного потока?

Ответы [ 3 ]

16 голосов
/ 18 ноября 2009

Возможно, самый простой способ - обернуть его в другую реализацию OutputStream, которая перенаправляет все запросы на запись, но сохраняет внутренний счетчик. Тогда вы просто пишите об этом. Не должно быть слишком сложно для реализации - и действительно, возможно, уже есть.

РЕДАКТИРОВАТЬ: просто угадать разумное имя (CountingOutputStream) придумал реализацию в Apache Commons IO .

РЕДАКТИРОВАТЬ: Как отмечалось в другом месте, если это для HTTP и ваш клиент еще не выполняет буферизацию полных данных (в этом случае я бы подумал, это может определить длину содержимого) могут возникнуть проблемы из-за необходимости записи длины до записи данных. В некоторых случаях вы можете обнаружить, что он будет работать до определенного размера (который клиент буферизирует), а затем потерпит неудачу. В этом случае решения Дэвида будут уместны.

8 голосов
/ 18 ноября 2009

Проблема заключается в том, что вы должны установить длину содержимого в заголовке ответа, прежде чем начинать записывать какие-либо данные в выходной поток. Итак, ваши варианты:

  1. Запишите данные в массив byte [], используя ByteOutputStream, а затем скопируйте их в выходной поток ответа, как только вы получите размер данных. Однако, если вы пишете большие файлы, это явно не вариант.
  2. Запишите данные во временный файл, а затем скопируйте их в ответный вывод, как только вы получите размер файла. В зависимости от того, что вы делаете, это может привести к снижению производительности, что недопустимо.
  3. В зависимости от того, насколько дорогой является генерация данных, вы можете сгенерировать их один раз и выбросить, чтобы получить счетчик, а затем сгенерировать снова. Предполагая, что это вряд ли будет реалистичным решением.
  4. Смирись с тем, что ты не сможешь сообщить длину контента в заголовке ответа.
2 голосов
/ 18 ноября 2009

Вы можете записать в свой собственный ByteArrayOutputStream и сбросить его в поток вывода ответа в самом конце.

...