springBoot整合shiro如何解決讀取不到@value值問題
springBoot整合shiro讀取不到@value值
1、通過@value將值注入shiroconfigure靜態(tài)屬性
private static String dropmenu_post;
@Value("${dropmenu.post}")
public void setDropmenu_post(String dropmenu_post) {
ShiroConfig.dropmenu_post = dropmenu_post;
}2、將LifecycleBeanPostProcessor獲取該對(duì)象的方法設(shè)為靜態(tài)
@Bean
public static LifecycleBeanPostProcessor getLifecycleBeanPostProcessor() {
return new LifecycleBeanPostProcessor();
}3、使用
@Bean(name = "shiroFilter")
public ShiroFilterFactoryBean getShiroFilterFactoryBean(
@Qualifier("securityManager") SecurityManager securityManager) {
ShiroFilterFactoryBean sfb = new ShiroFilterFactoryBean();
sfb.setSecurityManager(securityManager);
sfb.setLoginUrl(ShiroConfig.dropmenu_post + "/login");
sfb.setSuccessUrl("/report/list");
sfb.setUnauthorizedUrl("/goLogin");
Map<String, Filter> filters = new HashMap<>();
filters.put("per", getPermissionFilter());
// filters.put("verCode",getVerfityCodeFilter());
sfb.setFilters(filters);
Map<String, String> filterMap = new LinkedHashMap<>();
filterMap.put("/resources/**", "anon");
filterMap.put("/fx/**", "anon");
filterMap.put("/fx2/**", "anon");
filterMap.put("/process/**", "anon");
filterMap.put("/repeat/**", "anon");
filterMap.put("/repeat2/**", "anon");
filterMap.put("/ipad/**", "anon");
filterMap.put("/student/**", "anon");
filterMap.put("/excel/**", "anon");
filterMap.put("/exam/**", "anon");
filterMap.put("/progress/**", "anon");
filterMap.put("/param/**", "anon");
filterMap.put("/statics/**", "anon");
filterMap.put("/download/**", "anon");
filterMap.put("/knowledge/**", "anon");
filterMap.put("/login", "anon");
filterMap.put("/actuator/**", "anon");
filterMap.put("/hystrix", "anon");
filterMap.put("/hystrix.stream", "anon");
filterMap.put("/logout", "logout");
filterMap.put("/js/**", "anon");
filterMap.put("/css/**", "anon");
filterMap.put("/user/**", "per");
filterMap.put("/**", "authc");
sfb.setFilterChainDefinitionMap(filterMap);
return sfb;
}整個(gè)類的代碼如下
package com.whty.hxx.config;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;
import javax.servlet.Filter;
import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
import org.apache.shiro.cache.ehcache.EhCacheManager;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.spring.LifecycleBeanPostProcessor;
import org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.apache.shiro.web.servlet.Cookie;
import org.apache.shiro.web.servlet.ShiroHttpSession;
import org.apache.shiro.web.servlet.SimpleCookie;
import org.apache.shiro.web.session.mgt.DefaultWebSessionManager;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.filter.DelegatingFilterProxy;
import com.whty.hxx.common.filter.PermissionFilter;
import com.whty.hxx.common.shiro.LoginRealm;
import com.whty.hxx.common.shiro.MyWebSessionManager;
import com.whty.hxx.common.shiro.ShiroUtil;
import com.whty.hxx.common.shiro.redis.RedisSessionDAO;
import com.whty.hxx.common.shiro.redis.ShiroRedisCacheManager;
import lombok.extern.slf4j.Slf4j;
/**
* @author yym
* @date 2018/5/31. spring shiro 配置
*/
@Configuration
@Slf4j
public class ShiroConfig {
private static String dropmenu_post;
@Value("${dropmenu.post}")
public void setDropmenu_post(String dropmenu_post) {
ShiroConfig.dropmenu_post = dropmenu_post;
}
@Bean(value = "ehCacheManager")
public EhCacheManager ehCacheManager() {
EhCacheManager ehCacheManager = new EhCacheManager();
ehCacheManager.setCacheManagerConfigFile("classpath:ehcache/ehcache.xml");
return ehCacheManager;
}
// @Bean(name="credentialsMatcher")
// public RetryLimitCredentialsMatcher
// getRetryLimitCredentialsMatcher(@Qualifier("redisCacheManager")
// ShiroSpringCacheManager redisCacheManager){
RetryLimitCredentialsMatcher rm = new
// RetryLimitCredentialsMatcher(getCacheManager(),2);
// RetryLimitCredentialsMatcher rm = new
// RetryLimitCredentialsMatcher(redisCacheManager);
// rm.setHashAlgorithmName("md5");
// rm.setHashIterations(4);
// return rm;
//
// }
// @Bean(name = "redisCacheManager")
// public ShiroRedisCacheManager redisCacheManager() {
// log.debug("ShiroConfiguration.redisCacheManager()");
// return new ShiroRedisCacheManager();
// }
@Bean(name = "redisSessionDAO")
public RedisSessionDAO redisSessionDAO() {
log.debug("ShiroConfiguration.redisSessionDAO()");
return new RedisSessionDAO();
}
@Bean(name = "loginRealm")
public LoginRealm getLoginRealm(@Qualifier("redisCacheManager") ShiroRedisCacheManager redisCacheManager) {
LoginRealm realm = new LoginRealm();
// 密碼匹配校驗(yàn)??
HashedCredentialsMatcher credentialsMatcher = new HashedCredentialsMatcher();
credentialsMatcher.setHashAlgorithmName("md5");
credentialsMatcher.setHashIterations(4);
realm.setCredentialsMatcher(credentialsMatcher);
realm.setCacheManager(redisCacheManager);
// realm.setCachingEnabled(true);
return realm;
}
@Bean
public static LifecycleBeanPostProcessor getLifecycleBeanPostProcessor() {
return new LifecycleBeanPostProcessor();
}
// /**
// *
// * enterCacheSessionDAO:(EnterpriseCacheSessionDAO shiro sessionDao層的實(shí)現(xiàn)??).
// <br/>
// * 提供了緩存功能的會(huì)話維護(hù),默認(rèn)情況下使用MapCache實(shí)現(xiàn),內(nèi)部使用ConcurrentHashMap保存緩存的會(huì)話???.<br/>
// *
// * @author verywell
// * @return
// * @since JDK 1.8
// */
// @Bean(name="redisCacheSessionDAO")
// public RedisSessionDao
// getEnterCacheSessionDAO(@Qualifier("redisCacheManager")
// ShiroSpringCacheManager redisCacheManager) {
// RedisSessionDao enterCacheSessionDAO = new RedisSessionDao();
// //添加緩存管理??
// enterCacheSessionDAO.setCacheManager(redisCacheManager);
添加ehcache活躍緩存名稱(必須和ehcache緩存名稱??致)
enterCacheSessionDAO.setActiveSessionsCacheName("shiro-activeSessionCache");
// return enterCacheSessionDAO;
// }
// @Bean(name="sessionValidationScheduler")
// public MyQuartzSessionValidationScheduler
// getQuartzSessionValidationScheduler(@Qualifier("redisSessionDAO")RedisSessionDAO
// sessionDAO
// ,@Qualifier("redisCacheManager") ShiroRedisCacheManager redisCacheManager) {
// MyQuartzSessionValidationScheduler sessionValidationScheduler = new
// MyQuartzSessionValidationScheduler();
// sessionValidationScheduler.setSessionValidationInterval(10000);
// DefaultWebSessionManager sessionManager=new DefaultWebSessionManager();
// sessionManager.setCacheManager(redisCacheManager);
// sessionManager.setSessionDAO(sessionDAO);
// sessionValidationScheduler.setSessionManager(sessionManager);
// return sessionValidationScheduler;
// }
@Bean(name = "sessionManager")
public DefaultWebSessionManager getSessionManager(@Qualifier("redisSessionDAO") RedisSessionDAO sessionDAO,
@Qualifier("redisCacheManager") ShiroRedisCacheManager cacheManager) {
MyWebSessionManager sessionManager = new MyWebSessionManager();
sessionManager.setSessionIdUrlRewritingEnabled(false);// sessionId不顯示在url??
sessionManager.setCacheManager(cacheManager);
sessionManager.setSessionDAO(sessionDAO);
// sessionManager.setGlobalSessionTimeout(2000);
// sessionManager.setSessionValidationScheduler(sessionValidationScheduler);
// sessionManager.setSessionValidationInterval(3000);
// 創(chuàng)建會(huì)話Cookie
Cookie cookie = new SimpleCookie(ShiroHttpSession.DEFAULT_SESSION_ID_NAME);
cookie.setName(ShiroUtil.name_serssionId);
cookie.setHttpOnly(true);
sessionManager.setSessionIdCookie(cookie);
return sessionManager;
}
@Bean(name = "securityManager")
public SecurityManager getSecurityManager(@Qualifier("loginRealm") LoginRealm loginRealm,
@Qualifier("sessionManager") DefaultWebSessionManager sessionManager,
@Qualifier("redisCacheManager") ShiroRedisCacheManager cacheManager) {
DefaultWebSecurityManager dwm = new DefaultWebSecurityManager();
dwm.setRealm(loginRealm);
// dwm.setCacheManager(cacheManager);
dwm.setSessionManager(sessionManager);
return dwm;
}
@Bean
public PermissionFilter getPermissionFilter() {
PermissionFilter pf = new PermissionFilter();
return pf;
}
// @Bean
// public VerfityCodeFilter getVerfityCodeFilter(){
// VerfityCodeFilter vf= new VerfityCodeFilter();
// vf.setFailureKeyAttribute("shiroLoginFailure");
// vf.setJcaptchaParam("code");
// vf.setVerfitiCode(true);
// return vf;
// }
@Bean(name = "shiroFilter")
public ShiroFilterFactoryBean getShiroFilterFactoryBean(
@Qualifier("securityManager") SecurityManager securityManager) {
ShiroFilterFactoryBean sfb = new ShiroFilterFactoryBean();
sfb.setSecurityManager(securityManager);
sfb.setLoginUrl(ShiroConfig.dropmenu_post + "/login");
sfb.setSuccessUrl("/report/list");
sfb.setUnauthorizedUrl("/goLogin");
Map<String, Filter> filters = new HashMap<>();
filters.put("per", getPermissionFilter());
// filters.put("verCode",getVerfityCodeFilter());
sfb.setFilters(filters);
Map<String, String> filterMap = new LinkedHashMap<>();
filterMap.put("/resources/**", "anon");
filterMap.put("/fx/**", "anon");
filterMap.put("/fx2/**", "anon");
filterMap.put("/process/**", "anon");
filterMap.put("/repeat/**", "anon");
filterMap.put("/repeat2/**", "anon");
filterMap.put("/ipad/**", "anon");
filterMap.put("/student/**", "anon");
filterMap.put("/excel/**", "anon");
filterMap.put("/exam/**", "anon");
filterMap.put("/progress/**", "anon");
filterMap.put("/param/**", "anon");
filterMap.put("/statics/**", "anon");
filterMap.put("/download/**", "anon");
filterMap.put("/knowledge/**", "anon");
// //===== 測(cè)試
// filterMap.put("/test/**","anon");
// filterMap.put("/report/**","anon");
// filterMap.put("/upload/**","anon");
// filterMap.put("/city/**","anon");
// filterMap.put("/county/**","anon");
// filterMap.put("/unitSchool/**","anon");
// filterMap.put("/regionSchool/**","anon");
// filterMap.put("/school/**","anon");
// filterMap.put("/clazz/**","anon");
// filterMap.put("/clazzEvaluation/**","anon");
// filterMap.put("/schoolEvaluation/**","anon");
// filterMap.put("/canvas/**","anon");
// //===== end
filterMap.put("/login", "anon");
filterMap.put("/actuator/**", "anon");
filterMap.put("/hystrix", "anon");
filterMap.put("/hystrix.stream", "anon");
filterMap.put("/logout", "logout");
filterMap.put("/js/**", "anon");
filterMap.put("/css/**", "anon");
filterMap.put("/user/**", "per");
filterMap.put("/**", "authc");
sfb.setFilterChainDefinitionMap(filterMap);
return sfb;
}
@Bean
public DefaultAdvisorAutoProxyCreator advisorAutoProxyCreator() {
DefaultAdvisorAutoProxyCreator advisorAutoProxyCreator = new DefaultAdvisorAutoProxyCreator();
advisorAutoProxyCreator.setProxyTargetClass(true);
return advisorAutoProxyCreator;
}
@Bean
public AuthorizationAttributeSourceAdvisor getAuthorizationAttributeSourceAdvisor(
@Qualifier("securityManager") SecurityManager securityManager) {
AuthorizationAttributeSourceAdvisor as = new AuthorizationAttributeSourceAdvisor();
as.setSecurityManager(securityManager);
return as;
}
@Bean
public FilterRegistrationBean delegatingFilterProxy() {
FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean();
DelegatingFilterProxy proxy = new DelegatingFilterProxy();
proxy.setTargetFilterLifecycle(true);
proxy.setTargetBeanName("shiroFilter");
filterRegistrationBean.setFilter(proxy);
return filterRegistrationBean;
}
}springboot單元測(cè)試使用@value讀取不到值, yml的兩個(gè)坑
yml兩個(gè)坑
yml 和 properties都可以作為配置文件在springboot項(xiàng)目中使用


