Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
68 changes: 36 additions & 32 deletions example/src/main/resources/shiro.ini
Original file line number Diff line number Diff line change
Expand Up @@ -4,37 +4,41 @@
# For those that might not understand the references in this file, the
# definitions are all based on the classic Mel Brooks' film "Spaceballs". ;)
# =============================================================================
[main]
myRealm = example.ExampleRealm

# -----------------------------------------------------------------------------
# Users and their assigned roles
#
# Each line conforms to the format defined in the
# org.apache.shiro.realm.text.TextConfigurationRealm#setUserDefinitions JavaDoc
# -----------------------------------------------------------------------------
[users]
# user 'root' with password 'secret' and the 'admin' role
root = secret, admin
# user 'guest' with the password 'guest' and the 'guest' role
guest = guest, guest
# user 'presidentskroob' with password '12345' ("That's the same combination on
# my luggage!!!" ;)), and role 'president'
presidentskroob = 12345, president
# user 'darkhelmet' with password 'ludicrousspeed' and roles 'darklord' and 'schwartz'
darkhelmet = ludicrousspeed, darklord, schwartz
# user 'lonestarr' with password 'vespa' and roles 'goodguy' and 'schwartz'
lonestarr = vespa, goodguy, schwartz
# Uncomment the below to use simple static configuration instead of a custom realm.

# -----------------------------------------------------------------------------
# Roles with assigned permissions
#
# Each line conforms to the format defined in the
# org.apache.shiro.realm.text.TextConfigurationRealm#setRoleDefinitions JavaDoc
# -----------------------------------------------------------------------------
[roles]
# 'admin' role has all permissions, indicated by the wildcard '*'
admin = *
# The 'schwartz' role can do anything (*) with any lightsaber:
schwartz = lightsaber:*
# The 'goodguy' role is allowed to 'drive' (action) the winnebago (type) with
# license plate 'eagle5' (instance specific id)
goodguy = winnebago:drive:eagle5
## -----------------------------------------------------------------------------
## Users and their assigned roles
##
## Each line conforms to the format defined in the
## org.apache.shiro.realm.text.TextConfigurationRealm#setUserDefinitions JavaDoc
## -----------------------------------------------------------------------------
#[users]
## user 'root' with password 'secret' and the 'admin' role
#root = secret, admin
## user 'guest' with the password 'guest' and the 'guest' role
#guest = guest, guest
## user 'presidentskroob' with password '12345' ("That's the same combination on
## my luggage!!!" ;)), and role 'president'
#presidentskroob = 12345, president
## user 'darkhelmet' with password 'ludicrousspeed' and roles 'darklord' and 'schwartz'
#darkhelmet = ludicrousspeed, darklord, schwartz
## user 'lonestarr' with password 'vespa' and roles 'goodguy' and 'schwartz'
#lonestarr = vespa, goodguy, schwartz
#
## -----------------------------------------------------------------------------
## Roles with assigned permissions
##
## Each line conforms to the format defined in the
## org.apache.shiro.realm.text.TextConfigurationRealm#setRoleDefinitions JavaDoc
## -----------------------------------------------------------------------------
#[roles]
## 'admin' role has all permissions, indicated by the wildcard '*'
#admin = *
## The 'schwartz' role can do anything (*) with any lightsaber:
#schwartz = lightsaber:*
## The 'goodguy' role is allowed to 'drive' (action) the winnebago (type) with
## license plate 'eagle5' (instance specific id)
#goodguy = winnebago:drive:eagle5
5 changes: 4 additions & 1 deletion example/src/main/scala/bootstrap/liftweb/Boot.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package bootstrap.liftweb

import net.liftweb.http.LiftRules
import net.liftweb.http.{Html5Properties, LiftRules, Req}
import net.liftweb.sitemap._
import shiro.Shiro
import shiro.sitemap.Locs._
Expand All @@ -17,5 +17,8 @@ class Boot {
Menu("Login") / "login" >> DefaultLogin >> RequireNoAuthentication
) ::: Shiro.menus: _*
))

LiftRules.htmlProperties.default.set((r: Req) =>
new Html5Properties(r.userAgent))
}
}
83 changes: 83 additions & 0 deletions example/src/main/scala/example/ExampleRealm.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
package example

import org.apache.shiro.realm.AuthorizingRealm
import org.apache.shiro.authc._
import org.apache.shiro.authz._
import org.apache.shiro.authz.permission.WildcardPermission
import org.apache.shiro.subject.PrincipalCollection

import collection.JavaConverters._

