[SPRING] 스프링 보안을 구성하는 방법을 제공합니까?
SPRING스프링 보안을 구성하는 방법을 제공합니까?
외부 파일에서 구성 세부 사항을 읽고 이에 따라 구성하는 방식으로 스프링 보안을 구성 할 수 있습니까?
(나는 런타임에 설정을 변경하는 것을 고려하지 않고있다. 시작시 파일을 읽는 것에 대해 이야기하고있다)
내 Sporing 보안 설정의 예는 다음과 같습니다.
@EnableWebSecurity
@Configuration
public class SecurityConfig {
@Bean
public UserDetailsService userDetailsService() throws Exception {
InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
manager.createUser(User.withUsername("user").password("userPass").roles("USER").build());
manager.createUser(User.withUsername("admin").password("adminPass").roles("ADMIN").build());
return manager;
}
@Configuration
@Order(1)
public static class ApiWebSecurityConfigurationAdapter extends WebSecurityConfigurerAdapter {
@Override
public void configure(AuthenticationManagerBuilder auth)
throws Exception {
auth.inMemoryAuthentication().withUser("user").password("user").roles("USER");
auth.inMemoryAuthentication().withUser("admin").password("admin").roles("ADMIN");
}
protected void configure(HttpSecurity http) throws Exception {
http
.antMatcher("/api/v1/**")
.authorizeRequests()
.antMatchers("/api/v1/**").authenticated()
.and()
.httpBasic();
}
}
@Configuration
@Order(2)
public static class FormLoginWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter {
@Override
public void configure(AuthenticationManagerBuilder auth)
throws Exception {
auth.inMemoryAuthentication().withUser("user1").password("user").roles("USER");
auth.inMemoryAuthentication().withUser("admin1").password("admin").roles("ADMIN");
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.antMatcher("/api/test/**")
.authorizeRequests()
.antMatchers("/api/test/**").authenticated()
.and()
.formLogin();
}
}
}
보시다시피 여러 구성 (Order () 주석을 살펴보십시오)을 사용하고 있습니다. 내가 할 수 있기를 원하는 것은 시작 번호 및 구성 유형을 결정할 때입니다. 첫 번째 클라이언트의 예는 LdapConfig 및 SamlConfig와 같은 2 개의 구성을 원할 수 있습니다. 기타는 LdapConfig 및 SqlConfig를 원하고 세 번째는 4-5 구성을 원할 수 있습니다. 그렇게 할 수 있습니까?
참고 : 저는 Spring Boot를 사용하지 않습니다.
편집하다
내가 왜 이런 식으로 원하는지 요약 :
고객이란 내 제품을 구매할 회사를 의미합니다. 그리고 사용자는 내 제품을 구입 한 회사의 실제 최종 사용자를 의미합니다. 그래서 저는이 제품을 3 개 회사에 선적했습니다. 먼저 LDAP 인증 흐름과 google-oauth2 인증 흐름을 갖도록 구성합니다. 이 첫 번째 회사의 사용자는이 두 가지 옵션으로 로그인 페이지를 보게됩니다. 이제 회사 2는 LDAP 인증 흐름과 SAM 인증 흐름을 가질 수 있으며 해당 회사의 사용자는이 두 가지 옵션을 보게됩니다. 그리고 회사는 시작하기 전에 사용 가능한 옵션을 선택합니다.
해결법
-
==============================
1.속성을로드 할 수 있습니다 (예 : WebApplicationContext를 작성하기 전에 DB 신임을 작성하십시오. 다음 예제를보십시오.
속성을로드 할 수 있습니다 (예 : WebApplicationContext를 작성하기 전에 DB 신임을 작성하십시오. 다음 예제를보십시오.
public class WebAppInitializer implements WebApplicationInitializer { @Override public void onStartup(ServletContext servletContext) throws ServletException { // Tell the EnvironmentManager to load the properties. The path to the config // file is set by Tomcat's home variable. If you change the container you might // need to change this, too. EnvironmentParamManager.initialize(System.getProperty("catalina.home")); // now create the Spring Context AnnotationConfigWebApplicationContext rootContext = new AnnotationConfigWebApplicationContext(); rootContext.register(RootConfig.class); rootContext.setServletContext(servletContext); SpringApplicationContextProvider.configure(rootContext); // ... other config }
EnvironmentParamManager는 다음과 같을 수 있습니다. 응용 프로그램의 비 스프링 부분에서도 모든 곳에서 속성에 액세스 할 수 있도록 정적으로 만들려고했습니다.
public class EnvironmentParamManager { private static Properties properties = new Properties(); public static void initialize(String pathToConfigFile) { BufferedInputStream stream; try { stream = new BufferedInputStream(new FileInputStream( pathToConfigFile + "myconfig.props")); properties.load(stream); stream.close(); } catch (Throwable e) { throw new Error("Cannot read environment settings from file " + pathToConfigFile); } } public static String getMongoDBHostname() { return properties.getProperty("mongodb.username"); } }
JavaConfig를 사용할 때 Bean 생성 단계에서 다음과 같이 쉽게 구성 등록 정보에 액세스 할 수 있습니다.
@Configuration public class CoreConfig { @Bean public MongoDbFactory mongoDbFactory() throws Exception { ... ServerAddress address = new ServerAddress(EnvironmentParamManager.getMongoDBHost(), EnvironmentParamManager.getMongoDBPort()); ... }
물론 Spring 컨텍스트가 부트 스트랩되기 전에 로컬 속성 파일을로드하는 것과 같은 방법으로 LDAP 등의 다른 서비스에 자유롭게 연결할 수 있습니다. 희망이 도움이됩니다.
-
==============================
2.스프링 @Conditional 주석을 사용하여 구성 요소를 선택적으로로드 할 수 있습니다.
스프링 @Conditional 주석을 사용하여 구성 요소를 선택적으로로드 할 수 있습니다.
configs는 다음과 같습니다.
@Configuration(value = "some.security.config") @Conditional(value = LoadSecurityConfigCondition.class) public class SomeSecurityConfig { // some code } @Configuration(value = "other.security.config") @Conditional(value = LoadSecurityConfigCondition.class) public class OtherSecurityConfig { // other code }
그런 다음 LoadSecurityConfigCondition.class는 구성 요소가로드되는지 여부를 결정합니다.
@Component public class LoadSecurityConfigCondition implements Condition { @Override public boolean matches(final ConditionContext context, final AnnotatedTypeMetadata metadata) { boolean enabled = false; if (metadata.isAnnotated(Configuration.class.getName())) { final String name = (String) metadata.getAnnotationAttributes(Configuration.class.getName()).get("value"); if (StringUtils.isNotBlank(name)) { /* Here you may load your config file and * retrieve the information on wether to load * the config identified by its name. */ enabled = ...; } } return enabled; } }
이 예제에서 config 항목은 @Configuration 이름으로 생성 될 수 있으며 목적을 명확히하기 위해 .enabled가 뒤에 붙습니다.
some.security.config.enabled=true other.security.config.enabled=false
-
==============================
3.이것을 시도해 봤니?
이것을 시도해 봤니?
@EnableWebSecurity @Configuration public class SecurityConfig { @Bean public UserDetailsService userDetailsService() throws Exception { InMemoryUserDetailsManager manager = new MemoryUserDetailsManager(); manager.createUser(User.withUsername("user").password("userPass").roles("USER").build()); manager.createUser(User.withUsername("admin").password("adminPass").roles("ADMIN").build()); return manager; } @Configuration @Profile({"profile1", "profile2"}) @Order(1) public static class ApiWebSecurityConfigurationAdapter extends WebSecurityConfigurerAdapter { @Override public void configure(AuthenticationManagerBuilder auth) throws Exception { auth.inMemoryAuthentication().withUser("user").password("user").roles("USER"); auth.inMemoryAuthentication().withUser("admin").password("admin").roles("ADMIN"); } protected void configure(HttpSecurity http) throws Exception { http .antMatcher("/api/v1/**") .authorizeRequests() .antMatchers("/api/v1/**").authenticated() .and() .httpBasic(); } } @Configuration @Profile("profile1") @Order(2) public static class FormLoginWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter { @Override public void configure(AuthenticationManagerBuilder auth) throws Exception { auth.inMemoryAuthentication().withUser("user1").password("user").roles("USER"); auth.inMemoryAuthentication().withUser("admin1").password("admin").roles("ADMIN"); } @Override protected void configure(HttpSecurity http) throws Exception { http .antMatcher("/api/test/**") .authorizeRequests() .antMatchers("/api/test/**").authenticated() .and() .formLogin(); } } }
따라서 spring.profiles.active = profile1을 사용하면 두 구성 모두 spring.profiles.active = profile2로로드되고 첫 번째 구성 만로드됩니다. 물론 두 개 이상의 프로필을 사용할 수 있으며 시작할 때 둘 이상의 프로필을 활성화 할 수도 있습니다 (쉼표로 구분). 요구 사항에 맞는 방식으로 구성과 프로파일을 분리하면됩니다.
from https://stackoverflow.com/questions/48806067/providing-way-to-configure-spring-security by cc-by-sa and MIT license