2012-05-14 32 views
7

Tôi không thể truy cập thông tin Bảo mật mùa xuân trong một bài đăng đa servlet. Thông tin bảo mật mùa xuân có sẵn trong các phương thức nhận và gửi thông thường, nhưng không có sẵn cho phương thức đăng nhiều phần. Tôi đã cố gắng không thành công để truy cập thông tin bảo mật này trực tiếp thông qua SecurityContextHolder.getContext(). GetAuthentication() và thông qua một dịch vụ được tiêm để truy cập SecurityContextHolder.getContext(). GetAuthentication().Không thể truy cập thông tin Bảo mật mùa xuân trong một bài đăng đa truy cập servlet

Tôi cũng đã triển khai một HttpRequestHandler và một ServletWrappingController. Một lần nữa, tôi đã có thể tiêm đậu mùa xuân thành công vào chúng và truy cập thông tin Spring Security cho các phương thức get và post thông thường, nhưng tôi không thể truy cập thông tin Spring Security cho một bài viết nhiều phần. Tôi biết rằng có những khả năng MultiPart mới được tích hợp vào Spring 3.0 nhưng bởi vì trang web của chúng tôi sẽ yêu cầu truy cập đầy đủ vào luồng tải lên tệp, tôi sẽ không thể sử dụng chúng. Vì lý do đó, tôi đang tập trung vào HttpServlet, HttpRequestHandler và ServletWrappingController.

Mã tôi đăng ở đây là tất cả mã kiểm tra được viết để giải quyết vấn đề cụ thể này mà tôi đang gặp phải với thông tin bảo mật không khả dụng trong quá trình tải lên nhiều phần (không có nghĩa là chất lượng sản xuất). Nó dành cho một HttpServlet.

Vui lòng cho tôi biết nếu có điều gì đó tôi đang làm sai. Hoặc nếu không, nếu có cách giải quyết hoặc cách tốt hơn để thực hiện tải lên nhiều phần có quyền truy cập vào thông tin Bảo mật mùa xuân trong khi vẫn duy trì quyền truy cập vào luồng tải lên tệp? Bất kỳ sự hỗ trợ nào mà ai đó có thể cung cấp với vấn đề này sẽ được đánh giá cao!

Dưới đây là mã servlet thử nghiệm. Ý kiến ​​dưới đây như những gì làm việc và những gì không được dựa trên một người dùng đăng nhập vào trang web sử dụng Xuân An 3.1:

//many import statements not displayed 
import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.web.context.support.SpringBeanAutowiringSupport; 

import org.springframework.security.core.GrantedAuthority; 
import org.springframework.security.core.context.SecurityContextHolder; 

public class UploadServlet extends HttpServlet { 

    public void service(HttpServletRequest req, HttpServletResponse res) throws IOException, ServletException { 
     super.service(req, res); 
    } 

    public void init(ServletConfig config) throws ServletException { 
     super.init(config); 

     SpringBeanAutowiringSupport.processInjectionBasedOnServletContext(this, 
      config.getServletContext()); 
    } 


    //The following is always injected and available 
    //however, it only returns valid security information for regular get and post methods, 
    //not for multipart post methods 
    @Autowired 
    private CustomUserService customUserService; 

    //The following is always injected and available and always returns the expected data 
    @Autowired 
    private GuideService guideService; 

    //the following does not work when the client issues a multipart post, it does work for non-multipart 
    public boolean getAuthenticated(){ 
     boolean authorized = false; 

     for (GrantedAuthority authority : SecurityContextHolder.getContext().getAuthentication().getAuthorities()) { 
      if(authority.getAuthority().equals("ROLE_USER") || authority.getAuthority().equals("ROLE_ADMIN")) { 
       authorized = true; 
       break; 
      } 
     } 

     return authorized; 
    } 


    //The following test get method works fine 
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {   
     if(getAuthenticated()){ 
      PrintWriter out = resp.getWriter(); 
      out.write("<h1>Guide Info</h1><br/>"); 
      Guide guide = guideService.findById(2l); 
      out.write(guide.getName() + "<br/>"); 
      out.write(guide.getDescription() + "<br/>"); 
      out.write("UserName: " + customUserService.getCurrentUser().getUsername() + "<br/>"); 
     } 
     else{ 
      PrintWriter out = resp.getWriter(); 
      out.write("<h1>You're not authorized</h1><br/>"); 
     } 
    } 


