How to prevent accessing a Servlet unauthenticated with Apache Shiro?

1k Views Asked by At

I am using Apache Shiro for my web application's admin authentication. All the admin content is placed under the /admin directory and I have an AdminServlet that handles the requests to the admin features. The Admin Servlet's URL mapping is /Admin. Shiro successfully intercepts the request and redirects to the login page if the user wants to access something under /admin. However, I type in /Admin to the URL bar of the browser I can essentially bypass Shiro and get to the admin page without authentication. How can I protect my servlet so that it only performs a request if it is authenticated?

Here's the relevant bits of my code:

shiro.ini:

[main]
shiro.loginUrl = /login.jsp
[urls]
/login.jsp = authc
/logout = logout
/admin/** = authc

web.xml:

<servlet>
    <servlet-name>AdminServlet</servlet-name>
    <servlet-class>mypackage.servlet.AdminServlet</servlet-class>
</servlet>
<servlet-mapping>
    <servlet-name>AdminServlet</servlet-name>
    <url-pattern>/Admin</url-pattern>
</servlet-mapping>

<filter>
    <filter-name>ShiroFilter</filter-name>
    <filter-class>org.apache.shiro.web.servlet.ShiroFilter</filter-class>
</filter>

<filter-mapping>
    <filter-name>ShiroFilter</filter-name>
    <url-pattern>/*</url-pattern>
    <dispatcher>REQUEST</dispatcher>
    <dispatcher>FORWARD</dispatcher>
    <dispatcher>INCLUDE</dispatcher>
    <dispatcher>ERROR</dispatcher>
</filter-mapping>

Whatever functionality the servlet has, it always ends up creating a RequestDispatcher forwarding to some file located under /admin.

I tried putting /Admin/** (as the servlet URL mapping) into the shiro.ini file to be an authenticated content but as a result I kept getting redirected to the login page after submitting the credentials.

Thank you in advance!

1

There are 1 best solutions below

1
On BEST ANSWER

Try this:

  1. Your Admin Servlet url-pattern like this:
  <url-pattern>/admin/*</url-pattern>
  1. Add this to your web.xml:
  <listener>
     <listener-class>org.apache.shiro.web.env.EnvironmentLoaderListener</listener-class>
  </listener>
  1. Replace your filter-mapping with this:
  <filter-mapping>
     <filter-name>ShiroFilter</filter-name>
     <url-pattern>/*</url-pattern>
  </filter-mapping>

Your shiro.xml:

  [main]
  shiro.loginUrl = /login.jsp
  [urls]
  /login.jsp = authc
  /logout = logout
  /admin/** = authc

Hope that helps!