1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.kuali.rice.core.web.cache;
17
18 import java.util.ArrayList;
19 import java.util.Collections;
20 import java.util.Comparator;
21 import java.util.List;
22
23 import javax.servlet.http.HttpServletRequest;
24 import javax.servlet.http.HttpServletResponse;
25
26 import org.kuali.rice.core.api.cache.CacheManagerRegistry;
27 import org.kuali.rice.core.api.util.RiceKeyConstants;
28 import org.kuali.rice.core.api.util.tree.Node;
29 import org.kuali.rice.core.api.util.tree.Tree;
30 import org.kuali.rice.core.impl.services.CoreImplServiceLocator;
31 import org.kuali.rice.kim.api.KimConstants;
32 import org.kuali.rice.kim.api.identity.Person;
33 import org.kuali.rice.kim.api.services.KimApiServiceLocator;
34 import org.kuali.rice.krad.exception.AuthorizationException;
35 import org.kuali.rice.krad.util.GlobalVariables;
36 import org.kuali.rice.krad.util.KRADConstants;
37 import org.kuali.rice.krad.web.controller.UifControllerBase;
38 import org.kuali.rice.krad.web.form.UifFormBase;
39 import org.springframework.cache.CacheManager;
40 import org.springframework.stereotype.Controller;
41 import org.springframework.validation.BindingResult;
42 import org.springframework.web.bind.annotation.ModelAttribute;
43 import org.springframework.web.bind.annotation.RequestMapping;
44 import org.springframework.web.bind.annotation.RequestMethod;
45 import org.springframework.web.servlet.ModelAndView;
46
47 @Controller
48 @RequestMapping(value = "/core/admin/cache")
49 public class CacheAdminController extends UifControllerBase {
50
51 private CacheManagerRegistry registry;
52
53 public synchronized CacheManagerRegistry getRegistry() {
54 if (registry == null) {
55 registry = CoreImplServiceLocator.getCacheManagerRegistry();
56 }
57 return registry;
58 }
59
60
61
62
63 @Override
64 protected CacheAdminForm createInitialForm(HttpServletRequest request) {
65 return new CacheAdminForm();
66 }
67
68 @Override
69 @RequestMapping(params = "methodToCall=start")
70 public ModelAndView start(@ModelAttribute("KualiForm") UifFormBase form, BindingResult result,
71 HttpServletRequest request, HttpServletResponse response) {
72
73 final Tree<String, String> cacheTree = new Tree<String,String>();
74
75 final Node<String,String> root = new Node<String,String>("Root", "Root");
76 final List<CacheManager> cms = new ArrayList<CacheManager>(getRegistry().getCacheManagers());
77 Collections.sort(cms, new ByName());
78
79 for (final CacheManager cm : cms) {
80 final String name = getRegistry().getCacheManagerName(cm);
81 final Node<String, String> cmNode = new Node<String, String>(name, name);
82 final List<String> names = new ArrayList<String>(cm.getCacheNames());
83 Collections.sort(names, String.CASE_INSENSITIVE_ORDER);
84
85 for (final String cn : names) {
86 final Node<String, String> cNode = new Node<String, String>(cn, cn);
87
88
89
90 cmNode.addChild(cNode);
91 }
92
93 root.addChild(cmNode);
94 }
95
96 cacheTree.setRootElement(root);
97 ((CacheAdminForm) form).setCacheTree(cacheTree);
98
99 return super.start(form, result, request, response);
100 }
101
102 @RequestMapping(params = "methodToCall=flush", method = RequestMethod.POST)
103 public ModelAndView flush(@ModelAttribute("KualiForm") UifFormBase form, BindingResult result,
104 HttpServletRequest request, HttpServletResponse response) {
105 Person user = GlobalVariables.getUserSession().getPerson();
106 boolean isAuthorized = KimApiServiceLocator.getPermissionService().isAuthorized(
107 user.getPrincipalId(),
108 KRADConstants.KUALI_RICE_SYSTEM_NAMESPACE,
109 KRADConstants.USE_CACHE_ADMINISTRATION_SCREEN,
110 Collections.singletonMap(KimConstants.AttributeConstants.PRINCIPAL_ID, user.getPrincipalId()));
111 if(isAuthorized){
112
113
114
115 for (String name : ((CacheAdminForm) form).getFlush()) {
116
117 final List<Integer> path = path(removePrefix(name));
118 final Tree<String, String> tree = ((CacheAdminForm) form).getCacheTree();
119 final Integer cmIdx = path.get(0);
120 final Node<String, String> cmNode = tree.getRootElement().getChildren().get(cmIdx);
121 final String cmName = cmNode.getData();
122 final CacheManager cm = getRegistry().getCacheManager(cmName);
123
124 if (path.size() == 1) {
125 flushAllCaches(cm);
126 GlobalVariables.getMessageMap().putInfoForSectionId("mainGroup_div","flush.all.cachemanager", cmName);
127 } else {
128 final Integer cIdx = path.get(1);
129 final Node<String, String> cNode = cmNode.getChildren().get(cIdx);
130 final String cName = cNode.getData();
131 flushSpecificCache(cm, cName);
132 GlobalVariables.getMessageMap().putInfoForSectionId("mainGroup_div",
133 "flush.single.cachemanager", cName, cmName);
134 }
135 }
136 }else{
137 GlobalVariables.getMessageMap().putError("flush","error.authorization.general",user.getPrincipalName(),"flush","cachemanager");
138 }
139 return super.start(form, result, request, response);
140 }
141
142 private static void flushSpecificCache(CacheManager cm, String cache) {
143 for (String s : cm.getCacheNames()) {
144 if (cache.equals(s)) {
145 cm.getCache(s).clear();
146 return;
147 }
148 }
149 }
150
151 private static void flushAllCaches(CacheManager cm) {
152 for (String s : cm.getCacheNames()) {
153 cm.getCache(s).clear();
154 }
155 }
156
157
158 private static String removePrefix(String s) {
159 final StringBuilder sbn = new StringBuilder(s);
160 sbn.delete(0, sbn.indexOf("_") + 1);
161 return sbn.toString();
162 }
163
164
165 private static List<Integer> path(String s) {
166 final String[] path = s.split("_parent_");
167 final List<Integer> pathIdx = new ArrayList<Integer>();
168
169 for (int i = path.length - 2; i >= 0; i--) {
170 pathIdx.add(Integer.valueOf(path[i].substring(5)));
171 }
172 return Collections.unmodifiableList(pathIdx);
173 }
174
175 private final class ByName implements Comparator<CacheManager> {
176
177 @Override
178 public int compare(CacheManager o1, CacheManager o2) {
179 return String.CASE_INSENSITIVE_ORDER.compare(getRegistry().getCacheManagerName(o1),
180 getRegistry().getCacheManagerName(o2));
181 }
182 }
183
184 }