欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

SpringBoot集成Spring Security的方法

 更新時(shí)間:2020年07月06日 09:43:10   作者:良許Linux  
Spring security,是一個(gè)強(qiáng)大的和高度可定制的身份驗(yàn)證和訪(fǎng)問(wèn)控制框架。這篇文章主要介紹了SpringBoot集成Spring Security的操作方法,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下

至今Java能夠如此的火爆Spring做出了很大的貢獻(xiàn),它的出現(xiàn)讓Java程序的編寫(xiě)更為簡(jiǎn)單靈活,而Spring如今也形成了自己的生態(tài)圈,今天咱們探討的是Spring旗下的一個(gè)款認(rèn)證工具:SpringSecurity,如今認(rèn)證框架主流“shiro”和“SpringSecurity”,由于和Spring的無(wú)縫銜接,使用SpringSecurity的企業(yè)也越來(lái)越多。

1、Spring Security介紹

Spring security,是一個(gè)強(qiáng)大的和高度可定制的身份驗(yàn)證和訪(fǎng)問(wèn)控制框架。它是確保基于Spring的應(yīng)用程序的標(biāo)準(zhǔn)——來(lái)自官方參考手冊(cè)

Spring security 和 shiro 一樣,具有認(rèn)證、授權(quán)、加密等用于權(quán)限管理的功能。和 shiro 不同的是,Spring security擁有比shiro更豐富的功能,并且,對(duì)于Springboot而言,Spring Security比Shiro更合適一些,因?yàn)槎际荢pring家族成員。今天,我們來(lái)為SpringBoot項(xiàng)目集成Spring Security。

本文所使用的版本:

​SpringBoot : 2.2.6.RELEASE
​Spring Security : 5.2.2.RELEASE

2、配置Spring Security

在SpringBoot中集成Spring Security很簡(jiǎn)單,只需要在pom.xml中添加下面代碼就行:

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-security</artifactId>
</dependency>

這里可以不指定Spring Security的版本號(hào),它會(huì)根據(jù)SpringBoot的版本來(lái)匹配對(duì)應(yīng)的版本,SpringBoot版本是 2.2.6.RELEASE,對(duì)應(yīng)Spring Security的版本是5.2.2.RELEASE。

然后,我們就可以將springboot啟動(dòng)了。

當(dāng)我們嘗試訪(fǎng)問(wèn)項(xiàng)目時(shí),它會(huì)跳轉(zhuǎn)到這個(gè)界面來(lái):

​對(duì)!在此之前,你什么也不用做。這就是Spring Security的優(yōu)雅之處。你只需要引入Spring Security的包,它就能在你的項(xiàng)目中工作。因?yàn)樗呀?jīng)幫你實(shí)現(xiàn)了一個(gè)簡(jiǎn)單的登陸界面。根據(jù)官方介紹,登錄使用的賬號(hào)是user,密碼是隨機(jī)密碼,這個(gè)隨機(jī)密碼可以在控制臺(tái)中找到,類(lèi)似這樣的一句話(huà):

Using generated security password: 1cb77bc5-8d74-4846-9b6c-4813389ce096

​Using generated security password后面的的就是系統(tǒng)給的隨機(jī)密碼,我們可以使用這個(gè)密碼進(jìn)行登錄。隨機(jī)密碼在每一次啟動(dòng)服務(wù)后生成(如果你配置了熱部署devtools,你得隨時(shí)留意控制臺(tái)了,因?yàn)槊慨?dāng)你修改了代碼,系統(tǒng)會(huì)自動(dòng)重啟,那時(shí)隨機(jī)密碼就會(huì)重新生成)。

​當(dāng)然,這樣的功能一定不是你想要的,也一定不會(huì)就這樣拿給你的用戶(hù)使用。那么,接下來(lái),讓我們把它配置成我們想要的樣子。

