Restful API Permission Design n/A Sureness Integration Springboot Example N/A Database solution

In the previous article restful API permission design – quick build permission project, we described in detail step by step form from scratch using Sureness integration springboot to build a complete authentication function of the permission project background, this quick build background is based on configuration files, In other words, user information, resource information and corresponding permission information are written in the configuration file instead of the database. However, in the conventional enterprise application background, these data information is in the database, today we will describe in detail the use of the database as a data source to integrate Sureness, Springboot to build an enterprise-level complete function of the authentication background project.

For Surenss, both the configuration file scheme and the database scheme replace different data sources. We can completely modify and replace the project based on the configuration file established before and replace the database as the data source.

Learn about the data loading interface provided by Sureness

First let’s take a look at the two user information and resource permission information interfaces provided by Sureness. Users can customize these interfaces to provide data to Sureness from different data sources. When we switch the project from configuration file mode to database mode, we simply replace the implementation classes of these interfaces.

PathTreeProvider resource permission configuration information of the data source interface, we can achieve from the database, text and other load interface want to resource permission configuration data

public interface PathTreeProvider {

    Set<String> providePathData();

    Set<String> provideExcludedResource();
}

Copy the code

This interface mainly needs to implement the above two methods. ProvidePathData is to load the resource permission configuration information, that is, the resourceRole information column of sureness.yml in our configuration file mode. ProvideExcludedResource is the excludedResource information column under sureness.yml that loads which resources can be filtered without authentication.

resourceRole:
  - /api/v2/host===post===[role2,role3,role4]
  - /api/v2/host===get===[role2,role3,role4]
  - /api/v2/host===delete===[role2,role3,role4]
  - /api/v2/host===put===[role2,role3,role4]
  - /api/mi/**===put===[role2,role3,role4]
  - /api/v1/getSource1===get===[role1,role2]
  - /api/v2/getSource2/*/*===get===[role2]

excludedResource:
  - /api/v1/source3===get
  - /api/v3/host===get
  - /**/*.css===get
  - /**/*.ico===get
  - /**/*.png===get
Copy the code

