Question

L'une des actions de mon contrôleur de JPF édifie un fichier PDF et je voudrais revenir ce fichier à l'utilisateur afin qu'il puisse le télécharger.

Est-il possible de le faire ou que j'obligé d'écrire le fichier quelque part et avoir mon action avant un lien vers ce fichier? Notez que je voudrais éviter cela autant que possible pour des raisons de sécurité et parce que je n'ai aucun moyen de savoir quand l'utilisateur a téléchargé le fichier afin que je puisse le supprimer.

J'ai essayé d'accéder au HttpServletResponse, mais rien ne se passe:

getResponse().setContentLength(file.getSize());
getResponse().setContentType(file.getMimeType());
getResponse().setHeader("Content-Disposition", "attachment;filename=\"" + file.getTitle() + "\"");
getResponse().getOutputStream().write(file.getContent());
getResponse().flushBuffer();
Était-ce utile?

La solution

Nous avons quelque chose de similaire, à l'exception des images au lieu de revenir d'un document PDF; devrait être une solution similaire, bien que, je devine.

Sur une page JSP, nous avons une balise IMG, où le src est réglé sur:

<c:url value="/path/getImage.do?imageId=${imageID}" />

(je ne suis pas tout montrer, parce que je suis en train de simplifier.) Dans votre cas, il serait peut-être un lien, où le href se fait de la même manière.

Que des cartes getImage.do à notre contrôleur JPF, évidemment. Voici le code de la méthode getImage() JPF, qui est la partie que vous essayez de travailler sur:

@Jpf.Action(forwards = {
    @Jpf.Forward(name = FWD_SUCCESS, navigateTo = Jpf.NavigateTo.currentPage),
    @Jpf.Forward(name = FWD_FAILURE, navigateTo = Jpf.NavigateTo.currentPage) })
public Forward getImage(final FormType pForm) throws Exception {
  final HttpServletRequest lRequest = getRequest();
  final HttpServletResponse lResponse = getResponse();
  final HttpSession lHttpSession = getSession();
  final String imageIdParam = lRequest.getParameter("imageId");

  final long header = lRequest.getDateHeader("If-Modified-Since");
  final long current = System.currentTimeMillis();

  if (header > 0 && current - header < MAX_AGE_IN_SECS * 1000) {
    lResponse.setStatus(HttpServletResponse.SC_NOT_MODIFIED);
    return null;
  }

  try {
    if (imageIdParam == null) {
      throw new IllegalArgumentException("imageId is null.");
    }

    // Call to EJB, which is retrieving the image from
    // a separate back-end system
    final ImageType image = getImage(lHttpSession, Long
        .parseLong(imageIdParam));

    if (image == null) {
      lResponse.sendError(404, IMAGE_DOES_NOT_EXIST);
      return null;
    }

    lResponse.setContentType(image.getType());
    lResponse.addDateHeader("Last-Modified", current);
    // public: Allows authenticated responses to be cached.
    lResponse.setHeader("Cache-Control", "max-age=" + MAX_AGE_IN_SECS
        + ", public");
    lResponse.setHeader("Expires", null);
    lResponse.setHeader("Pragma", null);
    lResponse.getOutputStream().write(image.getContent());

  } catch (final IllegalArgumentException e) {
    LogHelper.error(this.getClass(), "Illegal argument.", e);
    lResponse.sendError(404, IMAGE_DOES_NOT_EXIST);
  } catch (final Exception e) {
    LogHelper.error(this.getClass(), "General exception.", e);
    lResponse.sendError(500);
  }
  return null;
}

Je l'ai effectivement retiré très peu de cette méthode, parce qu'il ya très peu de là-bas que je dois cacher des regards indiscrets - le code est assez générique, préoccupé par les images, non pas avec la logique métier. (Je l'ai changé quelques-uns des noms de type de données, mais pas une grosse affaire.)

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top