Added UserService, base of configuration Spring Security

This commit is contained in:
Andrey Terentev 2024-03-18 18:22:01 +07:00 committed by Andrey Terentev
parent 4de95771cb
commit 69113ee4a3
8 changed files with 180 additions and 1 deletions

View File

@ -63,6 +63,10 @@ public class RoomPickerClient {
return userRepository;
}
public @NotNull AccountRepository getAccountRepository() {
return accountRepository;
}
public @NotNull RoomPickerInfoResponse getServerInfo() {
return restTemplate.query("/info", HttpMethod.GET, RoomPickerInfoResponse.class, params -> {});
}

View File

@ -31,6 +31,8 @@ dependencies {
implementation project(":client-impl")
implementation 'com.vaadin:vaadin-spring-boot-starter'
implementation 'org.springframework.boot:spring-boot-starter-security'
implementation 'org.jetbrains:annotations:24.1.0'
compileOnly 'org.projectlombok:lombok'
annotationProcessor 'org.projectlombok:lombok'

View File

@ -5,6 +5,8 @@ import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import ru.dragonestia.picker.api.impl.RoomPickerClient;
import ru.dragonestia.picker.cp.annotation.ServerURL;
import ru.dragonestia.picker.cp.model.Account;
import ru.dragonestia.picker.cp.model.provider.AccountProvider;
@Configuration
public class RoomPickerConfig {
@ -12,6 +14,12 @@ public class RoomPickerConfig {
@Value("${ROOMPICKER_HOST_URL:http://localhost:8080}")
private String serverUrl;
@Value("${ROOMPICKER_ADMIN_USERNAME:admin}")
private String adminUsername;
@Value("${ROOMPICKER_ADMIN_PASSWORD:qwerty123}")
private String adminPassword;
@ServerURL
@Bean
String severUrl() {
@ -19,7 +27,12 @@ public class RoomPickerConfig {
}
@Bean
RoomPickerClient roomPickerClient() {
RoomPickerClient adminClient() {
return new RoomPickerClient(serverUrl, "admin", "qwerty123");
}
@Bean
AccountProvider accountProvider() {
return response -> new Account(response, new RoomPickerClient(serverUrl, response.getUsername(), response.getPassword()));
}
}

View File

@ -0,0 +1,34 @@
package ru.dragonestia.picker.cp.config;
import com.vaadin.flow.spring.security.VaadinWebSecurity;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.password.PasswordEncoder;
import ru.dragonestia.picker.api.impl.RoomPickerClient;
import ru.dragonestia.picker.cp.model.provider.AccountProvider;
import ru.dragonestia.picker.cp.service.AccountService;
@Configuration
public class SecurityConfig extends VaadinWebSecurity {
@Bean
PasswordEncoder passwordEncoder() {
return new PasswordEncoder() {
@Override
public String encode(CharSequence rawPassword) {
return rawPassword.toString();
}
@Override
public boolean matches(CharSequence rawPassword, String encodedPassword) {
return rawPassword.toString().equals(encodedPassword);
}
};
}
@Bean
UserDetailsService userDetailsService(RoomPickerClient adminClient, AccountProvider accountProvider) {
return new AccountService(adminClient, accountProvider);
}
}

View File

@ -0,0 +1,73 @@
package ru.dragonestia.picker.cp.model;
import org.jetbrains.annotations.NotNull;
import org.springframework.security.core.userdetails.UserDetails;
import ru.dragonestia.picker.api.impl.RoomPickerClient;
import ru.dragonestia.picker.api.model.account.IAccount;
import ru.dragonestia.picker.api.model.account.ResponseAccount;
import java.util.Collection;
import java.util.Set;
import java.util.stream.Collectors;
public class Account implements IAccount, UserDetails {
private final ResponseAccount original;
private final RoomPickerClient client;
private final Set<Permission> permissions;
public Account(ResponseAccount original, RoomPickerClient client) {
this.original = original;
this.client = client;
permissions = original.getPermissions().stream().map(Permission::new).collect(Collectors.toSet());
}
public @NotNull RoomPickerClient getClient() {
return client;
}
@Override
public Collection<Permission> getAuthorities() {
return permissions;
}
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return !original.isLocked();
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
@Override
public @NotNull String getUsername() {
return original.getUsername();
}
@Override
public @NotNull String getPassword() {
return original.getPassword();
}
@Override
public @NotNull Set<String> getPermissions() {
return original.getPermissions();
}
@Override
public boolean isLocked() {
return original.isLocked();
}
}

View File

@ -0,0 +1,18 @@
package ru.dragonestia.picker.cp.model;
import com.github.javaparser.quality.NotNull;
import org.springframework.security.core.GrantedAuthority;
public class Permission implements GrantedAuthority {
private final String authority;
public Permission(@NotNull String authority) {
this.authority = authority;
}
@Override
public String getAuthority() {
return authority;
}
}

View File

@ -0,0 +1,10 @@
package ru.dragonestia.picker.cp.model.provider;
import org.jetbrains.annotations.NotNull;
import ru.dragonestia.picker.api.model.account.ResponseAccount;
import ru.dragonestia.picker.cp.model.Account;
public interface AccountProvider {
@NotNull Account provide(@NotNull ResponseAccount responseAccount);
}

View File

@ -0,0 +1,25 @@
package ru.dragonestia.picker.cp.service;
import lombok.RequiredArgsConstructor;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;
import ru.dragonestia.picker.api.impl.RoomPickerClient;
import ru.dragonestia.picker.cp.model.Account;
import ru.dragonestia.picker.cp.model.provider.AccountProvider;
@Service
@RequiredArgsConstructor
public class AccountService implements UserDetailsService {
private final RoomPickerClient adminClient;
private final AccountProvider accountProvider;
@Override
public Account loadUserByUsername(String username) throws UsernameNotFoundException {
var response = adminClient.getAccountRepository().findAccountByUsername(username)
.orElseThrow(() -> new UsernameNotFoundException(username));
return accountProvider.provide(response);
}
}