springboot集成oauth2报错

参照官方文档:https://spring.io/guides/tutorials/spring-boot-oauth2/#_social_login_simple

引入的项目依赖:

	
		org.springframework.boot
		spring-boot-starter-parent
		2.1.4.RELEASE
		
	

	
		
			org.springframework.boot
			spring-boot-starter-web
		
		
			org.springframework.boot
			spring-boot-starter-security
		
		
			org.springframework.security.oauth.boot
			spring-security-oauth2-autoconfigure
			2.1.4.RELEASE
		
		
			org.webjars
			jquery
			2.1.1
		
		
			org.webjars
			bootstrap
			3.2.0
		
		
			org.webjars
			webjars-locator-core
		
		
			org.springframework.boot
			spring-boot-configuration-processor
			true
		
	

问题出现:引入一下代码,启动程序报错:The bean 'oauth2ClientFilterRegistration', defined in class path resource [org/springframework/boot/autoconfigure/security/oauth2/client/OAuth2RestOperationsConfiguration$SessionScopedConfiguration.class], could not be registered. A bean with that name has already been defined in com.hegret.SocialApplication and overriding is disabled.

    @Bean
    public FilterRegistrationBean oauth2ClientFilterRegistration(OAuth2ClientContextFilter filter) {
        FilterRegistrationBean registration = new FilterRegistrationBean();
        registration.setFilter(filter);
        registration.setOrder(-100);
        return registration;
    }

  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::        (v2.1.4.RELEASE)

2019-06-05 14:42:20.603  INFO 8560 --- [           main] com.hegret.SocialApplication             : Starting SocialApplication on zsx with PID 8560 (F:\workspace-test\spring-oauth2-server\target\classes started by zhang in F:\workspace-test\spring-oauth2-server)
2019-06-05 14:42:20.605  INFO 8560 --- [           main] com.hegret.SocialApplication             : No active profile set, falling back to default profiles: default
2019-06-05 14:42:20.877  WARN 8560 --- [           main] ConfigServletWebServerApplicationContext : Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.support.BeanDefinitionOverrideException: Invalid bean definition with name 'oauth2ClientFilterRegistration' defined in class path resource [org/springframework/boot/autoconfigure/security/oauth2/client/OAuth2RestOperationsConfiguration$SessionScopedConfiguration.class]: Cannot register bean definition [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=org.springframework.boot.autoconfigure.security.oauth2.client.OAuth2RestOperationsConfiguration$SessionScopedConfiguration; factoryMethodName=oauth2ClientFilterRegistration; initMethodName=null; destroyMethodName=(inferred); defined in class path resource [org/springframework/boot/autoconfigure/security/oauth2/client/OAuth2RestOperationsConfiguration$SessionScopedConfiguration.class]] for bean 'oauth2ClientFilterRegistration': There is already [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=socialApplication; factoryMethodName=oauth2ClientFilterRegistration; initMethodName=null; destroyMethodName=(inferred); defined in com.hegret.SocialApplication] bound.
2019-06-05 14:42:20.883  INFO 8560 --- [           main] ConditionEvaluationReportLoggingListener : 

Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled.
2019-06-05 14:42:20.884 ERROR 8560 --- [           main] o.s.b.d.LoggingFailureAnalysisReporter   : 

***************************
APPLICATION FAILED TO START
***************************

Description:

The bean 'oauth2ClientFilterRegistration', defined in class path resource [org/springframework/boot/autoconfigure/security/oauth2/client/OAuth2RestOperationsConfiguration$SessionScopedConfiguration.class], could not be registered. A bean with that name has already been defined in com.hegret.SocialApplication and overriding is disabled.

Action:

Consider renaming one of the beans or enabling overriding by setting spring.main.allow-bean-definition-overriding=true

问题分析:跟踪源码,在OAuth2RestOperationsConfiguration类中已经定义过该bean对象了

