java - Spring Security OAuth2 - 是否可以更改表和列名称?

标签 java spring spring-security oauth

我正在使用 Spring Boot 和 Spring Security 构建支持 OAuth2 的应用程序。最初,我使用了 here 所示的模式。这样,我至少能让应用程序正常运行。但是,我希望数据库对象的命名稍有不同 - 特别是使用 PascalCase 而不是下划线。

例如,而不是

CREATE TABLE [dbo].[oauth_client_details](
    [client_id] [varchar](256) NOT NULL,
    [resource_ids] [varchar](256) NULL,
    [client_secret] [varchar](256) NULL,
    [scope] [varchar](256) NULL,
    [authorized_grant_types] [varchar](256) NULL,
    [web_server_redirect_uri] [varchar](256) NULL,
    [authorities] [varchar](256) NULL,
    [access_token_validity] [int] NULL,
    [refresh_token_validity] [int] NULL,
    [additional_information] [varchar](4096) NULL,
    [autoapprove] [varchar](256) NULL,
PRIMARY KEY CLUSTERED 
(
    [client_id] ASC
)

我想要:

CREATE TABLE [dbo].[OAuthClientDetails](
    [ClientID] [nvarchar](256) NOT NULL,
    [ResourceIDs] [nvarchar](256) NULL,
    [ClientSecret] [nvarchar](256) NOT NULL,
    [Scope] [nvarchar](256) NULL,
    [AuthorizedGrantTypes] [nvarchar](256) NOT NULL,
    [AccessTokenValidity] [int] NULL,
    [RefreshTokenValidity] [int] NULL,
 CONSTRAINT [PK_OAuthClientDetails] PRIMARY KEY CLUSTERED 
(
    [ClientID] ASC
)

我不确定如何(或者是否可能)覆盖这些期望。例如,当我尝试使用 PascalCase 数据库时,它仍然期望原始的命名风格。请求 token 时我收到以下信息:

"message": "PreparedStatementCallback; bad SQL grammar [select client_id, client_secret, resource_ids, scope, authorized_grant_types, web_server_redirect_uri, authorities, access_token_validity, refresh_token_validity, additional_information, autoapprove from oauth_client_details where client_id = ?]; nested exception is com.microsoft.sqlserver.jdbc.SQLServerException: Invalid object name 'oauth_client_details'.",
"path": "/oauth/token"

我的AuthServerConfig:

 @EnableAuthorizationServer


 @Configuration
public class AuthServerConfig extends AuthorizationServerConfigurerAdapter{
    @Autowired
    private TokenStore tokenStore;

@Autowired
private AccessTokenConverter converter;

 private final AppConfig appConfig; 

private AuthenticationManager authenticationManager;

@Autowired
public AuthServerConfig(AuthenticationManager authenticationManager, AppConfig appConfig) {
    this.authenticationManager = authenticationManager;
    this.appConfig = appConfig;
}

@Override
public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
    security.checkTokenAccess("permitAll()");
    security.tokenKeyAccess("permitAll()");
}

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


    configurer.jdbc(appConfig.dataSource());
}

@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
    TokenEnhancerChain enhancerChain = new TokenEnhancerChain();
    endpoints.tokenStore(tokenStore)
            .accessTokenConverter(converter)
        .authenticationManager(authenticationManager);
}



   @Bean
   @Primary //Making this primary to avoid any accidental duplication with another token service instance of the same name
   public DefaultTokenServices tokenServices() {
      DefaultTokenServices defaultTokenServices = new DefaultTokenServices();
      defaultTokenServices.setTokenStore(tokenStore);
      defaultTokenServices.setSupportRefreshToken(true);
      return defaultTokenServices;
   }       

我的AppConfig类:

@Configuration
public class AppConfig {


    @Value("${spring.datasource.url}")
    private String datasourceUrl;

    @Value("${spring.datasource.driverClassName}")
    private String dbDriverClassName;

    @Value("${spring.datasource.username}")
    private String dbUsername;

    @Value("${spring.datasource.password}")
    private String dbPassword;

    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }

    @Bean
    public DataSource dataSource() {
        final DriverManagerDataSource dataSource = new DriverManagerDataSource();

        dataSource.setDriverClassName(dbDriverClassName);
        dataSource.setUrl(datasourceUrl);
        dataSource.setUsername(dbUsername);
        dataSource.setPassword(dbPassword);

        return dataSource;
    }    

    // Reference: http://www.baeldung.com/spring-security-oauth-jwt

    /* !!!!!!!!!!!!!!!!!!!!!!!!!! 
    ** TODO 
    * Secure key file for deployment.
    !!!!!!!!!!!!!!!!!!!! */
       @Bean
       public JwtAccessTokenConverter accessTokenConverter() {
          JwtAccessTokenConverter converter = new JwtAccessTokenConverter();
          KeyStoreKeyFactory keyStoreKeyFactory = 
                  new KeyStoreKeyFactory(new ClassPathResource("mytest.jks"), "mypass".toCharArray());
                converter.setKeyPair(keyStoreKeyFactory.getKeyPair("mytest"));
          return converter;
       }


       @Bean
       public TokenStore tokenStore() {
          return new JwtTokenStore(accessTokenConverter());
       }

根据Spring Security OAuth Documentation :

NOTE: the schema for the JDBC service is not packaged with the library (because there are too many variations you might like to use in practice), but there is an example you can start from in the test code in github.

但是,它似乎确实对结构做出了一些假设。例如,我从未明确“告诉”应用程序使用名为 o_auth_client_details 的表。

任何指导将不胜感激。谢谢。

最佳答案

您可以自定义JdbcClientDetailsS​​ervice,请参阅

并将其添加到您的配置器中,请参阅 ClientDetailsServiceConfigurer#withClientDetails :

withClientDetails

public ClientDetailsServiceBuilder<?> withClientDetails(ClientDetailsService clientDetailsService) throws Exception 

您修改后的代码:

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

     JdbcClientDetailsService clientDetailsService= new JdbcClientDetailsService(appConfig.dataSource()); 
     clientDetailsService.setDeleteClientDetailsSql(myDeleteClientDetailsSql);
     clientDetailsService.setFindClientDetailsSql(myFindClientDetailsSql); 
     clientDetailsService.setInsertClientDetailsSql(myInsertClientDetailsSql); 
     clientDetailsService.setInsertClientDetailsSql(myInsertClientDetailsSql); 
     clientDetailsService.setSelectClientDetailsSql(mySelectClientDetailsSql); 
     clientDetailsService.setUpdateClientDetailsSql(myUpdateClientDetailsSql); 
     clientDetailsService.setUpdateClientSecretSql(myUpdateClientSecretSql); 

     configurer.withClientDetails(clientDetailsService);
}

关于java - Spring Security OAuth2 - 是否可以更改表和列名称?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48506618/

相关文章:

java - Netbeans 开发 PHP 脚本时速度很慢

java - 泛型类型的 Spring 问题

java - 在 Spring 中使用 Java 驱动程序的无尽 MongoDB ReplicaSetStatus 更新程序异常

spring - spring security如何维护请求之间的认证信息?

spring @PreAuthorize 不适用于 @EnableGlobalMethodSecurity(prePostEnabled = true)

java - Java 中的内部类和字符串文字

java - 正则表达式匹配带通配符的字符串

java - 云存储1.88.0访问inputstream时出现异常

java - 直接支持JSR-330注入(inject)的嵌入式web容器?

spring-boot - Spring WebFlux Security - 是否可以在 SecurityWebFilterChain 上为不同的资源配置多个 ServerAuthenticationEntryPoints