​要實(shí)現(xiàn)自定義配置,首先要?jiǎng)?chuàng)建一個(gè)繼承于WebSecurityConfigurerAdapter的配置類(lèi):

import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

}

​這里使用了@EnableWebSecurity注解,這個(gè)注解是Spring Security用于啟用web安全的注解。具體實(shí)現(xiàn),這里就不深入了。

​要實(shí)現(xiàn)自定義攔截配置,首先得告訴Spring Security,用戶(hù)信息從哪里獲取,以及用戶(hù)對(duì)應(yīng)的角色等信息。這里就需要重寫(xiě)WebSecurityConfigurerAdapter的configure(AuthenticationManagerBuilder auth)方法了。這個(gè)方法將指使Spring Security去找到用戶(hù)列表,然后再與想要通過(guò)攔截器的用戶(hù)進(jìn)行比對(duì),再進(jìn)行下面的步驟。

​Spring Security的用戶(hù)存儲(chǔ)配置有多個(gè)方案可以選擇,包括:

  • 內(nèi)存用戶(hù)存儲(chǔ)
  • 數(shù)據(jù)庫(kù)用戶(hù)存儲(chǔ)
  • LDAP用戶(hù)存儲(chǔ)
  • 自定義用戶(hù)存儲(chǔ)

​我們分別來(lái)看看這幾種用戶(hù)存儲(chǔ)的配置方法:

1.內(nèi)存用戶(hù)存儲(chǔ)

​此配置方式是直接將用戶(hù)信息存儲(chǔ)在內(nèi)存中,這種方式在速度上無(wú)疑是最快的。但只適用于有限個(gè)用戶(hù)數(shù)量,且這些用戶(hù)幾乎不會(huì)發(fā)生改變。我們來(lái)看看配置方法:

@Override
	protected void configure(AuthenticationManagerBuilder auth) throws Exception {
		auth.inMemoryAuthentication().passwordEncoder(passwordEncoder())
			.withUser("zhangsan").password(passwordEncoder().encode("123456")).authorities("ADMIN")
			.and()
			.withUser("lisi").password(passwordEncoder().encode("123456")).authorities("ORDINARY");
	}
	
	private PasswordEncoder passwordEncoder() {
  return new BCryptPasswordEncoder();
 }

​可以看到,AuthenticationManagerBuilder使用構(gòu)造者方式來(lái)構(gòu)建的。在上面方法中,先調(diào)用了inMemoryAuthentication()方法,它來(lái)指定用戶(hù)存儲(chǔ)在內(nèi)存中。接下來(lái)又調(diào)用了passwordEncoder()方法,這個(gè)方法的作用是告訴Spring Security認(rèn)證密碼的加密方式。因?yàn)樵赟pring security5過(guò)后,必須指定某種加密方式,不然程序會(huì)報(bào)錯(cuò)。接下來(lái)調(diào)用的withUser()、password()、authorities()方法,分別是在指定用戶(hù)的賬號(hào)、密碼以及權(quán)限名。在添加完一個(gè)用戶(hù)后,要使用and()方法來(lái)連接下一個(gè)用戶(hù)的添加。

​如果使用這種配置方法,你會(huì)發(fā)現(xiàn),在修改用戶(hù)時(shí),就必須修改代碼。對(duì)于絕大多數(shù)項(xiàng)目來(lái)說(shuō),這種方式是滿(mǎn)足不了需求的,至少我們需要一個(gè)注冊(cè)功能。

2.數(shù)據(jù)庫(kù)用戶(hù)存儲(chǔ)

​將用戶(hù)信息存儲(chǔ)在數(shù)據(jù)庫(kù)中,讓我們可以很方便地對(duì)用戶(hù)信息進(jìn)行增刪改查。并且還可以為用戶(hù)添加除認(rèn)證信息外的附加信息,這樣的設(shè)計(jì)也是我們很多小心應(yīng)用所采取的方式。讓我們來(lái)實(shí)現(xiàn)以下:

