play中@With注解的用法

一:Play框架中应用@With注解主要作用是在某个action执行之前先执行@with注解申明的action,一般用来做权限安全控制。play权限安全控制主要有3个方法。

  1. @Security.Authenticated on each Action -------------------->在action之前用@Security.Authenticated注解
  2. @With using a custom Action  --------------------------------->在action调用之前用@With注解调用自定义的action
  3. @With on a controller using a custom Action--------------->在控制器类前用@With注解


二:

(1).@Security.Authenticated

我将使用最基本的token-based验证来演示,模型层的模型如下。


<span style="font-size:18px;">public User extends Model {  
    @Id
    public Integer id;
    public String username;
    public String authToken;

    public static Finder<Integer,User> find = new Finder(Integer.class, User.class);
}</span>

@Security.Authenticated注解会被所有使用该注解的action执行校验,它默认会调用类Security.Authenticator中的方法getUsername(Http.Context ctx),尝试取出session cookies中存储的username,如果username存在,那么被注解修饰的action会正常的执行,如果username不存在,那么会返回401错误码。

幸运的是,我们可以实现我们自己的认证器Authenticator去检查authentication token。代码如下:

public class ActionAuthenticator extends Security.Authenticator {  
    @Override
    public String getUsername(Http.Context ctx) {
        String token = getTokenFromHeader(ctx);
        if (token != null) {
            User user = User.find.where().eq("authToken", token).findUnique();
            if (user != null) {
                return user.username;
            }
        }
        return null;
    }

    @Override
    public Result onUnauthorized(Http.Context context) {
        return super.onUnauthorized(context);
    }

    private String getTokenFromHeader(Http.Context ctx) {
        String[] authTokenHeaderValues = ctx.request().headers().get("X-AUTH-TOKEN");
        if ((authTokenHeaderValues != null) && (authTokenHeaderValues.length == 1) && (authTokenHeaderValues[0] != null)) {
            return authTokenHeaderValues[0];
        }
        return null;
    }
}

控制器中使用该自定义的 Authenticator
<span style="font-size:18px;">@Security.Authenticated(ActionAuthenticator.class)
public static Result awesomeAction() {
    return ok("Very awesome content!");
}</span>

(2)@With using a custom Action

@With注解在目标action执行之前执行,我们可以使用该注解来对我们的权限安全进行验证。代码如下:

<span style="font-size:18px;">public class SecuredAction extends Action.Simple {  
    public F.Promise<Result> call(Http.Context ctx) throws Throwable {
        String token = getTokenFromHeader(ctx);
        if (token != null) {
              User user = User.find.where().eq("authToken", token).findUnique();
              if (user != null) {
                  ctx.request().setUsername(user.username);
                  return delegate.call(ctx);
              }
        }
        Result unauthorized = Results.unauthorized("unauthorized");
        return F.Promise.pure(unauthorized);
    }

    private String getTokenFromHeader(Http.Context ctx) {
        String[] authTokenHeaderValues = ctx.request().headers().get("X-AUTH-TOKEN");
        if ((authTokenHeaderValues != null) && (authTokenHeaderValues.length == 1) && (authTokenHeaderValues[0] != null)) {
            return authTokenHeaderValues[0];
        }
        return null;
    }
}</span>

现在我们在我们的目标action上使用该注解

<span style="font-size:18px;">@With(SecuredAction.class)
public static Result anotherAwesomeAction() {
	return ok("The best content!");
}</span>

(3)@With on a controller using a custom Action

有时候我们每个目标都需要在目标action执行之前检查权限安全,若此时给每个目标action都标记上@With注解,这显然是很繁琐的,幸运的是我们可以通过在控制器类上使用该注解来达到控制器中每个目标action执行之前都先执行注解标记的action,这样就大大提高了开发效率,并且易于维护。代码如下:

<span style="font-size:18px;">@With(SecuredAction.class)
public class SomeController extends Controller {
	...
}</span>

还有一种情况就是我不想在controller控制器上使用注解该怎么办,抑或我有多个控制器都需要使用该注解,办法很简单,如下:

<span style="font-size:18px;">@With(SecuredAction.class)
public abstract class SecuredController extends Controller {}</span>

<span style="font-size:18px;">public class SomeOtherController extends SecuredController {
	...
}</span>


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值