Spring Boot, Spring Security, Thymeleaf - nie działa "sec:authorize"

0

Witam,

Chciałbym aby dane elementy na stronie www były widocznie tylko dla "ADMIN". Konkretnie: piszę blog i chciałbym aby dostęp do operacji dodawania, usuwania, edycji postów miał tylko admin strony. Doczytałem, że Thymeleaf zapewnia taką funkcjonalność poprzez np.

...
<div sec:authorize="hasRole('ROLE_ADMIN')">
  Treść widoczna tylko dla role_admin.
</div>
...

Natomiast u mnie tekst w "div" widoczny jest bez względu czy jestem zalogowany czy nie, oraz bez względu na to czy jestem zalogowany jako user/admin.
W internetach doczytałem, że wystarczy dodać zależności w pom.xml do:

  1. spring-boot-starter-thymeleaf
  2. thymeleaf-extras-springsecurity4
  3. spring-boot-starter-security

oraz klasę : "public class SecurityConfig extends WebSecurityConfigurerAdapter", którą wstawiam poniżej.
Może ktoś pomóc? Czego tu brakuje? Bo już mi się kończą włosy na głowie do wyrywania.

pom.xml:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>

	<groupId>com.tom.tom</groupId>
	<artifactId>blog-project</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<packaging>jar</packaging>

	<name>blog-project</name>
	<description></description>

	<parent>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-parent</artifactId>
		<version>1.5.2.RELEASE</version>
		<relativePath /> <!-- lookup parent from repository -->
	</parent>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
		<java.version>1.8</java.version>
		<thymeleaf.version>3.0.2.RELEASE</thymeleaf.version>
		<thymeleaf-layout-dialect.version>2.1.1</thymeleaf-layout-dialect.version>
	</properties>

	<dependencies>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-jpa</artifactId>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-thymeleaf</artifactId>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>

		<dependency>
			<groupId>com.h2database</groupId>
			<artifactId>h2</artifactId>
			<scope>runtime</scope>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-devtools</artifactId>
		</dependency>

		<!-- /////////////// -->

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-security</artifactId>
		</dependency>

		<dependency>
			<groupId>org.thymeleaf.extras</groupId>
			<artifactId>thymeleaf-extras-springsecurity4</artifactId>
		</dependency>

		<dependency>
			<groupId>org.springframework.security</groupId>
			<artifactId>spring-security-taglibs</artifactId>
		</dependency>

		<dependency>
			<groupId>org.webjars</groupId>
			<artifactId>bootstrap</artifactId>
			<version>3.3.7</version>
			<exclusions>
				<exclusion>
					<groupId>org.webjars</groupId>
					<artifactId>jquery</artifactId>
				</exclusion>
			</exclusions>
		</dependency>
		<dependency>
			<groupId>org.webjars</groupId>
			<artifactId>jquery</artifactId>
			<version>3.1.1</version>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-test</artifactId>
			<scope>test</scope>
		</dependency>
	</dependencies>

	<build>
		<plugins>
			<plugin>
				<groupId>org.springframework.boot</groupId>
				<artifactId>spring-boot-maven-plugin</artifactId>
			</plugin>
		</plugins>
	</build>


</project>

SecurityConfig:

@EnableWebSecurity
@EnableGlobalMethodSecurity(securedEnabled = true)
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
	
	@Autowired
	public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
		auth
			.inMemoryAuthentication()
				.withUser("admin").password("123").roles("ADMIN", "USER")
				.and()
				.withUser("user").password("aaa").roles("USER");
	}

	
	@Override
	protected void configure(HttpSecurity http) throws Exception {
		http
		 .authorizeRequests().antMatchers("/**").permitAll()
		 
         .antMatchers("/blog/**").hasAuthority("ADMIN")
         .antMatchers("/blog").authenticated()
         .and()
         .formLogin()
         .loginPage("/blog/login")
         .defaultSuccessUrl("/blog")
         .and().csrf().disable();	
	}

}

index.html

<!DOCTYPE html>
<html lang="pl" 
xmlns="http://www.thymeleaf.org/extras/dialect" 
xmlns:th="http://www.thymeleaf.org" 
xmlns:sec="http://www.thymeleaf.org/thymeleaf-extras-springsecurity4" 
xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout">

<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>blog-project</title>
<link rel="stylesheet" href="/webjars/bootstrap/3.3.7/css/bootstrap.min.css" >
<link rel="stylesheet" href="/style.css" >	

