Show image as byte[] from database as graphic image in JSF page
Asked Answered
R

2

4

I have image content as byte[] from database.

private byte[] image;

How can I show that byte array as a real graphic image in JSF page?

Ruel answered 2/6, 2015 at 21:1 Comment(0)
T
12

This is not directly possible with <h:graphicImage>. It can only point to an URL, not to a byte[] nor InputStream. Basically, you need to make sure that those bytes are directly available as a HTTP response on the given URL, which you can then use in <h:graphicImage> (or even plain HTML <img>).

Provided that you're identifying the image by its ID like so:

<h:graphicImage value="/image/#{someBean.imageId}" />

Here's a kickoff example of such a servlet:

@WebServlet("/image/*")
public class ImageServlet extends HttpServlet {

    @EJB
    private ImageService service;

    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        Long id = Long.valueOf(request.getPathInfo().substring(1));
        Image image = service.find(id);
        response.setContentType(getServletContext().getMimeType(image.getName()));
        response.setContentLength(image.getBytes().length);
        response.getOutputStream().write(image.getBytes());
    }

}

A more advanced abstract template for a static resource servlet, supporting HTTP caching, can be found in this answer, along with a concrete example for serving from database.

If you happen to use JSF utility library OmniFaces on a JSF 2.2 + CDI environment, then you can instead use its <o:graphicImage> which can be used much more intuitively.

<o:graphicImage value="#{imageBean.getBytes(someBean.imageId)}" />

@Named
@ApplicationScoped
public class ImageBean {

    @EJB
    private ImageService service;

    public byte[] getBytes(Long imageId) {
        return service.getImageBytes(imageId);
    }

}
Tanah answered 3/6, 2015 at 6:53 Comment(6)
i have only array of bytes from database nothing else, and i am using jsf so i have only managedBean, can you help me with thatRuel
Yes certainly. See above answer for kickoff examples of two possible ways. Just alter them if necessary to fit your situation.Tanah
@Balus May I ask what data type or from which package Image is in Image image = service.find(id); Is the Image image on that line a byte[], a Blob or something else? ThanksBender
@p3ace: It's just your custom class. See also a.o. https://mcmap.net/q/17327/-places-where-javabeans-are-used and https://mcmap.net/q/16811/-jsf-controller-service-and-daoTanah
@Balus Thank you. Still trying to absorb and understand every piece.Bender
2nd link ( <o:graphicImage> ) brokenSperm
L
5

Just bind one String variable to image on UI.

<img src="data:image/png;base64, "#{imageString}">

For example you are loading the image byte[] from database then first encode it in base 64 String.

String imageString= new String(Base64.encodeBase64(byte array fetched from database));
Leprosy answered 5/12, 2018 at 7:20 Comment(2)
although it might (does) work, page-caching wise this is not the best solution if you want to cache the page but refresh the image.Laggard
Hi all, this answer is correct but the img element is supposed to be written like this: <img src="data:image/png;base64,#{imageString}">Particulate

© 2022 - 2024 — McMap. All rights reserved.