/*
 * Copyright 2012-2017 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      https://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.springframework.boot.autoconfigure.security.oauth2.client;

import org.springframework.beans.factory.ObjectProvider;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.autoconfigure.condition.AnyNestedCondition;
import org.springframework.boot.autoconfigure.condition.ConditionMessage;
import org.springframework.boot.autoconfigure.condition.ConditionOutcome;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnNotWebApplication;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.NoneNestedConditions;
import org.springframework.boot.autoconfigure.condition.SpringBootCondition;
import org.springframework.boot.autoconfigure.security.SecurityProperties;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ConditionContext;
import org.springframework.context.annotation.Conditional;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.context.annotation.Primary;
import org.springframework.context.annotation.Scope;
import org.springframework.context.annotation.ScopedProxyMode;
import org.springframework.core.type.AnnotatedTypeMetadata;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.oauth2.client.DefaultOAuth2ClientContext;
import org.springframework.security.oauth2.client.OAuth2ClientContext;
import org.springframework.security.oauth2.client.filter.OAuth2ClientContextFilter;
import org.springframework.security.oauth2.client.token.AccessTokenRequest;
import org.springframework.security.oauth2.client.token.DefaultAccessTokenRequest;
import org.springframework.security.oauth2.client.token.grant.client.ClientCredentialsResourceDetails;
import org.springframework.security.oauth2.common.DefaultOAuth2AccessToken;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableOAuth2Client;
import org.springframework.security.oauth2.config.annotation.web.configuration.OAuth2ClientConfiguration;
import org.springframework.security.oauth2.provider.OAuth2Authentication;
import org.springframework.security.oauth2.provider.authentication.OAuth2AuthenticationDetails;
import org.springframework.util.StringUtils;

/**
 * Configuration for OAuth2 Single Sign On REST operations.
 *
 * @author Dave Syer
 * @author Madhura Bhave
 * @since 1.3.0
 */
@Configuration
@ConditionalOnClass(EnableOAuth2Client.class)
public class OAuth2RestOperationsConfiguration {

	@Configuration
	@Conditional(ClientCredentialsCondition.class)
	protected static class SingletonScopedConfiguration {

		@Bean
		@ConfigurationProperties(prefix = "security.oauth2.client")
		@Primary
		public ClientCredentialsResourceDetails oauth2RemoteResource() {
			ClientCredentialsResourceDetails details = new ClientCredentialsResourceDetails();
			return details;
		}

		@Bean
		public DefaultOAuth2ClientContext oauth2ClientContext() {
			return new DefaultOAuth2ClientContext(new DefaultAccessTokenRequest());
		}

	}

	@Configuration
	@ConditionalOnBean(OAuth2ClientConfiguration.class)
	@Conditional({ OAuth2ClientIdCondition.class, NoClientCredentialsCondition.class })
	@Import(OAuth2ProtectedResourceDetailsConfiguration.class)
	protected static class SessionScopedConfiguration {

		@Bean
		public FilterRegistrationBean oauth2ClientFilterRegistration(
				OAuth2ClientContextFilter filter, SecurityProperties security) {
			FilterRegistrationBean registration = new FilterRegistrationBean<>();
			registration.setFilter(filter);
			registration.setOrder(security.getFilter().getOrder() - 10);
			return registration;
		}

	}

	// When the authentication is per cookie but the stored token is an oauth2 one, we can
	// pass that on to a client that wants to call downstream. We don't even need an
	// OAuth2ClientContextFilter until we need to refresh the access token. To handle
	// refresh tokens you need to @EnableOAuth2Client
	@Configuration
	@ConditionalOnMissingBean(OAuth2ClientConfiguration.class)
	@Conditional({ OAuth2ClientIdCondition.class, NoClientCredentialsCondition.class })
	@Import(OAuth2ProtectedResourceDetailsConfiguration.class)
	protected static class RequestScopedConfiguration {

		@Bean
		@Scope(value = "request", proxyMode = ScopedProxyMode.INTERFACES)
		public DefaultOAuth2ClientContext oauth2ClientContext() {
			DefaultOAuth2ClientContext context = new DefaultOAuth2ClientContext(
					new DefaultAccessTokenRequest());
			Authentication principal = SecurityContextHolder.getContext()
					.getAuthentication();
			if (principal instanceof OAuth2Authentication) {
				OAuth2Authentication authentication = (OAuth2Authentication) principal;
				Object details = authentication.getDetails();
				if (details instanceof OAuth2AuthenticationDetails) {
					OAuth2AuthenticationDetails oauthsDetails = (OAuth2AuthenticationDetails) details;
					String token = oauthsDetails.getTokenValue();
					context.setAccessToken(new DefaultOAuth2AccessToken(token));
				}
			}
			return context;
		}

	}

	/**
	 * Condition to check if a {@code security.oauth2.client.client-id} is specified.
	 */
	static class OAuth2ClientIdCondition extends SpringBootCondition {

		@Override
		public ConditionOutcome getMatchOutcome(ConditionContext context,
				AnnotatedTypeMetadata metadata) {
			String clientId = context.getEnvironment()
					.getProperty("security.oauth2.client.client-id");
			ConditionMessage.Builder message = ConditionMessage
					.forCondition("OAuth Client ID");
			if (StringUtils.hasLength(clientId)) {
				return ConditionOutcome.match(message
						.foundExactly("security.oauth2.client.client-id property"));
			}
			return ConditionOutcome.noMatch(message
					.didNotFind("security.oauth2.client.client-id property").atAll());
		}

	}