@Autowired
	private DataSource dataSource;
	
	@Override
	protected void configure(AuthenticationManagerBuilder auth) throws Exception {
		auth.jdbcAuthentication().dataSource(dataSource).passwordEncoder(passwordEncoder())
			.usersByUsernameQuery(
					"select username, password, status from Users where username = ?")
			.authoritiesByUsernameQuery(
					"select username, authority from Authority where username = ?");
		
	}
	
	private PasswordEncoder passwordEncoder() {
  return new BCryptPasswordEncoder();
 }

​調(diào)用jdbcAuthentication()來(lái)告訴Spring Security使用jdbc的方式來(lái)查詢(xún)用戶(hù)和權(quán)限,dataSource()方法指定數(shù)據(jù)庫(kù)連接信息,passwordEncoder()指定密碼加密規(guī)則,用戶(hù)的密碼數(shù)據(jù)應(yīng)該以同樣的方式進(jìn)行加密存儲(chǔ),不然,兩個(gè)加密方式不同的密碼,匹配補(bǔ)上。usersByUsernameQuery()和authoritiesByUsernameQuery()方法分別定義了查詢(xún)用戶(hù)和權(quán)限信息的sql語(yǔ)句。其實(shí),Spring security為我們默認(rèn)了查詢(xún)用戶(hù)、權(quán)限甚至還有群組用戶(hù)授權(quán)的sql,這三條默認(rèn)的sql存放在org.springframework.security.core.userdetails.jdbc.JdbcDaoImpl中,有興趣的小伙伴可以點(diǎn)進(jìn)去看看。如果你要使用默認(rèn)的,那你的表中關(guān)鍵性的字段必須和語(yǔ)句中的一致。

​使用數(shù)據(jù)庫(kù)來(lái)存儲(chǔ)用戶(hù)和權(quán)限等信息已經(jīng)可以滿(mǎn)足大部分的需求。但是Spring security還為我們提供了另外一種配置方式,讓我們來(lái)看一下。

3.LDAP用戶(hù)存儲(chǔ)

​LDAP:輕型目錄訪(fǎng)問(wèn)協(xié)議,是一個(gè)開(kāi)放的,中立的,工業(yè)標(biāo)準(zhǔn)的應(yīng)用協(xié)議,通過(guò)IP協(xié)議提供訪(fǎng)問(wèn)控制和維護(hù)分布式信息的目錄信息。簡(jiǎn)單來(lái)說(shuō),就是將用戶(hù)信息存放在另外一臺(tái)服務(wù)器中(當(dāng)然,也可以在同一臺(tái)服務(wù)器,但我們一般不這么做),通過(guò)網(wǎng)絡(luò)來(lái)進(jìn)行訪(fǎng)問(wèn)的技術(shù)。

​我們來(lái)簡(jiǎn)單配置一下:

@Override
	protected void configure(AuthenticationManagerBuilder auth) throws Exception {
		LdapAuthenticationProviderConfigurer<AuthenticationManagerBuilder> configurer = 					auth.ldapAuthentication()
			.userSearchBase("ou=people")
			.userSearchFilter("(uid={0})")
			.groupSearchBase("ou=groups")
			.groupSearchFilter("member={0}");
			
		configurer.passwordCompare()
			.passwordEncoder(passwordEncoder())
			.passwordAttribute("passcode");
		configurer.contextSource().url("ldap://xxxxx.com:33389/dc=xxxxxx,dc=com");
	}
	
	private PasswordEncoder passwordEncoder() {
  return new BCryptPasswordEncoder();
 }

