I am spring newbie
I've implemented OAuth2 implicit flow using spring security.
The question is how to check token validity? I've found oauth/check_token endpoint but first I wasn't able to reach it. Then I've made the following change:
#Override
public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception
{
oauthServer.checkTokenAccess("permitAll()");
}
After the configuration I can use check_token endpoint but I wonder if it is correct to use permitAll on the endpoint. I've tried to change it to isAuthenticated but in that case I am not able to reach the endpoint because I don't store client_secret on my frontend app.
Should I continue use permitAll or there is better way?
You should check access while using oAuth.
Try below code if works,
#Override
public void configure(
AuthorizationServerSecurityConfigurer oauthServer)
throws Exception {
oauthServer
.tokenKeyAccess("permitAll()")
.checkTokenAccess("isAuthenticated()");
}
If doesn't, please share your security related snippets. Happy coding :)
Related
I want to redirect users to a different page after login depending on what type of user they are, and if they're on a mobile device. My project uses Spring MVC and Spring Security. To get the redirect logic working, I use a Spring Security AuthenticationSuccessHandler to identify the type of user post-login and direct them to the correct page.
I was hoping to use Spring Mobile to check at this point whether they're on a mobile device, and if so send them to the mobile version of the URL. However, it seems that interceptors such as DeviceResolverHandlerInterceptor get executed after the Spring Security filters, and so the resolution hasn't happened at the point I need it to.
At the moment, the only solution I can see to this is to disable the interceptor and instead directly use LiteDeviceResolver's resolveDevice() method. This feels a little bit hacky, but I can't see another obvious choice.
Is there any better way to configure this people are aware of?
#Configuration
public class WebConfig implements WebMvcConfigurer {
#Bean
public DeviceResolverHandlerInterceptor deviceResolverHandlerInterceptor() {
return new DeviceResolverHandlerInterceptor();
}
#Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(deviceResolverHandlerInterceptor()).order(Ordered.HIGHEST_PRECEDENCE);
}
}
#Override
public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response,
Authentication authentication) throws IOException, ServletException {
boolean isMobile = DeviceUtils.getCurrentDevice(request) != null
&& DeviceUtils.getCurrentDevice(request).isMobile();
...
I have app on spring-boot
added
endpoints.shutdown.enabled=true
endpoints.shutdown.sensitive=false
to application.properties
and try to call:
curl -i -X POST devapp583.netcracker.com:26810/shutdown
But requres Auth header instead just shutting down:
{"errorCode":403,"userMessage":"No 'Authorization' header","stacktrace":null,"remoteMessage":null}
It seems like a bug, take a look here. (If you use #EnableResourceServer)
According to the docs for 1.3 for health access restrictions, a
non-sensitive health endpoint should allow anonymous access. However,
this stops working if the #EnableResourceServer annotation is found.
When the OAuth2 resource server is enabled, even non-sensitive
endpoints require full authentication.
Also there you can find a workaround:
I did manage to work around the problem for the health endpoint by
adding the following bean definition.
#Bean
ResourceServerConfigurer resourceServerConfigurer() {
new ResourceServerConfigurerAdapter() {
#Override
void configure(ResourceServerSecurityConfigurer resources)
throws Exception {
resources.resourceId('blah')
}
#Override
void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
// allow anonymous access to health check endpoint
.antMatchers("/manage/health").permitAll()
// everything else requires authentication
.anyRequest().authenticated()
}
}
}
However I have not tried it myself
I have a REST API written in Spring Boot with Spring Security and OAuth2. The resources are secured this way:
#Override
public void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/api/v1/security/**").hasRole("ADMIN");
}
I'd like to introduce a new part of the API where the permissions are fine grained, based on projects. Let's consider a simple endpoint that prints the project configuration.
GET /api/v1/project/{projectId}/config
How would I configure the resource server to only allow access for users who have the role ROLE_PROJECT_{projectId}_ADMIN without having to manually specify all projects?
Also if this mechanism has a specific name, please let me know in comments to I can change the question title.
You can use path values in authorization expressions.
According to Path Variables in Web Security Expressions you should write your custom authorization logic.
public class WebSecurity {
public boolean checkUserHasAccessToProjectId(Authentication authentication, int projectId) {
// here you can check if the user has the correct role
// or implement more complex and custom authorization logic if necessary
}
}
Then in your Java security configuration you can refer to this method and pass it the value of the relevant path fragment.
http.authorizeRequests()
.antMatchers("/api/v1/project/{projectId}/config")
.access("#webSecurity.checkUserHasAccessToProjectId(authentication,#projectId)")
...
I'm using Spring Boot to create my microservices and I'm enabling the OAuth2 to add security to my services.
However, there are some methods that I can not understand what are the differences between then. For example, I have the following code:
#Override
public void configure(HttpSecurity http) throws Exception {
http.csrf().disable();
http.sessionManagement().sessionCreationPolicy(STATELESS);
http.authorizeRequests()
.antMatchers(POST, "/v1/files/").access("#oauth2.clientHasRole('ROLE_CLIENT')");
}
In this example, I used the access method to check if the system that is going to access my services has the ROLE_CLIENT role.
The question is : what are the main differences between the following methods:
hasRole
hasAuthority
access
hasRole(NAME) checks that client has ROLE_NAME whether hasAuthority(NAME) checks only NAME role.
hasRole("CLIENT") is equivalent to hasAuthority("ROLE_CLIENT")
I was trying to enable csrf filter for some specific api calling and for the others no need of csrf filter.What I have done is
#Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable().authorizeRequests().antMatchers("/public/**").permitAll();
http.exceptionHandling().authenticationEntryPoint(authenticationEntryPoint);
http.csrf().disable().addFilterBefore(new StatelessCSRFFilter(), CsrfFilter.class).authorizeRequests().antMatchers("/rest/**").permitAll();
}
The problem is when I was calling localhost:8080/public/hello
An error was showing
"message": "Missing or non-matching CSRF-token"
I am using Spring boot and Spring Security.
Thanks for any help.
http.antMatcher("/public/**").authorizeRequests().anyRequest().permitAll();
http.exceptionHandling().authenticationEntryPoint(authenticationEntryPoint);
http.antMatcher("/rest/**").addFilterBefore(new StatelessCSRFFilter(), CsrfFilter.class).csrf().disable();
Or you can do like this.I think both will be working.
http.antMatcher("/public/**").csrf().disable();
http.exceptionHandling().authenticationEntryPoint(authenticationEntryPoint);
http.antMatcher("/rest/**").addFilterBefore(new StatelessCSRFFilter(), CsrfFilter.class).csrf().disable();
Try changing http.csrf().disable() to http.antMatcher("/public/**").csrf().disable() and http.antMatcher("/rest/**").csrf().disable(). You will likely have to put those two lines each in their own WebSecurityConfigurerAdapter.
That will tell Spring-Security to create multiple HTTP Security Filter Chains (akin to having multiple <http/> blocks in the XML model).