2013-02-06 66 views
2

鉴于我无法创建任何新角色,因为它们是在CAS服务器中创建的,并且我没有对它们的任何控制,是否有一种方法可以保护仅打开的PDF文件如果用户既具有“客户”角色又具有“专业”角色?web.xml安全约束角色组合

换句话说,考虑到以下三个用户:

USER1只有“顾客”的角色 用户2具有“客户”和“专业”的角色 用户3具有“客户”和“专业”的角色 USER4有只有“专业”角色

只有user2和user3应该被允许看到PDF。

基本上,我想这样做:

<security-constraint> 
    <web-resource-collection> 
     <web-resource-name>auth</web-resource-name> 
     <url-pattern>/doc/profesionalCustomer.pdf</url-pattern> 
    </web-resource-collection> 
    <auth-constraint> 
     <role-name>professional,customer</role-name> 
    </auth-constraint> 
</security-constraint> 

这甚至可能吗?

预先感谢

回答

4

这是不可能使用声明安全(即经由web.xml)中。你可以只列出有访问资源的角色,如以下:

<security-constraint> 
<web-resource-collection> 
    <web-resource-name>auth</web-resource-name> 
    <url-pattern>/doc/profesionalCustomer.pdf</url-pattern> 
</web-resource-collection> 
<auth-constraint> 
    <role-name>professional</role-name> 
    <role-name>customer</role-name> 
</auth-constraint> 

但是在这种情况下,你会获得访问权要么专业或客户角色的所有用户这是不是你想。没有允许您为具有角色组合的用户授予访问权限的结构。

你可以采取的一种方法是以编程方式处理它:将客户端指向一个servlet,该servlet使用HttpServletRequest#isUserInRole(String)来检查用户是否具有客户和专业角色,并且它将请求转发给默认servlet检索pdf。此外,如果您想推迟什么组合角色被授予访问部署时间的权限,而不是在servlet中对其进行硬编码,则可以通过您的web.xml的/web-app/servlet/init-param或元素正确参数化servlet。

以下是摘录的web.xml将支持这一点:

<servlet> 
    <servlet-name>PDF Retriever</servlet-name> 
    <servlet-class>com.stackoverflow.PDFRetrieverServlet</servlet-class> 
</servlet> 
<servlet-mapping> 
    <servlet-name>PDF Retriever</servlet-name> 
    <url-pattern>/docs/pdf/*</url-pattern> 
</servlet-mapping> 
<security-constraint> 
    <web-resource-collection> 
     <web-resource-name>PDF Docs - customer and professional only</web-resource-name> 
     <url-pattern>/docs/pdf/*</url-pattern> 
    </web-resource-collection> 
    <auth-constraint> 
     <role-name>*</role-name> 
    </auth-constraint> 
</security-constraint> 
<security-constraint> 
    <web-resource-collection> 
     <web-resource-name>PDF Docs Private</web-resource-name> 
     <url-pattern>/private/pdf/*</url-pattern> 
    </web-resource-collection> 
    <auth-constraint> 
     <role-name /> 
    </auth-constraint> 
</security-constraint>` 

,这里是编码的servlet的doGet:

protected void doGet(HttpServletRequest request, 
    HttpServletResponse response) throws ServletException, IOException { 
    if (request.isUserInRole("customer") && request.isUserInRole("professional")) { 
     String urlSuffix = request.getPathInfo(); 
     RequestDispatcher rd = request.getRequestDispatcher("/private/pdf" 
       + urlSuffix); 
      rd.forward(request, response); 
    } else { 
      response.sendError(HttpServletResponse.SC_FORBIDDEN); 
    } 
} 
+0

谢谢你的回答。 我唯一担心的是,如果有人知道PDF文件的完整路径,他可以直接访问它,而无需任何控制。 – Pierpaolo

+0

@Pierpaolo我编辑了包含web.xml和servlet代码的答案。为了防止每个人访问PDF,您可以将URL放置在一个没有角色可以访问的保护区中(您的pdf文件实际位于/ private/pdf目录下) - 请注意第二个空角色名称元素安全性约束。唯一的访问是通过PDFRetrievalServlet。 – Nenad