​userSearchFilter()和groupSearchFilter()設(shè)置的是用戶(hù)和群組的過(guò)濾條件,而userSearchBase()和groupSearchBase()設(shè)置了搜索起始位置,contextSource().url()設(shè)置LDAP服務(wù)器的地址。如果沒(méi)有遠(yuǎn)程的服務(wù)器可以使用contextSource().root()來(lái)使用嵌入式LDAP服務(wù)器,此方式將使用項(xiàng)目中的用戶(hù)數(shù)據(jù)文件來(lái)提供認(rèn)證服務(wù)。

​如果以上幾種方式還不能滿(mǎn)足我們的需求,我們可以用自定義的方式來(lái)配置。

4.自定義用戶(hù)存儲(chǔ)

​自定義用戶(hù)存儲(chǔ),就是自行使用認(rèn)證名稱(chēng)來(lái)查找對(duì)應(yīng)的用戶(hù)數(shù)據(jù),然后交給Spring Security使用。我們需要定義一個(gè)實(shí)現(xiàn)UserDetailsService的service類(lèi):

@Service
public class MyUserDetailsService implements UserDetailsService{

	@Autowired
	private UserMapper userMapper;
	
	@Override
	public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
		User user = userMapper.getUserByUsername(username);
		return user == null ? new User() : user;
	}
}

public class User implements UserDetails {
 ...
}

​該類(lèi)只需要實(shí)現(xiàn)一個(gè)方法:loadUserByUsername()。該方法需要做的是使用傳過(guò)來(lái)的username來(lái)匹配一個(gè)帶有密碼等信息的用戶(hù)實(shí)體。需要注意的是這里的User類(lèi)需要實(shí)現(xiàn)UserDetails,也就是說(shuō),查到的信息里,必須得有Spring Security所需要的信息。

​下面,讓我們來(lái)繼續(xù)配置:

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

	@Autowired
	private MyUserDetailsService userDetailsService;
	
	@Override
	protected void configure(AuthenticationManagerBuilder auth) throws Exception {
		auth.userDetailsService(userDetailsService)
			.passwordEncoder(passwordEncoder());
	}
	
	@Bean
	private PasswordEncoder passwordEncoder() {
  return new BCryptPasswordEncoder();
 }
}

​這樣的配置方法就很簡(jiǎn)單了,只需要告訴Spring Security你的UserDetailsService實(shí)現(xiàn)類(lèi)是哪個(gè)就可以了,它會(huì)去調(diào)用loadUserByUsername()來(lái)查找用戶(hù)。

​以上就是Spring Security所提供的4種用戶(hù)存儲(chǔ)方式,接下來(lái),需要考慮的是,怎么攔截請(qǐng)求。

3、請(qǐng)求攔截

1.安全規(guī)則

​Spring Security的請(qǐng)求攔截配置方法是用戶(hù)存儲(chǔ)配置方法的重載方法,我們先來(lái)簡(jiǎn)單配置一下:

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

	@Override
	protected void configure(HttpSecurity http) throws Exception {
		http.authorizeRequests()
			.antMatchers("/user", "/menu")
			.hasRole("ADMIN")
			.antMatchers("/", "/**").permitAll();
	}
}

​調(diào)用authorizeRequests()方法后,就可以添加自定義攔截路徑了。antMatchers()方法配置了請(qǐng)求路徑,hasRole()和permitAll()指定了訪(fǎng)問(wèn)規(guī)則,分別表示擁有“ADMIN”權(quán)限的用戶(hù)才能訪(fǎng)問(wèn)、所有用戶(hù)可以訪(fǎng)問(wèn)。

​需要注意的是:這里的配置需要成對(duì)出現(xiàn),并且配置的順序也很重要。聲明在前面的規(guī)則擁有更高的優(yōu)先級(jí)。也就是說(shuō),如果我們將.antMatchers("/", "/").permitAll()**放到了最前面,像這樣:

@Override
	protected void configure(HttpSecurity http) throws Exception {
		http.authorizeRequests()
			.antMatchers("/", "/**").permitAll()
    .antMatchers("/user", "/menu")
			.hasRole("ADMIN");
	}