縮進(jìn)問題
yml使用空格縮進(jìn)代表包之間的層級(jí)問題,有時(shí)候差一個(gè)空格就可能導(dǎo)致配置不生效。另外,在同級(jí)配置之間使用 # 注釋
也會(huì)導(dǎo)致該問題,因?yàn)槌绦蚴前磳蛹?jí)讀取配置的,加上注釋隔斷上下兩行之后,程序會(huì)不清楚下一條配置是上一個(gè)的下級(jí)還是同級(jí)(大致是這意思。。。)
springboot 2.X版本在單元測(cè)試中讀取不到y(tǒng)ml配置文件的值
這是個(gè)大坑,在項(xiàng)目中寫單元測(cè)試的時(shí)候需要讀取一個(gè)yml配置文件的值,發(fā)現(xiàn)無論如何都讀取不到,后來發(fā)現(xiàn)了這個(gè)坑。改成properties就行了。
總結(jié)
建議用properties!
以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
相關(guān)文章
Java基本數(shù)據(jù)類型存儲(chǔ)在JVM中的存儲(chǔ)位置介紹
這篇文章主要介紹了Java基本數(shù)據(jù)類型存儲(chǔ)在JVM中的存儲(chǔ)位置,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-07-07
springboot集成flyway自動(dòng)創(chuàng)表的詳細(xì)配置
Flayway是一款數(shù)據(jù)庫版本控制管理工具,支持?jǐn)?shù)據(jù)庫版本自動(dòng)升級(jí),Migrations可以寫成sql腳本,也可以寫在java代碼里;本文通過實(shí)例代碼給大家介紹springboot集成flyway自動(dòng)創(chuàng)表的詳細(xì)過程,感興趣的朋友一起看看吧2021-06-06
SpringBoot實(shí)現(xiàn)數(shù)據(jù)庫讀寫分離的3種方法小結(jié)
為了提高系統(tǒng)的讀寫性能和可用性,讀寫分離是一種經(jīng)典的數(shù)據(jù)庫架構(gòu)模式,在SpringBoot應(yīng)用中,有多種方式可以實(shí)現(xiàn)數(shù)據(jù)庫讀寫分離,本文將介紹三種主實(shí)現(xiàn)方案,大家可以根據(jù)需要自行選擇2025-04-04
關(guān)于Mybatis插入對(duì)象時(shí)空值的處理
這篇文章主要介紹了關(guān)于Mybatis插入對(duì)象時(shí)空值的處理方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-06-06
Spring AI與DeepSeek實(shí)戰(zhàn)一之快速打造智能對(duì)話應(yīng)用
本文詳細(xì)介紹了如何通過SpringAI框架集成DeepSeek大模型,實(shí)現(xiàn)普通對(duì)話和流式對(duì)話功能,步驟包括申請(qǐng)API-KEY、項(xiàng)目搭建、配置API-KEY、創(chuàng)建ChatClient對(duì)象、創(chuàng)建對(duì)話接口、切換模型、使用prompt模板、流式對(duì)話等,感興趣的朋友一起看看吧2025-03-03
Java?spring注解@PostConstruct實(shí)戰(zhàn)案例講解
我們?cè)赟pring項(xiàng)目中經(jīng)常會(huì)遇到@PostConstruct注解,可能有的伙伴對(duì)這個(gè)注解很陌生,下面這篇文章主要給大家介紹了關(guān)于Java?spring注解@PostConstruct實(shí)戰(zhàn)案例講解的相關(guān)資料,需要的朋友可以參考下2023-12-12

