Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/kotlin/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
SpringBoot应用程序需要一个带有@Primary注释的bean来启动_Spring_Spring Boot - Fatal编程技术网

SpringBoot应用程序需要一个带有@Primary注释的bean来启动

SpringBoot应用程序需要一个带有@Primary注释的bean来启动,spring,spring-boot,Spring,Spring Boot,我在Spring Boot应用程序启动时看到以下消息: > *************************** APPLICATION FAILED TO START > *************************** > > Description: > > Field oauthProps in com.example.authservice.AuthorizationServerConfig > required a single

我在Spring Boot应用程序启动时看到以下消息:

> *************************** APPLICATION FAILED TO START
> ***************************
> 
> Description:
> 
> Field oauthProps in com.example.authservice.AuthorizationServerConfig
> required a single bean, but 2 were found:
>   - OAuthProperties: defined in file [/Users/simeonleyzerzon/abc/spring-security/spring-security-5-oauth-client/auth-service/target/classes/com/example/authservice/config/OAuthProperties.class]
>   - kai-com.example.authservice.config.OAuthProperties: defined in null
> 
> 
> Action:
> 
> Consider marking one of the beans as @Primary, updating the consumer
> to accept multiple beans, or using @Qualifier to identify the bean
> that should be consumed
我想知道是什么导致了该bean的重复,以及如何在不需要使用
@Primary
注释的情况下删除它?不确定上面的kai com包(?)来自何处

下面是一个问题:

package com.example.authservice.config;

    //@Primary
    @Component
    @ConfigurationProperties(prefix="kai")
    @Setter @Getter
    public class OAuthProperties {


        private String[] redirectUris;


        private String clientId;


        private String clientSecret;

        private final Token token = new Token();


        @Setter @Getter
        public static class Token{

            private String value;

            private String type="";

        }

    }
以及app/config等:

package com.example.authservice;

import ...
@SpringBootApplication
public class AuthServiceApplication {

    public static void main(String[] args) {
        SpringApplication.run(AuthServiceApplication.class, args);
    }
}

@Controller
class MainController {

    @GetMapping("/")
    String index() {
        return "index";
    }
}

@RestController
class ProfileRestController {

    @GetMapping("/resources/userinfo")
    Map<String, String> profile(Principal principal) {
        return Collections.singletonMap("name", principal.getName());
    }
}

@Configuration
@EnableResourceServer
class ResourceServerConfig extends ResourceServerConfigurerAdapter {

    @Override
    public void configure(HttpSecurity http) throws Exception {
        http
                .antMatcher("/resources/**")
                .authorizeRequests()
                .mvcMatchers("/resources/userinfo").access("#oauth2.hasScope('profile')");
    }
}

@Configuration
@EnableAuthorizationServer
@EnableConfigurationProperties(OAuthProperties.class)
class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {



    @Autowired private OAuthProperties oauthProps;

    private final AuthenticationManager authenticationManager;

    AuthorizationServerConfig(AuthenticationManager authenticationManager) {
        this.authenticationManager = authenticationManager;
    }

    @Override
    public void configure(ClientDetailsServiceConfigurer clients) throws Exception {

        clients
            .inMemory()

                .withClient(oauthProps.getClientId())
                .secret(oauthProps.getClientSecret())
                .authorizedGrantTypes("authorization_code")
                .scopes("profile")
                .redirectUris(oauthProps.getRedirectUris());


    }

    @Override
    public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {

        endpoints.authenticationManager(this.authenticationManager);

        if (oauthProps.getToken().getType().equals("jwt")) {
            endpoints.tokenStore(this.tokenStore()).accessTokenConverter(jwtAccessTokenConverter());
        }else {
            endpoints.tokenEnhancer(eapiTokenEnhancer());
        }
    }

    TokenEnhancer eapiTokenEnhancer() {

        return new TokenEnhancer() {

            @Override
            public OAuth2AccessToken enhance(OAuth2AccessToken accessToken, OAuth2Authentication authentication) {

                DefaultOAuth2AccessToken result = new DefaultOAuth2AccessToken(accessToken);
                result.setValue(oauthProps.getToken().getValue());
                return result;
            }
        };

    }

    @Bean
    JwtAccessTokenConverter jwtAccessTokenConverter() {
        KeyStoreKeyFactory factory = new KeyStoreKeyFactory(new ClassPathResource(".keystore-oauth2-demo"), //keystore
                "admin1234".toCharArray());                                                                 //storepass
        JwtAccessTokenConverter jwtAccessTokenConverter = new JwtAccessTokenConverter();
        jwtAccessTokenConverter.setKeyPair(factory.getKeyPair("oauth2-demo-key"));                          //alias
        return jwtAccessTokenConverter;
    }

    @Bean
    TokenStore tokenStore() {
        return new JwtTokenStore(this.jwtAccessTokenConverter());
    }
}

@Service
class SimpleUserDetailsService implements UserDetailsService {

    private final Map<String, UserDetails> users = new ConcurrentHashMap<>();

    SimpleUserDetailsService() {
        Arrays.asList("josh", "rob", "joe")
                .forEach(username -> this.users.putIfAbsent(
                        username, new User(username, "pw", true, true, true, true, AuthorityUtils.createAuthorityList("USER","ACTUATOR"))));
    }

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        return this.users.get(username);
    }
}