/**
* An example class to demonstrate setting up a custom realm in shiro.
*/
class ExampleRealm extends AuthorizingRealm {
class User(val username: String, val password: String)

/**
* A fake DAO for storing user credentials, roles, permissions, etc.
* In practice this will probably be a db/persistence obj of some sort.
*/
object UserDAO {
// Passwords are stored plain here but in real life please at least BCrypt them like a decent human being.
private[this] val userCredentials = Map(
"root" -> "secret",
"guest" -> "guest",
"presidentskroob" -> "12345",
"darkhelmet" -> "ludicrousspeed",
"lonestarr" -> "vespa"
)

private[this] val userRoles = Map(
"root" -> Set("admin"),
"guest" -> Set("guest"),
"presidentskroob" -> Set("president"),
"darkhelmet" -> Set("darklord", "schwartz"),
"lonestarr" -> Set("goodguy", "schwartz")
)

private[this] val rolePermissions = Map(
"admin" -> Set(new WildcardPermission("*")),
"schwartz" -> Set(new WildcardPermission("lightsaber:*")),
"darklord" -> Set(new WildcardPermission("winnebago:steal:eagle5")),
// Good guys can do whatever they want with the eagle5.
"goodguy" -> Set(new WildcardPermission("winnebago:*:eagle5"))
)

def getUser(username: String, password: String): Option[User] = for {
pass <- userCredentials.get(username)
if (pass == password)
} yield new User(username, password)

def getRoles(user: User): Set[String] = {
userRoles.getOrElse(user.username, Set())
}

def getRolePermissions(role: String): Set[WildcardPermission] = {
rolePermissions.getOrElse(role, Set())
}
}

// The methods from AuthorizingRealm that actually have to be implemented.

def doGetAuthenticationInfo(token: AuthenticationToken): AuthenticationInfo = {
val userpassToken = token.asInstanceOf[UsernamePasswordToken]
val username = userpassToken.getUsername()
val password = userpassToken.getPassword()

UserDAO.getUser(username, password.mkString("")) match {
case Some(user: User) => new SimpleAuthenticationInfo(user, user.password, "ExampleRealm")
case None => throw new AuthenticationException("Invalid credentials provided!")
}
}

def doGetAuthorizationInfo(principals: PrincipalCollection): AuthorizationInfo = {
val roles: Set[String] = principals.asScala.flatMap(p => UserDAO.getRoles(p.asInstanceOf[User])).toSet
val permissions: Set[Permission] = roles.flatMap(r => UserDAO.getRolePermissions(r)).toSet

val authInfo = new SimpleAuthorizationInfo(roles.asJava)
authInfo.setObjectPermissions(permissions.asJava)

return authInfo
}
}
29 changes: 21 additions & 8 deletions example/src/main/webapp/index.html
Original file line number Diff line number Diff line change
@@ -1,8 +1,21 @@
<lift:surround with="default" at="content">
<h2>Home</h2>

<lift:has_role name="admin">
<p>This content is only available for admins</p>
</lift:has_role>

</lift:surround>
<html>
<head>
<title>Lift Shiro</title>
</head>
<body class="lift:content_id=content">
<div id="content" data-lift="surround?with=default;at=content">
<h2>Home</h2>

<div data-lift="has_role?name=admin">
<p>This content is only available for admins</p>
</div>

<div data-lift="has_permission?name=winnebago:drive:eagle5">
<p>Whoooooosh, you can drive the eagle5!</p>
</div>
<div data-lift="has_permission?name=winnebago:steal:eagle5">
<p>Sneaky sneaky, you can steal the eagle5!</p>
</div>
</div>
</body>
</html>
26 changes: 16 additions & 10 deletions example/src/main/webapp/login.html
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
<lift:surround with="default" at="content">
<h2>Login</h2>

<form lift="login?form=post">
<p>Username: <br /><input type="text" /></p>
<p>Password: <br /><input type="password" /></p>
<p><input type="submit" value="login" /></p>
</form>

</lift:surround>
<html>
<head>
<title>Lift Shiro</title>
</head>
<body class="lift:content_id=content">
<div id="content" data-lift="surround?with=default;at=content">
<h2>Login</h2>

<form data-lift="login?form=post">
<p>Username: <br /><input type="text" /></p>
<p>Password: <br /><input type="password" /></p>
<p><input type="submit" value="login" /></p>
</form>
</div>
</body>
</html>
13 changes: 10 additions & 3 deletions example/src/main/webapp/restricted.html
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
<lift:surround with="default" at="content">
<h2>Restricted to admin</h2>
</lift:surround>
<html>
<head>
<title>Lift Shiro</title>
</head>
<body class="lift:content_id=content">
<div id="content" data-lift="surround?with=default;at=content">
<h2>Restricted to admin</h2>
</div>
</body>
</html>
14 changes: 8 additions & 6 deletions example/src/main/webapp/templates-hidden/default.html
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,15 @@
<head>
<meta http-equiv="content-type" content="text/html; charset=UTF-8" />
<title>Lift Shiro</title>
<script id="jquery" src="/classpath/jquery.js" type="text/javascript" />
<script id="jquery" src="/classpath/jquery.js" type="text/javascript"></script>
</head>
<body>
<lift:menu.builder />
<hr />
<lift:bind name="content" />
<hr />
<lift:msgs showAll="true" />
<div id="content_frame">
<div data-lift="Menu.builder"></div>
<hr />
<div id="content"></div>
<hr />
<div data-lift="msgs?showAll=true"></div>
</div>
</body>
</html>