</head>
<body>
	<div class="container tom_main">
		<div class="container tom_main">
			<ul class="tom_menu">
  				<li><a href="/blog"><span class="glyphicon glyphicon-home"></span>  &nbsp;Home</a></li>
  				<li><a href="/blog/aboutMe">O mnie</a></li>
  				<li><a href="#">Kategorie</a></li>
  				<li><a href="#">Archiwum</a></li>
  				<li><a href="#">Kontakt</a></li>
  				<li><a href="/blog/login">Zaloguj</a></li>
  				<li class="pull-right"><a href="/blog/addPost" style="color: gray;">Dodaj post</a></li>
			</ul>
		</div>
		
		<div class="container text-center">
			<h2 th:text="${greetings}"></h2>
		</div>
		
		<div class="tom_pagination">
			<ul class="pagination">	
				<li>
					<a th:if="${posts.hasPrevious()}" th:href="@{/blog(page=${posts.getNumber()-1})}">&lt;</a>
				</li>
				<li>
					<a class="active" th:if="${posts.hasNext()}" th:href="@{/blog(page=${posts.getNumber()+1})}">&gt;</a>
				</li>
			</ul>
		</div>
		
		<div class="container" th:each="post : ${posts}">
			<div class="tom_content" >
				<h2 th:text="${post.title}"></h2>
				<p style="padding: 20px 0;" th:text="${#strings.abbreviate(post.content,400)}"></p>
				<p class="tom_right">
					<a class="btn btn-info" th:href="@{/blog/{postId}(postId=${post.id})}">więcej...</a>
				</p>
				
			</div>	
		</div>
		
		 <h1 th:inline="text">Hello [[${#httpServletRequest.remoteUser}]]!</h1>
        <form th:action="@{/logout}" method="post">
            <input type="submit" value="Wyloguj"/>
        </form>
		
		<div sec:authorize="hasRole('ROLE_ADMIN')">
		  Treść widoczna tylko dla admina.
		</div>
		
		<div class="footer text-center">
			<a href="mailto:[email protected]">[email protected]</a>
		</div>
	</div>
	
<script type="text/javascript" src="/webjars/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<script type="text/javascript" src="/webjars/jquery/3.1.1/dist/jquery.min.js"></script>	
		
</body>
</html>
1

Spróbuj zamiast


<div sec:authorize="hasRole('ROLE_ADMIN')">

Zrobić

<div sec:authorize="hasAuthority('ROLE_ADMIN')">


Miałem ten sam problem i u mnie pomogło.

0

Próbowałem tego i treść też jest widoczna dla wszystkich.
Może trzeba dodać jakąś konfigurację dodatkowo albo w coś kontrolerze?

0
.withUser("admin").password("123").roles("ADMIN", "USER")

A tu masz

<div sec:authorize="hasRole('ROLE_ADMIN')">

Powinieneś w obu mieć albo ROLE_ADMIN albo ADMIN, a nie dwa różne.

0

Próbowałem różnych wersji:

<div sec:authorize="hasRole('ROLE_ADMIN')">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasRole(ROLE_ADMIN)">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasRole(ADMIN)">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasRole('ADMIN')">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasAuthority(ADMIN)">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasAuthority('ADMIN')">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasAuthority('ROLE_ADMIN')">
				widoczne tylko dla admina.
			</div>
			<div sec:authorize="hasAuthority(ROLE_ADMIN)">
				widoczne tylko dla admina.
			</div>

I dostaję 8 * widoczne tylko dla admina.
Może wersje thymeleaf i spring boot / security się kłócą?
Albo coś w pliku .properties trzeba dodać?

btw dzięki za zainteresowanie

0

Tak siedzę i myślę. Spring boot nie tworzy beana SpringSecurityDialect a chyba powinien

?

0

Można sprawdzić prosto które beany są tworzone.

0

Sprawdziłem, i ten bean się nie tworzy.

0

Bo to nie działa z inMemoryAuthentication, tylko z autentykacją opartą o bazę i role, które w bazie muszą być w kształcie "ROLE_USER".

0

Mi pomogło dodanie SpringSecurityDialect
@Configuration
@EnableWebMvc
public class MvcConfig implements WebMvcConfigurer

.
.
.
.

@Bean
@Description("Thymeleaf template engine with Spring integration")
public SpringTemplateEngine templateEngine() {

    SpringTemplateEngine templateEngine = new SpringTemplateEngine();
    templateEngine.addDialect(new LayoutDialect());
    templateEngine.addDialect(new SpringSecurityDialect());
    templateEngine.setEnableSpringELCompiler(true);

    templateEngine.setTemplateResolver(templateResolver());

    return templateEngine;
}

1 użytkowników online, w tym zalogowanych: 0, gości: 1