@Configuration
@EnableWebSecurity
class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {

        http
                .authorizeRequests()
                    .anyRequest().authenticated()
                    .and()
                .formLogin();

    }
}
package com.example.authservice;
导入。。。
@SpringBoot应用程序
公共类AuthServiceApplication{
公共静态void main(字符串[]args){
run(AuthServiceApplication.class,args);
}
}
@控制器
类主控制器{
@GetMapping(“/”)
字符串索引(){
返回“索引”;
}
}
@RestController
类ProfileRestController{
@GetMapping(“/resources/userinfo”)
地图简介(校长){
返回Collections.singletonMap(“name”,principal.getName());
}
}
@配置
@EnableResourceServer
类ResourceServerConfig扩展了ResourceServerConfigurerAdapter{
@凌驾
public void configure(HttpSecurity http)引发异常{
http
.antMatcher(“/resources/**”)
.授权请求()
.mvcMatchers(“/resources/userinfo”).access(“#oauth2.hasScope('profile')”);
}
}
@配置
@EnableAuthorizationServer
@EnableConfigurationProperties(OAuthProperties.class)
类AuthorizationServerConfig扩展AuthorizationServerConfigurerAdapter{
@自动连线专用OAuthProperties oauthProps;
私人最终身份验证经理AuthenticationManager;
AuthorizationServerConfig(AuthenticationManager AuthenticationManager){
this.authenticationManager=authenticationManager;
}
@凌驾
公共无效配置(ClientDetailsServiceConfigurer客户端)引发异常{
客户
.inMemory()
.withClient(oauthProps.getClientId())
.secret(oauthProps.getClientSecret())
.authorizedGrantTypes(“授权代码”)
.范围(“概要文件”)
.redirectUris(oauthProps.getRedirectUris());
}
@凌驾
public void configure(AuthorizationServerEndpointsConfigurer端点)引发异常{
endpoints.authenticationManager(this.authenticationManager);
if(oauthProps.getToken().getType().equals(“jwt”)){
endpoints.tokenStore(this.tokenStore()).accessTokenConverter(jwtAccessTokenConverter());
}否则{
标记增强器(eapiTokenEnhancer());
}
}
令牌增强子eapiTokenEnhancer(){
返回新的令牌增强器(){
@凌驾
公共OAuth2AccessToken增强(OAuth2AccessToken accessToken,OAuth2Authentication身份验证){
DefaultOAuth2AccessToken结果=新的DefaultOAuth2AccessToken(accessToken);
setValue(oauthProps.getToken().getValue());
返回结果;
}
};
}
@豆子
JwtAccessTokenConverter JwtAccessTokenConverter(){
KeyStoreKeyFactory=newkeystorekeyFactory(newclasspathResource(“.keystore-oauth2-demo”),//keystore
“admin1234.toCharArray());//storepass
JwtAccessTokenConverter JwtAccessTokenConverter=新的JwtAccessTokenConverter();
jwtAccessTokenConverter.setKeyPair(工厂.getKeyPair(“oauth2演示密钥”);//别名
返回JWT转换器;
}
@豆子
TokenStore TokenStore(){
返回新的JwtTokenStore(this.jwtAccessTokenConverter());
}
}
@服务
类SimpleUserDetailsService实现UserDetailsService{
私有最终映射用户=新ConcurrentHashMap();
SimpleUserDetailsService(){
数组。asList(“josh”、“rob”、“joe”)
.forEach(用户名->this.users.putIfAbsent(
用户名,新用户(用户名,“pw”,true,true,true,AuthorityUtils.createAuthorityList(“用户”,“执行器”));
}
@凌驾
public UserDetails loadUserByUsername(字符串用户名)引发UsernameNotFoundException{
返回此.users.get(用户名);
}
}
@配置
@启用Web安全性
类SecurityConfig扩展了WebSecurity配置适配器{
@凌驾
受保护的无效配置(HttpSecurity http)引发异常{
http
.授权请求()
.anyRequest().authenticated()
.及()
.formLogin();
}
}
Eclipse似乎也只知道bean的一个实例:

以下更改(删除
@EnableConfigurationProperties
)似乎有助于缓解对@Primary注释的需求:

@Configuration
@EnableAuthorizationServer
//@EnableConfigurationProperties(OAuthProperties.class)
class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {


    @Autowired private OAuthProperties oauthProps;
也许有人可以通过注释来描述二次bean创建的内部Spring机制(及其名称空间/包分配),该注释似乎会导致与
@Autowired
one的冲突,或者向我指出此行为的适当文档

以下更改(删除
@EnableConfigurationProperties
)似乎有助于缓解对@Primary注释的需求:

@Configuration
@EnableAuthorizationServer
//@EnableConfigurationProperties(OAuthProperties.class)
class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {


    @Autowired private OAuthProperties oauthProps;

也许有人可以通过注释来描述二次bean创建的内部Spring机制(及其名称空间/包分配),该注释似乎会导致与
@Autowired
one的冲突,或者向我指出此行为的适当文档

@EnableConfigurationProperties
@ConfigurationProperties
一起使用时,您将得到一个名为
-
的bean,即
kai com.example.authservice.config.OAuthProperties
。(另见)

@ConfigurationProperties
bean以这种方式注册时,该bean有一个常规名称:
-