Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using intercept-url in Spring security

What is the preferred way of making patterns in the intercept-url element in Spring security? I am creating a web service (RESTful) and I currently require that all users are logged in and have the role ROLE_USER. Then further constraints are enforced by @PreAuthorize annotations on the service layer. However is it common to also add multiple intercept-url elements that have different configuration?

like image 582
LuckyLuke Avatar asked May 12 '13 17:05

LuckyLuke


People also ask

How do I intercept a URL in Spring Security?

Most web applications using Spring Security only have a couple of intercept-url s because they only have very basic security requirements. You need to have unauthenticated access to the login and login-error screens and usually some aspect of the public site, so that can be a few URL patterns.

How does hasRole works in Spring Security?

By default, Spring Security uses a thread-local copy of this class. This means each request in our application has its security context that contains details of the user making the request. To use it, we simply call the static methods in SecurityContextHolder: Authentication auth = SecurityContextHolder.


1 Answers

I should think that "the preferred way" is [necessarily] subjective. I had <intercept-url> elements in my security.xml, but abandoned them in favor of @RequestMapping annotations with @PreAuthorize on the controllers. It's purely personal preference (in my case), as I favor keeping things in Java rather than in XML namespaces, as much as it is possible to do so.

You can use one, the other, or both, and you can make the annotation enhance the XML -- you can, for example have something like the following:

security.xml:

<intercept-url pattern="/something" access="hasRole('ROLE_USER')"/>

YourController.java:

@RequestMapping(value="/something/else")
@PreAuthorize("hasRole('ROLE_ADMIN')")
public String getSomethingElseContents(){ return "somethingelse"; }

As I said, it seems like it's merely a matter of preference. The benefit to using the XML namespace is that the base access rules are all in one place, easy to read, and easy to follow. The rules imposed by @PreAuthorize (or the other annotation variants) are particularly sexy because you can call your own SpEL expression in them, and base your permission decision on access to parameters passed or fields accessible by the class (i.e. @PreAuthorize("@my.project.package.hasMagicPower(#power.INVISIBILITY)")), or combinations of these. You can apply logic and dynamic permissions which are otherwise unavailable to the namespace option.

Of course you can apply rudimentary logic with the 'and', 'or' and '!' connectives in SpEL expressions in the namespace (and you may be able to access external class [boolean] methods via the @ designator in the XML), but everything specified in the XML must be static.


tl;dr: Personal preference is preference, but if you want or need dynamic flexibility in your permission handling, you have to use annotations. If you neither want nor need dynamic flexibility, you have the option (and a sound argument would suggest that the namespace option is better with respect to SoC). I prefer letting the Java handle it for the flexibility and because once I set up my XML, I want to leave it the hell alone and focus on the Java. Also, there is a somewhat convincing counterargument to the SoC view, which is that a properly conventionalized Java application will have its controllers in easy-to-find packages with obvious-by-name control.


still tl;dr: Meh. Six of one, half a dozen of the other. I say po-tay-to.

like image 194
cabbagery Avatar answered Sep 23 '22 07:09

cabbagery