​那么,下面的"/user"和 "/menu"的配置是徒勞,因?yàn)榍懊娴囊?guī)則已經(jīng)指明所有路徑能被所有人訪(fǎng)問(wèn)。當(dāng)然權(quán)限的規(guī)則方法還有很多,我這里只列舉了兩個(gè)。以下為常見(jiàn)的內(nèi)置表達(dá)式:

表達(dá) 描述
hasRole(String role) 返回true當(dāng)前委托人是否具有指定角色。例如, hasRole('admin')默認(rèn)情況下,如果提供的角色不是以“ ROLE_”開(kāi)頭,則會(huì)添加該角色??梢酝ㄟ^(guò)修改defaultRolePrefixon來(lái)自定義DefaultWebSecurityExpressionHandler。
hasAnyRole(String… roles) 返回true當(dāng)前委托人是否具有提供的任何角色(以逗號(hào)分隔的字符串列表形式)。例如, hasAnyRole('admin', 'user')默認(rèn)情況下,如果提供的角色不是以“ ROLE_”開(kāi)頭,則會(huì)添加該角色??梢酝ㄟ^(guò)修改defaultRolePrefixon來(lái)自定義DefaultWebSecurityExpressionHandler。
hasAuthority(String authority) 返回true當(dāng)前委托人是否具有指定權(quán)限。例如, hasAuthority('read')
hasAnyAuthority(String… authorities) 返回true如果當(dāng)前主體具有任何所提供的當(dāng)局的(給定為逗號(hào)分隔的字符串列表)例如, hasAnyAuthority('read', 'write')
principal 允許直接訪(fǎng)問(wèn)代表當(dāng)前用戶(hù)的主體對(duì)象
authentication 允許直接訪(fǎng)問(wèn)Authentication從SecurityContext
permitAll 始終評(píng)估為 true
denyAll 始終評(píng)估為 false
isAnonymous() 返回true當(dāng)前委托人是否為匿名用戶(hù)
isRememberMe() 返回true當(dāng)前主體是否是“記住我”的用戶(hù)
isAuthenticated() true如果用戶(hù)不是匿名的,則返回
isFullyAuthenticated() 返回true如果用戶(hù)不是匿名或記得,我的用戶(hù)
hasPermission(Object target, Object permission) 返回true用戶(hù)是否可以訪(fǎng)問(wèn)給定權(quán)限的給定目標(biāo)。例如,hasPermission(domainObject, 'read')
hasPermission(Object targetId, String targetType, Object permission) 返回true用戶(hù)是否可以訪(fǎng)問(wèn)給定權(quán)限的給定目標(biāo)。例如,hasPermission(1, 'com.example.domain.Message', 'read')

除此之外,還有一個(gè)支持SpEL表達(dá)式計(jì)算的方法,它的使用方法如下:

@Override
	protected void configure(HttpSecurity http) throws Exception {
		http.authorizeRequests()
			.antMatchers("/user", "/menu")
			.access("hasRole('ADMIN')")
			.antMatchers("/", "/**").permitAll();
	}

​它所實(shí)現(xiàn)的規(guī)則和上面的方法一樣。Spring Security還提供了其他豐富的SpEL表達(dá)式,如:

表達(dá) 描述
hasRole(String role) 返回true當(dāng)前委托人是否具有指定角色。例如, hasRole('admin')默認(rèn)情況下,如果提供的角色不是以“ ROLE_”開(kāi)頭,則會(huì)添加該角色??梢酝ㄟ^(guò)修改defaultRolePrefixon來(lái)自定義DefaultWebSecurityExpressionHandler。
hasAnyRole(String… roles) 返回true當(dāng)前委托人是否具有提供的任何角色(以逗號(hào)分隔的字符串列表形式)。例如, hasAnyRole('admin', 'user')默認(rèn)情況下,如果提供的角色不是以“ ROLE_”開(kāi)頭,則會(huì)添加該角色。可以通過(guò)修改defaultRolePrefixon來(lái)自定義DefaultWebSecurityExpressionHandler。
hasAuthority(String authority) 返回true當(dāng)前委托人是否具有指定權(quán)限。例如, hasAuthority('read')
hasAnyAuthority(String… authorities) 返回true如果當(dāng)前主體具有任何所提供的當(dāng)局的(給定為逗號(hào)分隔的字符串列表)例如, hasAnyAuthority('read', 'write')
principal 允許直接訪(fǎng)問(wèn)代表當(dāng)前用戶(hù)的主體對(duì)象
authentication 允許直接訪(fǎng)問(wèn)Authentication從SecurityContext
permitAll 始終評(píng)估為 true
denyAll 始終評(píng)估為 false
isAnonymous() 返回true當(dāng)前委托人是否為匿名用戶(hù)
isRememberMe() 返回true當(dāng)前主體是否是“記住我”的用戶(hù)
isAuthenticated() true如果用戶(hù)不是匿名的,則返回
isFullyAuthenticated() 返回true如果用戶(hù)不是匿名或記得,我的用戶(hù)
hasPermission(Object target, Object permission) 返回true用戶(hù)是否可以訪(fǎng)問(wèn)給定權(quán)限的給定目標(biāo)。例如,hasPermission(domainObject, 'read')
hasPermission(Object targetId, String targetType, Object permission) 返回true用戶(hù)是否可以訪(fǎng)問(wèn)給定權(quán)限的給定目標(biāo)。例如,hasPermission(1, 'com.example.domain.Message', 'read')

2.登錄

​如果此時(shí),我們有自己的登錄界面,需要替換掉Spring Security所提供的默認(rèn)的界面,這時(shí)可以用fromLogin()和loginPage()方法來(lái)實(shí)現(xiàn):

@Override
	protected void configure(HttpSecurity http) throws Exception {
		http.authorizeRequests()
			.antMatchers("/user", "/menu")
			.access("hasRole('ADMIN')")
			.antMatchers("/", "/**").permitAll()
			.and()
			.formLogin()
			.loginPage("/login");
	}

​這便將登錄地址指向了“/login”。如果需要指定登錄成功時(shí),跳轉(zhuǎn)的地址,可以使用defaultSuccessUrl()方法:

 .and()
   .formLogin()
   .loginPage("/login")
   .defaultSuccessUrl("/home")

​此時(shí)用戶(hù)登錄過(guò)后,將跳轉(zhuǎn)到主頁(yè)來(lái)。

​下面,我們來(lái)看看登出。

3.登出

​和登錄類(lèi)似的,可以使用logout()和logoutSuccessUrl()方法來(lái)實(shí)現(xiàn):

.and()
			.logout()
			.logoutSuccessUrl("/login")

​上面例子中,用戶(hù)登出后將跳轉(zhuǎn)到登錄界面。

4、小結(jié)

​至此,我們已基本了解了Spring Security配置,可以將它配置成我們想要的樣子(基本)。其實(shí)Spring Security能做的事還有很多,光看我這篇文章是不夠的。學(xué)習(xí)它最有效的方法就是閱讀官方文檔。里面有關(guān)于Spring Security最全最新的知識(shí)?。ü倬W(wǎng)地址:https://spring.io/projects/spring-security)

