1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.shiro.web.config;
20
21 import org.apache.shiro.config.Ini;
22 import org.apache.shiro.config.IniFactorySupport;
23 import org.apache.shiro.config.IniSecurityManagerFactory;
24 import org.apache.shiro.config.ReflectionBuilder;
25 import org.apache.shiro.util.CollectionUtils;
26 import org.apache.shiro.util.Factory;
27 import org.apache.shiro.web.filter.mgt.DefaultFilter;
28 import org.apache.shiro.web.filter.mgt.FilterChainManager;
29 import org.apache.shiro.web.filter.mgt.FilterChainResolver;
30 import org.apache.shiro.web.filter.mgt.PathMatchingFilterChainResolver;
31 import org.slf4j.Logger;
32 import org.slf4j.LoggerFactory;
33
34 import javax.servlet.Filter;
35 import javax.servlet.FilterConfig;
36 import java.util.Collections;
37 import java.util.LinkedHashMap;
38 import java.util.List;
39 import java.util.Map;
40
41
42
43
44
45
46 public class IniFilterChainResolverFactory extends IniFactorySupport<FilterChainResolver> {
47
48 public static final String FILTERS = "filters";
49 public static final String URLS = "urls";
50
51 private static transient final Logger log = LoggerFactory.getLogger(IniFilterChainResolverFactory.class);
52
53 private FilterConfig filterConfig;
54
55 private List<String> globalFilters = Collections.singletonList(DefaultFilter.invalidRequest.name());
56
57 public IniFilterChainResolverFactory() {
58 super();
59 }
60
61 public IniFilterChainResolverFactory(Ini ini) {
62 super(ini);
63 }
64
65 public IniFilterChainResolverFactory(Ini ini, Map<String, ?> defaultBeans) {
66 this(ini);
67 this.setDefaults(defaultBeans);
68 }
69
70 public FilterConfig getFilterConfig() {
71 return filterConfig;
72 }
73
74 public void setFilterConfig(FilterConfig filterConfig) {
75 this.filterConfig = filterConfig;
76 }
77
78 public List<String> getGlobalFilters() {
79 return globalFilters;
80 }
81
82 public void setGlobalFilters(List<String> globalFilters) {
83 this.globalFilters = globalFilters;
84 }
85
86 protected FilterChainResolver createInstance(Ini ini) {
87 FilterChainResolver filterChainResolver = createDefaultInstance();
88 if (filterChainResolver instanceof PathMatchingFilterChainResolver) {
89 PathMatchingFilterChainResolverhiro/web/filter/mgt/PathMatchingFilterChainResolver.html#PathMatchingFilterChainResolver">PathMatchingFilterChainResolver resolver = (PathMatchingFilterChainResolver) filterChainResolver;
90 FilterChainManager manager = resolver.getFilterChainManager();
91 buildChains(manager, ini);
92 }
93 return filterChainResolver;
94 }
95
96 protected FilterChainResolver createDefaultInstance() {
97 FilterConfig filterConfig = getFilterConfig();
98 if (filterConfig != null) {
99 return new PathMatchingFilterChainResolver(filterConfig);
100 } else {
101 return new PathMatchingFilterChainResolver();
102 }
103 }
104
105 protected void buildChains(FilterChainManager manager, Ini ini) {
106
107 Ini.Section section = ini.getSection(FILTERS);
108
109 if (!CollectionUtils.isEmpty(section)) {
110 String msg = "The [{}] section has been deprecated and will be removed in a future release! Please " +
111 "move all object configuration (filters and all other objects) to the [{}] section.";
112 log.warn(msg, FILTERS, IniSecurityManagerFactory.MAIN_SECTION_NAME);
113 }
114
115 Map<String, Object> defaults = new LinkedHashMap<String, Object>();
116
117 Map<String, Filter> defaultFilters = manager.getFilters();
118
119
120
121
122 if (!CollectionUtils.isEmpty(defaultFilters)) {
123 defaults.putAll(defaultFilters);
124 }
125
126
127 Map<String, ?> defaultBeans = getDefaults();
128 if (!CollectionUtils.isEmpty(defaultBeans)) {
129 defaults.putAll(defaultBeans);
130 }
131
132 Map<String, Filter> filters = getFilters(section, defaults);
133
134
135 registerFilters(filters, manager);
136
137 manager.setGlobalFilters(getGlobalFilters());
138
139
140 section = ini.getSection(URLS);
141 createChains(section, manager);
142
143
144 manager.createDefaultChain("/**");
145 }
146
147 protected void registerFilters(Map<String, Filter> filters, FilterChainManager manager) {
148 if (!CollectionUtils.isEmpty(filters)) {
149 boolean init = getFilterConfig() != null;
150 for (Map.Entry<String, Filter> entry : filters.entrySet()) {
151 String name = entry.getKey();
152 Filter filter = entry.getValue();
153 manager.addFilter(name, filter, init);
154 }
155 }
156 }
157
158 protected Map<String, Filter> getFilters(Map<String, String> section, Map<String, ?> defaults) {
159
160 Map<String, Filter> filters = extractFilters(defaults);
161
162 if (!CollectionUtils.isEmpty(section)) {
163 ReflectionBuilderlder.html#ReflectionBuilder">ReflectionBuilder builder = new ReflectionBuilder(defaults);
164 Map<String, ?> built = builder.buildObjects(section);
165 Map<String,Filter> sectionFilters = extractFilters(built);
166
167 if (CollectionUtils.isEmpty(filters)) {
168 filters = sectionFilters;
169 } else {
170 if (!CollectionUtils.isEmpty(sectionFilters)) {
171 filters.putAll(sectionFilters);
172 }
173 }
174 }
175
176 return filters;
177 }
178
179 private Map<String, Filter> extractFilters(Map<String, ?> objects) {
180 if (CollectionUtils.isEmpty(objects)) {
181 return null;
182 }
183 Map<String, Filter> filterMap = new LinkedHashMap<String, Filter>();
184 for (Map.Entry<String, ?> entry : objects.entrySet()) {
185 String key = entry.getKey();
186 Object value = entry.getValue();
187 if (value instanceof Filter) {
188 filterMap.put(key, (Filter) value);
189 }
190 }
191 return filterMap;
192 }
193
194 protected void createChains(Map<String, String> urls, FilterChainManager manager) {
195 if (CollectionUtils.isEmpty(urls)) {
196 if (log.isDebugEnabled()) {
197 log.debug("No urls to process.");
198 }
199 return;
200 }
201
202 if (log.isTraceEnabled()) {
203 log.trace("Before url processing.");
204 }
205
206 for (Map.Entry<String, String> entry : urls.entrySet()) {
207 String path = entry.getKey();
208 String value = entry.getValue();
209 manager.createChain(path, value);
210 }
211 }
212 }