Restlet实战(九)访问敏感资源之Digest认证

首先对所有的请求进行安全检验和认证,后面会给出对固定的URL进行安全认证的情况。对Restlet1.1.5来说,需要借助于Guard类来完成。

 

说一下大概的思路,建立一个Guard,并把它直接attach到Componet,当请求过来以后,会首先路由到这个Guard,如果通过认证,则路由到对应URL的Resource,否则,拦截掉。

 

首先修改Spring的配置文件:

 

Xml代码   收藏代码
  1. <bean id="component" class="org.restlet.ext.spring.SpringComponent">  
  2.     <property name="defaultTarget" ref="guard" />  
  3. </bean>  
  4.   
  5. <bean id="guard" class="com.mycompany.restlet.filter.CustomerGuardFilter">   
  6.     <property name="next" ref="restRoute"/>  
  7.     <property name="secretResolver" ref="customerResolver"/>   
  8. </bean>  
  9.   
  10. <bean id="customerResolver" class="com.mycompany.restlet.filter.CustomerResolver"/>  

 

从上述配置文件能看到,我们为SpringComponent的defaultTarget属性配置了一个Guard,当然这个是我们自己customized的一个Guard。而对于这个Guard,则指定其中的两个属性:next和secretResolver,next的意思是,如果通过校验和认证,则路由到下一个restlet实例,而secretResolver则是进行校验的地方。相关代码如下:

 

 

Java代码   收藏代码
  1. public class CustomerGuardFilter extends Guard {  
  2.   
  3.     public CustomerGuardFilter(Context context, ChallengeScheme scheme, String realm) {  
  4.         super(context, scheme, realm);  
  5.     }  
  6.       
  7.     public CustomerGuardFilter(){  
  8.         this(Context.getCurrent(), ChallengeScheme.HTTP_DIGEST, "realm");  
  9.     }  
  10.       
  11. }  

 

Java代码   收藏代码
  1. public class CustomerResolver extends Resolver<char[]> {  
  2.   
  3.     /** 
  4.      * Returns the value that corresponds to the given name. 
  5.      */  
  6.     @Override  
  7.     public char[] resolve(String name) {  
  8.         // Could have a look into a database, LDAP directory, etc.  
  9.         if ("login".equals(name)) {  
  10.             return "secret".toCharArray();  
  11.         }  
  12.   
  13.         return null;  
  14.     }  
  15.   
  16. }  

 

CustomerResolver类里面注释的地方,实际上就是我们在产品环境中从数据库或者LDAPdirectory或者别的地方取出密码的过程,这里,仅仅是为了测试,所以,直接硬编码了。

 

下面我们分别分别使用Restlet和Httpclient提供的API来编写客户端进行测试:

 

1.使用Restlet来测试

 

Java代码   收藏代码
  1. public static void testClientWithRestlet() {  
  2.     Reference reference = new Reference("http://localhost:8080/restlet/resources/customers");  
  3.     Client client = new Client(Protocol.HTTP);  
  4.     Request request = new Request(Method.GET, reference);  
  5.   
  6.     ChallengeResponse challengeResponse = new ChallengeResponse(ChallengeScheme.HTTP_DIGEST, "login""secret");  
  7.     request.setChallengeResponse(challengeResponse);  
  8.   
  9.     // Send the first request  
  10.     Response response = client.handle(request);  
  11.   
  12.     // Complete the challengeResponse object according to the server's data  
  13.     Form form = new Form();  
  14.     form.add("username""login");  
  15.     form.add("uri", reference.getPath());  
  16.   
  17.     // Loop over the challengeRequest objects sent by the server.  
  18.     for (ChallengeRequest challengeRequest : response.getChallengeRequests()) {  
  19.         // Get the data from the server's response.  
  20.         if (ChallengeScheme.HTTP_DIGEST.equals(challengeRequest.getScheme())) {  
  21.             Series<Parameter> params = challengeRequest.getParameters();  
  22.             form.add(params.getFirst("nonce"));  
  23.             form.add(params.getFirst("realm"));  
  24.             form.add(params.getFirst("domain"));  
  25.             form.add(params.getFirst("algorithm"));  
  26.             form.add(params.getFirst("qop"));  
  27.         }  
  28.     }  
  29.   
  30.     // Compute the required data  
  31.     String a1 = Engine.getInstance().toMd5("login" + ":" + form.getFirstValue("realm") + ":" + "secret");  
  32.     String a2 = Engine.getInstance().toMd5(request.getMethod() + ":" + form.getFirstValue("uri"));  
  33.     form.add("response", Engine.getInstance().toMd5(a1 + ":" + form.getFirstValue("nonce") + ":" + a2));  
  34.     challengeResponse.setCredentialComponents(form);  
  35.   
  36.     // Send the completed request  
  37.     request.setChallengeResponse(challengeResponse);  
  38.     response = client.handle(request);  
  39. }  

 

 2. 使用Httpclient测试

 

Java代码   收藏代码
  1. public static void testClientWithHttpclient() throws Exception{  
  2.     HttpClient client = new HttpClient();  
  3.     client.getState().setCredentials(  
  4.         new AuthScope("localhost"8080"realm"),  
  5.         new UsernamePasswordCredentials("login""secret"));  
  6.   
  7.     List<String> authPrefs = new ArrayList<String>();  
  8.     authPrefs.add(AuthPolicy.DIGEST);  
  9.     client.getParams().setParameter(AuthPolicy.AUTH_SCHEME_PRIORITY, authPrefs);  
  10.   
  11.     GetMethod httpget = new GetMethod("http://localhost:8080/restlet/resources/customers");  
  12.   
  13.     try {  
  14.         int status = client.executeMethod(httpget);  
  15.         // print the status and response  
  16.         System.out.println(status);  
  17.         System.out.println(httpget.getStatusLine());  
  18.         System.out.println(httpget.getResponseBodyAsString());  
  19.     } finally {  
  20.         // release any connection resources used by the method  
  21.         httpget.releaseConnection();  
  22.     }              
  23. }  

 

 

猜你喜欢

转载自chenjianfei2016.iteye.com/blog/2355187
今日推荐