    //This post method 
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 

     //the following always works, whether the clients posts using multipart or not  
     String guideName = guideService.findById(2l).getName(); 

     //the following does not work when the client issues a multipart post, it does work for non-multipart 
     String userName = customUserService.getCurrentUser().getUsername(); 

     //the following does not work when the client issues a multipart post, it does work for non-multipart 
     if(getAuthenticated()){ 
      String responseString = RESP_SUCCESS; 
      boolean isMultipart = ServletFileUpload.isMultipartContent(req); 

      if (isMultipart) { 
       ServletFileUpload upload = new ServletFileUpload(); 

       //commmons fileupload code 

      // Not a multi-part MIME request. 
      else { 
       //... 
      } 
      //... 
     } 
     else{ 
      //... 
     } 


    } 

} 

Dưới đây là phần có liên quan của web.xml:

<servlet> 
    <servlet-name>fgm</servlet-name> 
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> 
    <init-param> 
     <param-name>contextConfigLocation</param-name> 
     <param-value>WEB-INF/spring/webmvc-config.xml</param-value> 
    </init-param> 
    <load-on-startup>1</load-on-startup> 
</servlet> 

<servlet-mapping> 
    <servlet-name>fgm</servlet-name> 
    <url-pattern>/</url-pattern> 
</servlet-mapping> 

<servlet> 
    <servlet-name>UploadServlet</servlet-name> 
    <servlet-class>com.guides.servlet.UploadServlet</servlet-class> 
</servlet> 
<servlet-mapping> 
    <servlet-name>UploadServlet</servlet-name> 
    <url-pattern>/upload</url-pattern> 
</servlet-mapping> 
+0

Bạn có thể thêm phần web.xml hiển thị cấu hình Spring Security không? – Ritesh

+0

Tại sao bạn ánh xạ các yêu cầu tới 'UploadServlet' trong web.xml thay vì trong cấu hình Spring? –

Trả lời

0

Điều này có thể giúp bạn, nếu bạn đang sử dụng Spring MVC:

{ 
    @RequestMapping(method = RequestMethod.POST, value = "/some/post/url") 
    public void postFile(MultipartHttpServletRequest request) { 
    MultipartFile multipartFile = request.getFileMap().get("fileControlName"); 
    ... 
    } 
} 
+0

Bạn nên giải thích cách giải quyết vấn đề này. –

0

Chi tiết bảo mật được cung cấp bởi SecurityContextHolder (mặc định) được lưu trữ trong ThreadLocal.

Trình tải lên có tạo chuỗi mới để xử lý nhiều phần không? Hãy thử thay đổi SecurityContextHolderStrategy để MODE_INHERITABLETHREADLOCAL

vấn đề tương tự: How to set up Spring Security SecurityContextHolder strategy?

0

Nó có thể là giá trị kiểm tra như thế nào khách hàng của bạn đang thực hiện các bài đa phần, bạn đang sử dụng một cơ chế khác nhau/thư viện bài tiêu chuẩn của bạn?

Nếu tôi phải đoán tôi sẽ nói mã khách hàng của bạn không xác thực chính xác cho trường hợp sử dụng nhiều phần.

Ví dụ: Sử dụng Java tiêu chuẩn cho bài đăng bình thường và thư mục Apache cho bài đăng nhiều phần và quên đặt tiêu đề http thích hợp khi sử dụng nội dung của Apache.

2

Tôi có thể xác nhận rằng Spring 3.0.x và Spring Security 3.0.x cùng làm việc với các bài đăng nhiều phần cũng như chúng hoạt động với các loại yêu cầu khác. Tôi đã chạy vào hành vi tương tự, và trong trường hợp của chúng tôi, bộ lọc bảo mật đã không được áp dụng cho yêu cầu do lỗi của chúng tôi trong ánh xạ bộ lọc.

Bạn có thể đăng các phần trên web của mình không.xml xác định bộ lọc bảo mật và ánh xạ nó tới đường dẫn mong muốn?

Các vấn đề liên quan