当前位置: 首页 > 知识库问答 >
问题:

将Spring授权服务器连接到外部IDP并触发身份验证

鲁弘厚
2023-03-14

我们创建了一个具有 JDBC 后端令牌存储的授权服务器。GitHub 上托管了类似的实现。它在我们的环境中使用不同的授权类型运行良好。不同的 Web 应用程序将其用于 SSO,并颁发令牌,然后这些令牌也用于使用 API。

我们需要一种方法让用户登录,如果从外部IDP返回的用户是经过身份验证的,就颁发令牌,这有点类似于用户从登录表单手动登录。

我们必须使用外部IDP身份验证来扩展此服务器。因此,如果用户连接到他们的域网络,并且具有ADFS(例如),预期流程如下:

  • 用户尝试访问客户端应用
  • 已重定向至授权服务器
  • 用户可以单击按钮通过 ADFS 进行身份验证,而不是输入凭据(这也可以在以后自动执行)
  • ADFS 应返回身份验证正常,包含用户信息
  • 在授权服务器中触发该用户的登录,以便颁发 OAuth2 令牌,并将其重定向回客户端应用

我们已经尝试了多种方法来实现它,并在网上参考了多种资源,但还没有成功。请注意,我们不需要连接到社交媒体IDP,而是需要使用来自企业级的响应,如ADFS、One-登录等。

任何最初的指示都将不胜感激。

共有1个答案

冯育
2023-03-14

要使用 GitHub 进行身份验证并生成可用于下游应用程序的 spring 令牌,我们可以更改我们的代码,如下所示。

在 WebSecurityConfigurerAdapter 中添加以下代码,附加到 configure(HttpSecurity http)

http.exceptionHandling()
                  .authenticationEntryPoint(new LoginUrlAuthenticationEntryPoint("/")).and()
                .addFilterBefore(ssoFilter(), BasicAuthenticationFilter.class).addFilter(customBasicAuthFilter);

然后再次在 WebSecurityConfigurerAdapter 中

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

        @Bean
        @ConfigurationProperties("github")
        public ClientResources github() {
            return new ClientResources();
        }


    private Filter ssoFilter() {
        CompositeFilter filter = new CompositeFilter();
        List<Filter> filters = new ArrayList<>();
        filters.add(ssoFilter(github(), "/login/github"));
        filter.setFilters(filters);
        return filter;
    }

    private Filter ssoFilter(ClientResources client, String path) {
        OAuth2ClientAuthenticationProcessingFilter oAuth2ClientAuthenticationFilter = new OAuth2ClientAuthenticationProcessingFilter(
                path);
        OAuth2RestTemplate oAuth2RestTemplate = new OAuth2RestTemplate(client.getClient(), oauth2ClientContext);
        oAuth2ClientAuthenticationFilter.setRestTemplate(oAuth2RestTemplate);
        UserInfoTokenServices tokenServices = new UserInfoTokenServices(client.getResource().getUserInfoUri(),
                client.getClient().getClientId());
        tokenServices.setRestTemplate(oAuth2RestTemplate);
        oAuth2ClientAuthenticationFilter.setTokenServices(tokenServices);
        return oAuth2ClientAuthenticationFilter;
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.parentAuthenticationManager(authenticationManager);
        PasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
        auth.jdbcAuthentication().dataSource(dataSource).passwordEncoder(passwordEncoder);
    }

添加一个类 客户资源

class ClientResources {

    @NestedConfigurationProperty
    private AuthorizationCodeResourceDetails client = new AuthorizationCodeResourceDetails();

    @NestedConfigurationProperty
    private ResourceServerProperties resource = new ResourceServerProperties();

    public AuthorizationCodeResourceDetails getClient() {
        return client;
    }

    public ResourceServerProperties getResource() {
        return resource;
    }
}

除此之外,我们还需要在我们的应用程序中添加GitHub设置。

github.client.clientId = <<Clientid>>
github.client.clientSecret = <<clientSecret>>
github.client.accessTokenUri = https://github.com/login/oauth/access_token
github.client.userAuthorizationUri = https://github.com/login/oauth/authorize
github.client.clientAuthenticationScheme = form
github.resource.userInfoUri = https://api.github.com/user
logging.level.org.springframework.security = DEBUG

对于其他支持OAuth的应用程序,也可以采用类似的方法。我也在探索如何使用ADFS身份验证。在Stacksoverflow上发布了相同的查询。

 类似资料:
  • 我们正在尝试找出IPC身份验证和授权的最佳实践。我会解释的。我们有一个基于微服务的体系结构SaaS和一个专门的认证服务。该服务负责执行身份验证和管理身份验证令牌(JWT)。 现在的问题是如何验证和授权由其他服务发起的请求(没有特定用户的上下文)? 我们是否应该为每个服务生成一个专用用户,并像对待系统中的任何其他用户一样对待它(具有适当的权限)? 我们是否应该在服务之间部署“硬编码”/动态令牌? 还

  • 我正在尝试使用Spring Boot和OAuth2进行概念验证。我设立了一些项目,与这里概述的项目非常相似: https://spring.io/guides/tutorials/spring-boot-oauth2/ 这里:https://spring.io/guides/tutorials/spring-security-and-angular-js/ 与我的主要区别是我遗漏了所有Angula

  • 我试图通过Jmeter Java请求采样器通过Java代码连接到WSO2身份服务器授权服务。每当我运行我的测试计划(它只有一个指向我的测试类的java请求采样器)时,我都会得到以下错误:

  • 连接到服务器时出错:fatal:用户“postgres”的密码身份验证失败 fatal:用户“postgres”的密码身份验证失败

  • 我有一个REST服务,它依赖于外部系统来验证令牌,但需要自己进行授权(使用like@Secured进行API级访问)。 要求: UI使用外部系统生成令牌 一种可能的解决方案是使用过滤器: > UI使用外部系统生成令牌 UI使用令牌对我的服务进行REST调用 我的服务有一个过滤器,它使用令牌调用外部系统 有效令牌的外部系统发回用户详细信息 我对成功呼叫集的服务与SecurityContextHold

  • 在JWT配置中,我不想做任何花哨的事情,只是想让它暂时通过: 我得到以下异常: 我对此的理解是:看起来,当Google发布访问令牌时,授权服务器(作为Google OAuth的客户机)试图将访问令牌解码为JWT,并抛出异常,因为Google的令牌不是有效的JWT(它只是一个访问令牌)。