When we use the database schema, it is ok to implement this information to read from the database associatively, and the specification returns eg: / API /v2/host===post===[role2, ROle3,role4

The second related interface of SurenessAccountProvider is the interface to provide user account key information. We need to load the user account information data we want from database or other data sources, such as text, and provide such data to Sureness for user authentication.

public interface SurenessAccountProvider {
    SurenessAccount loadAccount(String appId);
}
Copy the code

This interface mainly needs to implement the loadAccount method above, through the user’s unique identification appID to find the user’s account information from the database or redis cache. User account information class SurenessAccount is as follows:

public class DefaultAccount implements SurenessAccount {

    private String appId;
    private String password;
    private String salt;
    private List<String> ownRoles;
    private boolean disabledAccount;
    private boolean excessiveAttempts;
}
Copy the code

It is relatively simple, mainly needs to provide the user password information, for sureness authentication key to determine whether is correct. For this specific database interface implementation, refer to the class – DatabaseAccountProvider

Use custom configuration to configure sureness

In the previous simple example, we used the default configuration provided by Sureness, which created a new configuration class, Sureness default configuration bean sureness default configuration uses file data source sureness.yml to provide account permission data Default configuration supports JWT, Basic Auth, Digest Auth authentication

@Configuration public class SurenessConfiguration { /** * sureness default config bean * @return default config bean */ @Bean public DefaultSurenessConfig surenessConfig() { return new DefaultSurenessConfig(); }}Copy the code

Before customizing sureness, let’s take a look at the general process of sureness, so that we can easily understand the subsequent custom sureness configuration. The process is as follows:

As described in the process above, the Subject is created by SubjectCreate according to the request body, and the different authentication processors will determine the supported Subject. Instead of using the default configuration, we will use a custom configuration to configure the sureness features. For this custom configuration, we replaced the default file data source with the database data source as follows:

@Configuration public class SurenessConfiguration { @Bean ProcessorManager processorManager(SurenessAccountProvider AccountProvider) {// Processor Processor initializes List<Processor> processorList = new LinkedList<>(); NoneProcessor NoneProcessor = new NoneProcessor(); processorList.add(noneProcessor); JwtProcessor JwtProcessor JwtProcessor = new JwtProcessor(); processorList.add(jwtProcessor); PasswordProcessor PasswordProcessor PasswordProcessor = new PasswordProcessor(); PasswordProcessor = new PasswordProcessor(); // Note that the PasswordProcessor needs to verify the password of the user account, so it needs the account information provider to provide it with the desired account data. // The SurenessAccountProvider accountProvider bean is the account data provider. // The implementation bean is the DatabaseAccountProvider bean described above, which is the account data provider for the database implementation. passwordProcessor.setAccountProvider(accountProvider); processorList.add(passwordProcessor); return new DefaultProcessorManager(processorList); } @bean TreePathRoleMatcher pathRoleMatcher(PathTreeProvider databasePathTreeProvider) {// Here is the PathTreeProvider DatabasePathTreeProvider is a bean instance that provides resource permission configuration information through the database. // Now we instantiate PathTreeProvider, a provider that provides resource permission configuration information through the file sureness.yml documentPathTreeProvider = new DocumentPathTreeProvider(); / / below we instantiate another resource permissions by annotation form @ RequiresRoles @ WithoutAuth provide configuration information provider AnnotationPathTreeProvider AnnotationPathTreeProvider = new  AnnotationPathTreeProvider(); // Set the annotation scan package path, That's the controller path where you provide the API annotationPathTreeProvider.setScanPackages(Collections.singletonList("com.usthe.sureness.sample.tom.controller")); // Initialize the resource permission matcher. We can add all three providers to the matcher to provide resource permission data. The data in the matcher is the set of data provided by these three providers. t DefaultPathRoleMatcher pathRoleMatcher = new DefaultPathRoleMatcher(); pathRoleMatcher.setPathTreeProviderList(Arrays.asList( documentPathTreeProvider, annotationPathTreeProvider, databasePathTreeProvider)); / / use the resource access configuration data to establish the corresponding matching tree pathRoleMatcher. BuildTree (); return pathRoleMatcher; } @bean SubjectFactory SubjectFactory () {} @bean SubjectFactory SubjectFactory () { A different SubjectCreator is required to create a Subject object based on the request information for subsequent processes to use SubjectFactory SubjectFactory = New SurenessSubjectFactory(); / / here we register we need SubjectCreator subjectFactory. RegisterSubjectCreator (arrays.aslist (/ / attention! Mandatory must first add a noSubjectCreator new NoneSubjectServletCreator (), / / register is used to create PasswordSubject creator of new BasicSubjectServletCreator (), New JwtSubjectServletCreator(), // Of course you can implement a custom creator, Implement SubjectCreate interface can be new CustomPasswdSubjectCreator ())); return subjectFactory; } @Bean SurenessSecurityManager securityManager(ProcessorManager processorManager, TreePathRoleMatcher pathRoleMatcher, SubjectFactory SubjectFactory) {// We will combine the above configuration beans to initialize surenessSecurityManager securityManager = SurenessSecurityManager.getInstance(); / / resource permissions set a match securityManager. SetPathRoleMatcher (pathRoleMatcher); / / set the subject creation factory securityManager. SetSubjectFactory (subjectFactory); / / set the CPU processor managers securityManager. SetProcessorManager (processorManager); return securityManager; }}Copy the code

The SurenessConfiguration above details the purpose of each configuration, which we summarize here. SubjectCreator creates the Subject, and the Processor processes the Subject.

The processorManager method provides the processors supported by our configuration. Each processor needs different dependencies. For example, the PasswordProcessor needs to compare and authenticate user accounts and passwords. Therefore, it needs to inject the account information provider to provide it with the account data it wants. Above, we inject the database account information provider.

The pathRoleMatcher method is to provide the resource path and the matcher corresponding to the supported role. This matcher of course also needs the corresponding resource permission data to support, so above we provide three resource permission data providers (database, file, annotation form), and stuff the configuration data provided by them into the matcher.

The subjectFactory method is the Subject factory, and we need to register different types of subject creation methods – that is, SubjectCreator – into the factory for different requests to create the subject

The securityManager approach simply combines all of the above configuration into one manager.

For a specific configuration example, see the class SurenessConfiguration

other

The authentication project is implemented by replacing the file data source with the database data source. However, the design of the database table structure, how to provide sureness want to provide the data interface format through the design of the table data association. This can refer to sureness integration Springboot sample (database solution) which provides a complete database sample implementation and corresponding table design and data.

For more customizations, visit sureness website at su.usthe.com/