Shiro報錯No SecurityManager accessible to the calling code, either bound to the org.apache.shiro.util.
阿新 • • 發佈:2019-01-10
問題描述:
專案使用 SpringMVC 並使用 Shiro 來管理Session控制權限。
經常會不定期的發現異常:
org.apache.shiro.UnavailableSecurityManagerException: No SecurityManager accessible to the calling code, either bound to the org.apache.shiro.util.ThreadContext or as a vm static singleton. This is an invalid application configuration.
at org.apache .shiro.SecurityUtils.getSecurityManager(SecurityUtils.java:123)
at org.apache.shiro.subject.Subject$Builder.<init>(Subject.java:627)
at org.apache.shiro.SecurityUtils.getSubject(SecurityUtils.java:56)
……………………
……………………
……………………
通俗的對錯誤原因描述為:
你所請求的URL是不在Shiro所管轄範圍的,而你又在你請求的這個URL後試圖通過Shiro來獲取Session,所以對Shiro來說“你不讓我負責的事,為什麼要跟我要結果”。
下面是我web.xml 原來的配置:
<filter>
<filter-name>shiroFilter</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
<init-param>
<param-name>targetFilterLifecycle</param-name>
<param -value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
我修改後的配置為:
<filter>
<filter-name>shiroFilter</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
<init-param>
<param-name>targetFilterLifecycle</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>/*</url-pattern>
<dispatcher>REQUEST</dispatcher>
<dispatcher>FORWARD</dispatcher>
<dispatcher>INCLUDE</dispatcher>
<dispatcher>ERROR</dispatcher>
</filter-mapping>
配置的區別顯而易見。
至此,我再說一下,我後來總結出來我出現這個異常的必現操作:就是我訪問的頁面是404的時候,異常100%出現。
404很明顯是一個ERROR,此前我沒有新增 <dispatcher>ERROR</dispatcher>
,而我在發生錯誤的時候又使用 SecurityUtils.getSubject().getSession()
來獲取Session(我需要從會話中讀取相關資料記錄日誌),所以被Shiro 所拒絕(丟擲異常)。
如果你使用Shiro,並且沒有配置 <dispatcher>ERROR</dispatcher>
。那麼,你登入後,隨便訪問一個不存在的頁面觸發404,或者觸發500這樣的錯誤頁。再回頭看登入後的頁面,登入狀態就丟失了。因為這個時候sessionid 被重新生成覆蓋了登入狀態時的sessionid。