Image servlet security, allow calls from JSP/JSF only, not standalone

I have developed an image servlet which can dynamically retrieve and display local images in JSP/JSF pages, using file names. This works as follows:

JSF<h:graphicImage value="image?file=test.jpg" />

But I found out that this can also be called directly by the browser:

http://www.example.com/webapplication/image?file=test.jpg

Which can be a security risk, because the you can do something like:

http://www.example.com/webapplication/image?file=/etc/usr/password.txt

I have several options:

1) In the imageservlet, check if the file extension is valid (gif, jpg, jpeg, etc)

2) Put images in one map and strip the file path, keeping filename.ext.

3) Disallow the user to call http://www.example.com/webapplication/image directly. Only allow the call to /image by the running JSP/JSF files.

1) and 2) are easy to implement, but I like to apply the solution described at 3). Can someone explain me how to implement this? I know this have to be done in web.xml, but it's not clear to me how to do.

[1092 byte] By [BalusCa] at [2007-10-3 0:09:14]
# 1

That depends on what the h:graphicImage element does. Is it some kind of server-side include, or does it generate HTML that links to that servlet?

If it generates HTML that links to the servlet, then the browser is going to follow the link just the same way it would follow a link typed into its address bar.

DrClapa at 2007-7-14 16:58:13 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...
# 2
Yes, it generates HTML as <img>.But there is no way to restrict the accessibility from a servlet? On the other hand, is there any way to check in the HttpServletRequest whether the servlet is called by an JSF/JSP page or directly by the browser?
BalusCa at 2007-7-14 16:58:13 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...
# 3

> Yes, it generates HTML as <img>.

>

> But there is no way to restrict the accessibility

> from a servlet?

No. The requests come from the browser who doesn't know anything about a servlet or JSP or whatever. A page is a page is a page to the browser. So it can't inform the image-getter that it was called from a servlet, since it doesn't know.

> On the other hand, is there any way

> to check in the HttpServletRequest whether the

> servlet is called by an JSF/JSP page or directly by

> the browser?

You could try using the Referrer header. This would onlybe set if the request was made by a click on a previous page (be it JSP, servlet, or regular HTML), and not if typed into the address bar. But not all browsers use the Referrer header so you may get a lot of false negatives.

String referrer = request.getHeader("Referrer");

//if referrer ends with .jsp or .jsf do something

//if referrer is null don't do domething

Another thought...

This h:graphicImage is used inside a JSP/JSF page, correct? At the very top of that page you could add a value to the user's session that says 'this user is okay'. On the request made to h:graphicImage you would check if that session variable exists, if it does proceed to the image download, otherwise skip it. At the end, remove the session variable.

stevejlukea at 2007-7-14 16:58:13 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...
# 4

Using referrer header is also a good idea, but as you can easily fake the referrer this is not a solution to me.

Using an user session value isn't a bad idea. I will have a thorough look for it. I already have tested whether the current instance of the faces context is visible in the image servlet, but despitely it is not. Or is there another way to get the facescontext (or session) in the servlet?

Otherwise I'll look if it is possible to use a backing bean for this purpose, which can provide much more security.

BalusCa at 2007-7-14 16:58:13 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...
# 5
OK, I got it well-working thanks to http://wiki.apache.org/myfaces/AccessFacesContextFromServletIn the image servlet: if there is no facescontext available, then do nothing. I also have more room to play in :)
BalusCa at 2007-7-14 16:58:13 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...