	/**
	 * Condition to check for no client credentials.
	 */
	static class NoClientCredentialsCondition extends NoneNestedConditions {

		NoClientCredentialsCondition() {
			super(ConfigurationPhase.PARSE_CONFIGURATION);
		}

		@Conditional(ClientCredentialsCondition.class)
		static class ClientCredentialsActivated {
		}

	}

	/**
	 * Condition to check for client credentials.
	 */
	static class ClientCredentialsCondition extends AnyNestedCondition {

		ClientCredentialsCondition() {
			super(ConfigurationPhase.PARSE_CONFIGURATION);
		}

		@ConditionalOnProperty(prefix = "security.oauth2.client", name = "grant-type", havingValue = "client_credentials", matchIfMissing = false)
		static class ClientCredentialsConfigured {
		}

		@ConditionalOnNotWebApplication
		static class NoWebApplication {
		}

	}

}

springboot集成oauth2报错_第1张图片

解决方法:

在application.yml文件中添加配置,对bean进行重新定义覆盖

spring:
  main:
    allow-bean-definition-overriding: true

重新启动,运行正常


  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::        (v2.1.4.RELEASE)

2019-06-05 15:34:51.519  INFO 724 --- [           main] com.hegret.SocialApplication             : Starting SocialApplication on zsx with PID 724 (F:\workspace-test\spring-oauth2-server\target\classes started by zhang in F:\workspace-test\spring-oauth2-server)
2019-06-05 15:34:51.521  INFO 724 --- [           main] com.hegret.SocialApplication             : No active profile set, falling back to default profiles: default
2019-06-05 15:34:52.069  INFO 724 --- [           main] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat initialized with port(s): 8080 (http)
2019-06-05 15:34:52.081  INFO 724 --- [           main] o.apache.catalina.core.StandardService   : Starting service [Tomcat]
2019-06-05 15:34:52.081  INFO 724 --- [           main] org.apache.catalina.core.StandardEngine  : Starting Servlet engine: [Apache Tomcat/9.0.17]
2019-06-05 15:34:52.147  INFO 724 --- [           main] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring embedded WebApplicationContext
2019-06-05 15:34:52.147  INFO 724 --- [           main] o.s.web.context.ContextLoader            : Root WebApplicationContext: initialization completed in 606 ms
2019-06-05 15:34:52.312  INFO 724 --- [           main] o.s.s.concurrent.ThreadPoolTaskExecutor  : Initializing ExecutorService 'applicationTaskExecutor'
2019-06-05 15:34:52.358  INFO 724 --- [           main] o.s.b.a.w.s.WelcomePageHandlerMapping    : Adding welcome page: class path resource [static/index.html]
2019-06-05 15:34:52.398  INFO 724 --- [           main] .s.s.UserDetailsServiceAutoConfiguration : 

Using generated security password: d8670419-1986-4c55-a811-e147c18f0174

2019-06-05 15:34:52.444  INFO 724 --- [           main] o.s.s.web.DefaultSecurityFilterChain     : Creating filter chain: Ant [pattern='/**'], [org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter@1cb19dba, org.springframework.security.web.context.SecurityContextPersistenceFilter@6e106680, org.springframework.security.web.header.HeaderWriterFilter@16c8b7bd, org.springframework.security.web.csrf.CsrfFilter@4dafba3e, org.springframework.security.web.authentication.logout.LogoutFilter@2f5c1332, org.springframework.security.oauth2.client.filter.OAuth2ClientAuthenticationProcessingFilter@7c3ebc6b, org.springframework.security.web.savedrequest.RequestCacheAwareFilter@55ecbafe, org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter@205b132e, org.springframework.security.web.authentication.AnonymousAuthenticationFilter@1931d99, org.springframework.security.web.session.SessionManagementFilter@65bcf7c2, org.springframework.security.web.access.ExceptionTranslationFilter@476a736d, org.springframework.security.web.access.intercept.FilterSecurityInterceptor@5bca7664]
2019-06-05 15:34:52.479  INFO 724 --- [           main] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat started on port(s): 8080 (http) with context path ''
2019-06-05 15:34:52.481  INFO 724 --- [           main] com.hegret.SocialApplication             : Started SocialApplication in 1.146 seconds (JVM running for 1.472)

 

你可能感兴趣的:(springboot,oauth2)