#jakarta-ee #servlets #download #jsf-2.2 #ajax4jsf
#джакарта-ee #сервлеты #Скачать #jsf-2.2 #ajax4jsf
Вопрос:
Это мой первый вопрос по SO.
Я хотел бы создать файл отчета сразу после импорта другого файла с некоторыми бизнес-элементами.
После выбора import file with h:inputFile
я запускаю действие компонента с h:commandButton
помощью и вложенный a4j:ajax
:
FacesContext facesContext = FacesContext.getCurrentInstance();
try {
HttpServletRequest req = (HttpServletRequest) facesContext.getExternalContext().getRequest();
HttpServletResponse res = (HttpServletResponse) facesContext.getExternalContext().getResponse();
byte[] byteSourceExcelFile = IOUtils.toByteArray(sourceExcelFile.getInputStream());
req.setAttribute("excel", DatatypeConverter.printBase64Binary(byteSourceExcelFile));
RequestDispatcher dispatcher = req.getRequestDispatcher("importReport.jsf");
dispatcher.forward(req, res);
} catch (IOException e) {
FacesUtils.createErrorMessage(e.getMessage(), null, msgs);
} catch (ServletException e) {
FacesUtils.createErrorMessage(e.getMessage(), null, msgs);
} finally {
facesContext.responseComplete();
fileClear();
}
Запрос перенаправляется на сервлет, где импорт работает хорошо, но когда я пытаюсь получить объект, необходимый для вывода двоичных данных:
ServletOutputStream outputStream = response.getOutputStream();
Я получаю сообщение об ошибке:
org.apache.myfaces.view.facelets.el.ContextAwareELException: javax.el.ELException: java.lang.IllegalStateException: SRVE0209E: Writer already obtained
Я отладил код сервлета и заметил, что поле _gotWriter
имеет значение true в объекте ответа. Это указывает на то, что:
PrintWriter outputStream = response.getWriter();
. Ни один из моих фильтров этого не сделал. Кроме того, другие сервлеты, которые используются для получения данных, работают нормально.
Использование MyFaces 2.2.3 в качестве общей библиотеки в WebSphere 8.5.5.
Механизм, описанный выше, работает с реализацией Websphere 7 JSF (Sun-RI 1.2) и компонентом Richfaces (3.3.3) rich:FileUpload.
- Каковы возможные причины описанного состояния объекта ответа?
- Есть ли какой-нибудь способ заменить
PrintWriter
object наServletOutputStream
object ?
Я надеюсь, что это подходящий способ задать вопрос. Я буду признателен за любые предложения.
Комментарии:
1. Ваш код не вызывался
response.getWriter()
, но фреймворк реализации JSF вызвал.2. @Isaac Почему это происходит в данном конкретном случае (а не в других)?
3. если бы я знал, я бы написал это как ответ… но ошибка, которую вы получаете, подразумевает, что что- то вызывается
response.getWriter()
, поэтому, если это не ваш код, тогда это должна быть реализация JSF. Я не эксперт по JSF, поэтому не могу комментировать дальше, извините.
Ответ №1:
Все дело a4j:ajax
во вложенности h:commandButton
. Оказывается, это было причиной вызова response.getWriter()
в середине обработки запроса (я до сих пор не знаю, где и почему).
<h:commandButton action="#{listBean['processImport']}" >
<a4j:ajax oncomplete="js();" execute="fileUploadId" render="fileUploadId"/>
</h:commandButton>
Я удалил a4j:ajax
, и загрузка файла работает так, как и предполагалось.
<h:commandButton action="#{listBean['processImport']}" onclick="js();">
</h:commandButton>
Теперь мне нужно выяснить, как обновить желаемые элементы на странице jsf. Но это другая история…
Приложение: JSF 1.2
Стоит упомянуть, что перед переходом с WAS-7 (Sun-RI 1.2) на WAS-8.5.5 (MyFaces 2.2.3) вышеупомянутый механизм работает с комбинацией:
<h:commandButton action="#{listBean['processImport']}" >
<a4j:support oncomplete="js();" reRender="fileUploadId"/>
</h:commandButton>
но не сработало с:
<a4j:commandButton action="#{listBean['processImport']}" oncomplete="js();" reRender="fileUploadId" />
РЕДАКТИРОВАТЬ: После последнего обновления безопасности IE 14-037 (KB2962872) файл принимается браузером, но больше не может быть открыт или сохранен.
Ответ №2:
response.getOutputStream() и response.getWriter() не должны вызываться одновременно. Вам нужно проверить, есть ли какие-либо выходные данные в importReport.jsf. Если да, удалите их или используйте отдельный класс для обработки логики импорта.
Комментарии:
1. Я бы ожидал, что это также сломается под WAS 7.0. В OP говорится, что код работает на WAS 7.