Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Lift Integration with the Shiro security framework

tree: 44b7c8378e

Fetching latest commit…

Octocat-spinner-32-eaf2f5

Cannot retrieve the latest commit at this time

Octocat-spinner-32 example
Octocat-spinner-32 library
Octocat-spinner-32 notes
Octocat-spinner-32 project
Octocat-spinner-32 LICENSE.txt
Octocat-spinner-32 README.textile
Octocat-spinner-32 TODO.texile
README.textile

Lift Shiro

This is an initial version of integration between Apache Shiro and the Lift Web framework. Specifically this integration does not use Shiro’s built in web.xml resource filters to control access to URLs… it instead uses Lift’s sitemap Locs. In addition it also has a range of snippets for conditionally displaying content based on rules and permissions.

Usage

First, add the SBT dependency:

libraryDependencies += "eu.getintheloop" %% "lift-shiro" % "0.0.2-SNAPSHOT"

Next, you need to add this to the web.xml within your project in order to initialise the Shiro context when your application receives a request:

  <listener>
    <listener-class>org.apache.shiro.web.env.EnvironmentLoaderListener</listener-class>
  </listener>
  <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>
  </filter-mapping>

Next, you need to add some configuration to your Boot.scala like so:

class Boot {
  def boot {
    import shiro.Shiro
    import shiro.sitemap.Locs._
    Shiro.init()
    ...
  }
}

By default this uses the Shiro IniSecurityManagerFactory meaning you need to supply a shiro.ini at the root of your classpath that uses the Shiro ini configuration style. If however you want to use another security manager, you simply supply it into the init() method like so:

Shiro.init(new IniSecurityManagerFactory("classpath:shiro.ini"))

In order to actually use the integration within your sitemap to restrict access to resources, apply it to your SiteMap like so:

LiftRules.setSiteMap(SiteMap(List(
    Menu("Home") / "index" >> RequireAuthentication,
    Menu("Role Test") / "restricted" >> RequireAuthentication >> HasRole("admin"),
    Menu("Login") / "login" >> RequireNoAuthentication
    ) ::: Shiro.menus: _*
  ))

There are several LocParam that you can use to augment your Menu structure. Specifically you can use:

  • RequireAuthentication – Ensures that users are authenticated, irrespective of roles or permissions
  • HasRole("rolename") – Ensures that user has a specific role.
  • HasPermission("somePermission") – Ensures that user has a specific permission.
  • LacksPermission("permissionName") – Ensures that user lacks a specific permission.

In addition to using the integration in the SiteMap, you can also use it within your markup using the following snippet technique:

  <lift:has_role name="someRole">
    Some content that is only available to users who have the "someRole" role assigned to them
  </lift:has_role>

The snippets this integration wires in are the follow (all are methods on subject/subjects):

  • has_role
  • lacks_role
  • has_permission
  • lacks_permission
  • has_any_roles

All use the name attribute, with the exception of has_any_roles which takes the roles attribute which contains a comma-delimited list of assigned roles.

FAQ

  • Why did you bother making this? Well MegaProtoUberTron was not really for me, as I don’t typically want the user data stored within my application (i.e. im using AD, OpenDirectory etc)
  • In that case, why not just make the LDAP connection using javax.naming? Because i’m lazy, and frankly I dont want to have to maintain that code when someone else is already doing it (likely better than I would)
Something went wrong with that request. Please try again.