到此這篇關(guān)于SpringBoot集成Spring Security的文章就介紹到這了,更多相關(guān)SpringBoot集成Spring Security內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • java中參數(shù)傳遞方式詳解

    java中參數(shù)傳遞方式詳解

    這篇文章主要介紹了java中參數(shù)傳遞方式詳解的相關(guān)資料,需要的朋友可以參考下
    2017-03-03
  • 使用Java WebSocket獲取客戶(hù)端IP地址的示例代碼

    使用Java WebSocket獲取客戶(hù)端IP地址的示例代碼

    在開(kāi)發(fā)Web應(yīng)用程序時(shí),我們通常需要獲取客戶(hù)端的 IP 地址用于日志記錄、身份驗(yàn)證、限制訪(fǎng)問(wèn)等操作,本文將介紹如何使用Java WebSocket API獲取客戶(hù)端IP地址,以及如何在常見(jiàn)的WebSocket框架中獲得客戶(hù)端 IP地址,需要的朋友可以參考下
    2023-11-11
  • ChatGpt都使用的Java BPE分詞算法不要了解一下

    ChatGpt都使用的Java BPE分詞算法不要了解一下

    Byte Pair Encoding(BPE)是一種文本壓縮算法,它通常用于自然語(yǔ)言處理領(lǐng)域中的分詞、詞匯表構(gòu)建等任務(wù),本文將對(duì) BPE 算法進(jìn)行全面、詳細(xì)的講解,并提供 Java 相關(guān)的代碼示例,希望對(duì)大家有所幫助
    2023-06-06
  • 詳解hibernate4基本實(shí)現(xiàn)原理

    詳解hibernate4基本實(shí)現(xiàn)原理

    本文通過(guò)圖文并茂的形式給大家介紹的hibernate4基本實(shí)現(xiàn)原理,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友參考下吧
    2017-09-09
  • 淺談Spring如何解決循環(huán)依賴(lài)的問(wèn)題

    淺談Spring如何解決循環(huán)依賴(lài)的問(wèn)題

    這篇文章主要介紹了淺談Spring如何解決循環(huán)依賴(lài)的問(wèn)題,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2019-09-09
  • 利用Maven添加工程版本信息及時(shí)間戳

    利用Maven添加工程版本信息及時(shí)間戳

    這篇文章主要介紹了利用Maven添加工程版本信息及時(shí)間戳方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-12-12
  • MyBatis一級(jí)與二級(jí)緩存相關(guān)配置

    MyBatis一級(jí)與二級(jí)緩存相關(guān)配置

    mybatis-plus是一個(gè)Mybatis的增強(qiáng)工具,在Mybatis的基礎(chǔ)上只做增強(qiáng)不做改變,為簡(jiǎn)化開(kāi)發(fā)、提高效率而生,這篇文章帶你了解Mybatis的一級(jí)和二級(jí)緩存
    2023-01-01
  • Java通過(guò)SSLEngine與NIO實(shí)現(xiàn)HTTPS訪(fǎng)問(wèn)的操作方法

    Java通過(guò)SSLEngine與NIO實(shí)現(xiàn)HTTPS訪(fǎng)問(wèn)的操作方法

    這篇文章主要介紹了Java通過(guò)SSLEngine與NIO實(shí)現(xiàn)HTTPS訪(fǎng)問(wèn),需要在Connect操作、Connected操作、Read和Write操作中加入SSL相關(guān)的處理即可,需要的朋友可以參考下
    2021-08-08
  • Java中新建一個(gè)文件、目錄及路徑操作實(shí)例

    Java中新建一個(gè)文件、目錄及路徑操作實(shí)例

    這篇文章主要給大家介紹了關(guān)于Java中新建一個(gè)文件、目錄及路徑操作的相關(guān)資料,新建文件、目錄及路徑是我們?nèi)粘i_(kāi)發(fā)中經(jīng)常會(huì)遇到的一個(gè)需求,本文通過(guò)示例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2023-12-12
  • 修改Android應(yīng)用的樣式的一些關(guān)鍵點(diǎn)解析

    修改Android應(yīng)用的樣式的一些關(guān)鍵點(diǎn)解析

    這篇文章主要介紹了修改Android應(yīng)用的樣式的一些關(guān)鍵點(diǎn),即對(duì)影響外觀的theme跟style的相關(guān)修改,需要的朋友可以參考下
    2015-12-12

最新評(píng)論