View Javadoc
1   /*
2    * Copyright 2012-2017 CodeLibs Project and the Others.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    *     http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
13   * either express or implied. See the License for the specific language
14   * governing permissions and limitations under the License.
15   */
16  package org.codelibs.fess.app.web.admin.dataconfig;
17  
18  import static org.codelibs.core.stream.StreamUtil.split;
19  import static org.codelibs.core.stream.StreamUtil.stream;
20  
21  import java.util.ArrayList;
22  import java.util.HashMap;
23  import java.util.List;
24  import java.util.Map;
25  import java.util.stream.Collectors;
26  import java.util.stream.Stream;
27  
28  import javax.annotation.Resource;
29  
30  import org.codelibs.core.lang.StringUtil;
31  import org.codelibs.fess.Constants;
32  import org.codelibs.fess.app.pager.DataConfigPager;
33  import org.codelibs.fess.app.service.DataConfigService;
34  import org.codelibs.fess.app.service.LabelTypeService;
35  import org.codelibs.fess.app.service.RoleTypeService;
36  import org.codelibs.fess.app.web.CrudMode;
37  import org.codelibs.fess.app.web.base.FessAdminAction;
38  import org.codelibs.fess.ds.DataStoreFactory;
39  import org.codelibs.fess.es.config.exentity.DataConfig;
40  import org.codelibs.fess.helper.PermissionHelper;
41  import org.codelibs.fess.helper.SystemHelper;
42  import org.codelibs.fess.util.ComponentUtil;
43  import org.codelibs.fess.util.RenderDataUtil;
44  import org.dbflute.optional.OptionalEntity;
45  import org.dbflute.optional.OptionalThing;
46  import org.lastaflute.web.Execute;
47  import org.lastaflute.web.response.HtmlResponse;
48  import org.lastaflute.web.response.render.RenderData;
49  import org.lastaflute.web.ruts.process.ActionRuntime;
50  
51  /**
52   * @author shinsuke
53   * @author Keiichi Watanabe
54   */
55  public class AdminDataconfigAction extends FessAdminAction {
56  
57      // ===================================================================================
58      //                                                                           Attribute
59      //                                                                           =========
60      @Resource
61      private DataConfigService dataConfigService;
62      @Resource
63      private DataConfigPager dataConfigPager;
64      @Resource
65      private RoleTypeService roleTypeService;
66      @Resource
67      private LabelTypeService labelTypeService;
68      @Resource
69      protected DataStoreFactory dataStoreFactory;
70  
71      // ===================================================================================
72      //                                                                               Hook
73      //                                                                              ======
74      @Override
75      protected void setupHtmlData(final ActionRuntime runtime) {
76          super.setupHtmlData(runtime);
77          runtime.registerData("helpLink", systemHelper.getHelpLink(fessConfig.getOnlineHelpNameDataconfig()));
78      }
79  
80      // ===================================================================================
81      //                                                                      Search Execute
82      //                                                                      ==============
83      @Execute
84      public HtmlResponse index() {
85          return asListHtml();
86      }
87  
88      @Execute
89      public HtmlResponse list(final OptionalThing<Integer> pageNumber, final SearchForm form) {
90          pageNumber.ifPresent(num -> {
91              dataConfigPager.setCurrentPageNumber(pageNumber.get());
92          }).orElse(() -> {
93              dataConfigPager.setCurrentPageNumber(0);
94          });
95          return asHtml(path_AdminDataconfig_AdminDataconfigJsp).renderWith(data -> {
96              searchPaging(data, form);
97          });
98      }
99  
100     @Execute
101     public HtmlResponse search(final SearchForm form) {
102         copyBeanToBean(form, dataConfigPager, op -> op.exclude(Constants.PAGER_CONVERSION_RULE));
103         return asHtml(path_AdminDataconfig_AdminDataconfigJsp).renderWith(data -> {
104             searchPaging(data, form);
105         });
106     }
107 
108     @Execute
109     public HtmlResponse reset(final SearchForm form) {
110         dataConfigPager.clear();
111         return asHtml(path_AdminDataconfig_AdminDataconfigJsp).renderWith(data -> {
112             searchPaging(data, form);
113         });
114     }
115 
116     protected void searchPaging(final RenderData data, final SearchForm form) {
117         RenderDataUtil.register(data, "dataConfigItems", dataConfigService.getDataConfigList(dataConfigPager)); // page navi
118 
119         // restore from pager
120         copyBeanToBean(dataConfigPager, form, op -> op.include("id"));
121     }
122 
123     // ===================================================================================
124     //                                                                        Edit Execute
125     //                                                                        ============
126     // -----------------------------------------------------
127     //                                            Entry Page
128     //                                            ----------
129     @Execute
130     public HtmlResponse createnew() {
131         saveToken();
132         return asEditHtml().useForm(CreateForm.class, op -> {
133             op.setup(form -> {
134                 form.initialize();
135                 form.crudMode = CrudMode.CREATE;
136             });
137         });
138     }
139 
140     @Execute
141     public HtmlResponse edit(final EditForm form) {
142         validate(form, messages -> {}, () -> asListHtml());
143         final String id = form.id;
144         dataConfigService
145                 .getDataConfig(id)
146                 .ifPresent(
147                         entity -> {
148                             copyBeanToBean(entity, form, copyOp -> {
149                                 copyOp.excludeNull();
150                                 copyOp.exclude(Constants.PERMISSIONS, Constants.VIRTUAL_HOSTS);
151                             });
152                             final PermissionHelper permissionHelper = ComponentUtil.getPermissionHelper();
153                             form.permissions =
154                                     stream(entity.getPermissions()).get(
155                                             stream -> stream.map(permissionHelper::decode).filter(StringUtil::isNotBlank).distinct()
156                                                     .collect(Collectors.joining("\n")));
157                             form.virtualHosts =
158                                     stream(entity.getVirtualHosts()).get(
159                                             stream -> stream.filter(StringUtil::isNotBlank).collect(Collectors.joining("\n")));
160                         }).orElse(() -> {
161                     throwValidationError(messages -> messages.addErrorsCrudCouldNotFindCrudTable(GLOBAL, id), () -> asListHtml());
162                 });
163         saveToken();
164         if (form.crudMode.intValue() == CrudMode.EDIT) {
165             // back
166             form.crudMode = CrudMode.DETAILS;
167             return asDetailsHtml();
168         } else {
169             form.crudMode = CrudMode.EDIT;
170             return asEditHtml();
171         }
172     }
173 
174     // -----------------------------------------------------
175     //                                               Details
176     //                                               -------
177     @Execute
178     public HtmlResponse details(final int crudMode, final String id) {
179         verifyCrudMode(crudMode, CrudMode.DETAILS);
180         saveToken();
181         return asDetailsHtml().useForm(
182                 EditForm.class,
183                 op -> {
184                     op.setup(form -> {
185                         dataConfigService
186                                 .getDataConfig(id)
187                                 .ifPresent(
188                                         entity -> {
189                                             copyBeanToBean(entity, form, copyOp -> {
190                                                 copyOp.excludeNull();
191                                                 copyOp.exclude(Constants.PERMISSIONS, Constants.VIRTUAL_HOSTS);
192                                             });
193                                             final PermissionHelper permissionHelper = ComponentUtil.getPermissionHelper();
194                                             form.permissions =
195                                                     stream(entity.getPermissions()).get(
196                                                             stream -> stream.map(s -> permissionHelper.decode(s))
197                                                                     .filter(StringUtil::isNotBlank).distinct()
198                                                                     .collect(Collectors.joining("\n")));
199                                             form.virtualHosts =
200                                                     stream(entity.getVirtualHosts()).get(
201                                                             stream -> stream.filter(StringUtil::isNotBlank).collect(
202                                                                     Collectors.joining("\n")));
203                                             form.crudMode = crudMode;
204                                         })
205                                 .orElse(() -> throwValidationError(messages -> messages.addErrorsCrudCouldNotFindCrudTable(GLOBAL, id),
206                                         () -> asListHtml()));
207                     });
208                 });
209     }
210 
211     // -----------------------------------------------------
212     //                                         Actually Crud
213     //                                         -------------
214     @Execute
215     public HtmlResponse create(final CreateForm form) {
216         verifyCrudMode(form.crudMode, CrudMode.CREATE);
217         validate(form, messages -> {}, () -> asEditHtml());
218         verifyToken(() -> asEditHtml());
219         getDataConfig(form).ifPresent(
220                 entity -> {
221                     try {
222                         dataConfigService.store(entity);
223                         saveInfo(messages -> messages.addSuccessCrudCreateCrudTable(GLOBAL));
224                     } catch (final Exception e) {
225                         throwValidationError(messages -> messages.addErrorsCrudFailedToCreateCrudTable(GLOBAL, buildThrowableMessage(e)),
226                                 () -> asEditHtml());
227                     }
228                 }).orElse(() -> {
229             throwValidationError(messages -> messages.addErrorsCrudFailedToCreateInstance(GLOBAL), () -> asEditHtml());
230         });
231         return redirect(getClass());
232     }
233 
234     @Execute
235     public HtmlResponse update(final EditForm form) {
236         verifyCrudMode(form.crudMode, CrudMode.EDIT);
237         validate(form, messages -> {}, () -> asEditHtml());
238         verifyToken(() -> asEditHtml());
239         getDataConfig(form).ifPresent(
240                 entity -> {
241                     try {
242                         dataConfigService.store(entity);
243                         saveInfo(messages -> messages.addSuccessCrudUpdateCrudTable(GLOBAL));
244                     } catch (final Exception e) {
245                         throwValidationError(messages -> messages.addErrorsCrudFailedToUpdateCrudTable(GLOBAL, buildThrowableMessage(e)),
246                                 () -> asEditHtml());
247                     }
248                 }).orElse(() -> {
249             throwValidationError(messages -> messages.addErrorsCrudCouldNotFindCrudTable(GLOBAL, form.id), () -> asEditHtml());
250         });
251         return redirect(getClass());
252     }
253 
254     @Execute
255     public HtmlResponse delete(final EditForm form) {
256         verifyCrudMode(form.crudMode, CrudMode.DETAILS);
257         validate(form, messages -> {}, () -> asDetailsHtml());
258         verifyToken(() -> asDetailsHtml());
259         final String id = form.id;
260         dataConfigService
261                 .getDataConfig(id)
262                 .ifPresent(
263                         entity -> {
264                             try {
265                                 dataConfigService.delete(entity);
266                                 saveInfo(messages -> messages.addSuccessCrudDeleteCrudTable(GLOBAL));
267                             } catch (final Exception e) {
268                                 throwValidationError(
269                                         messages -> messages.addErrorsCrudFailedToDeleteCrudTable(GLOBAL, buildThrowableMessage(e)),
270                                         () -> asEditHtml());
271                             }
272                         })
273                 .orElse(() -> throwValidationError(messages -> messages.addErrorsCrudCouldNotFindCrudTable(GLOBAL, id),
274                         () -> asDetailsHtml()));
275         return redirect(getClass());
276     }
277 
278     // ===================================================================================
279     //                                                                        Assist Logic
280     //                                                                        ============
281     public static OptionalEntity<DataConfig> getEntity(final CreateForm form, final String username, final long currentTime) {
282         switch (form.crudMode) {
283         case CrudMode.CREATE:
284             return OptionalEntity.of(new DataConfig()).map(entity -> {
285                 entity.setCreatedBy(username);
286                 entity.setCreatedTime(currentTime);
287                 return entity;
288             });
289         case CrudMode.EDIT:
290             if (form instanceof EditForm) {
291                 return ComponentUtil.getComponent(DataConfigService.class).getDataConfig(((EditForm) form).id);
292             }
293             break;
294         default:
295             break;
296         }
297         return OptionalEntity.empty();
298     }
299 
300     public static OptionalEntity<DataConfig> getDataConfig(final CreateForm form) {
301         final SystemHelper systemHelper = ComponentUtil.getSystemHelper();
302         final String username = systemHelper.getUsername();
303         final long currentTime = systemHelper.getCurrentTimeAsLong();
304         return getEntity(form, username, currentTime).map(
305                 entity -> {
306                     entity.setUpdatedBy(username);
307                     entity.setUpdatedTime(currentTime);
308                     copyBeanToBean(
309                             form,
310                             entity,
311                             op -> op.exclude(Stream.concat(Stream.of(Constants.COMMON_CONVERSION_RULE),
312                                     Stream.of(Constants.PERMISSIONS, Constants.VIRTUAL_HOSTS)).toArray(n -> new String[n])));
313                     final PermissionHelper permissionHelper = ComponentUtil.getPermissionHelper();
314                     entity.setPermissions(split(form.permissions, "\n").get(
315                             stream -> stream.map(s -> permissionHelper.encode(s)).filter(StringUtil::isNotBlank).distinct()
316                                     .toArray(n -> new String[n])));
317                     entity.setVirtualHosts(split(form.virtualHosts, "\n").get(
318                             stream -> stream.filter(StringUtil::isNotBlank).distinct().toArray(n -> new String[n])));
319                     return entity;
320                 });
321     }
322 
323     protected void registerRolesAndLabels(final RenderData data) {
324         RenderDataUtil.register(data, "roleTypeItems", roleTypeService.getRoleTypeList());
325         RenderDataUtil.register(data, "labelTypeItems", labelTypeService.getLabelTypeList());
326     }
327 
328     protected void registerHandlerNames(final RenderData data) {
329         final List<String> dataStoreNameList = dataStoreFactory.getDataStoreNameList();
330         final List<Map<String, String>> itemList = new ArrayList<>();
331         for (final String name : dataStoreNameList) {
332             final Map<String, String> map = new HashMap<>();
333             map.put(Constants.ITEM_LABEL, name);
334             map.put(Constants.ITEM_VALUE, name);
335             itemList.add(map);
336         }
337         RenderDataUtil.register(data, "handlerNameItems", itemList);
338     }
339 
340     // ===================================================================================
341     //                                                                        Small Helper
342     //                                                                        ============
343     protected void verifyCrudMode(final int crudMode, final int expectedMode) {
344         if (crudMode != expectedMode) {
345             throwValidationError(messages -> {
346                 messages.addErrorsCrudInvalidMode(GLOBAL, String.valueOf(expectedMode), String.valueOf(crudMode));
347             }, () -> asListHtml());
348         }
349     }
350 
351     // ===================================================================================
352     //                                                                              JSP
353     //                                                                           =========
354 
355     private HtmlResponse asListHtml() {
356         return asHtml(path_AdminDataconfig_AdminDataconfigJsp).renderWith(data -> {
357             RenderDataUtil.register(data, "dataConfigItems", dataConfigService.getDataConfigList(dataConfigPager));
358         }).useForm(SearchForm.class, setup -> {
359             setup.setup(form -> {
360                 copyBeanToBean(dataConfigPager, form, op -> op.include("id"));
361             });
362         });
363     }
364 
365     private HtmlResponse asEditHtml() {
366         return asHtml(path_AdminDataconfig_AdminDataconfigEditJsp).renderWith(data -> {
367             registerRolesAndLabels(data);
368             registerHandlerNames(data);
369         });
370     }
371 
372     private HtmlResponse asDetailsHtml() {
373         return asHtml(path_AdminDataconfig_AdminDataconfigDetailsJsp).renderWith(data -> {
374             registerRolesAndLabels(data);
375             registerHandlerNames(data);
376         });
377     }
378 
379 }