Sun, 01 Apr 2018 18:16:47 +0200
adds first part of a module manager UI
1.1 --- a/src/java/de/uapcore/lightpit/AbstractLightPITServlet.java Sat Mar 31 19:35:04 2018 +0200 1.2 +++ b/src/java/de/uapcore/lightpit/AbstractLightPITServlet.java Sun Apr 01 18:16:47 2018 +0200 1.3 @@ -266,10 +266,13 @@ 1.4 LOG.trace("Continuing session {} with language {}", session.getId(), sessionLocale); 1.5 } 1.6 1.7 + // set some internal request attributes 1.8 req.setAttribute(Constants.REQ_ATTR_PATH, Functions.fullPath(req)); 1.9 req.setAttribute(Constants.REQ_ATTR_MODULE_CLASSNAME, this.getClass().getName()); 1.10 moduleInfoELProxy.ifPresent((proxy) -> req.setAttribute(Constants.REQ_ATTR_MODULE_INFO, proxy)); 1.11 1.12 + 1.13 + // call the handler, if available, or send an HTTP 404 error 1.14 Optional<HandlerMethod> mapping = findMapping(method, req); 1.15 if (mapping.isPresent()) { 1.16 forwardAsSepcified(mapping.get().apply(req, resp), req, resp);
2.1 --- a/src/java/de/uapcore/lightpit/LightPITModule.java Sat Mar 31 19:35:04 2018 +0200 2.2 +++ b/src/java/de/uapcore/lightpit/LightPITModule.java Sun Apr 01 18:16:47 2018 +0200 2.3 @@ -60,7 +60,7 @@ 2.4 String[] requires() default {}; 2.5 2.6 /** 2.7 - * The path for this module, which will be used for the menu entry. 2.8 + * The path for this module, which will also be used for the menu entry. 2.9 * 2.10 * This path must adhere to the URL pattern of the Servlet but must not 2.11 * contain any starting or trailing slashes. 2.12 @@ -70,6 +70,21 @@ 2.13 String modulePath(); 2.14 2.15 /** 2.16 + * Returns the properties key for the module name. 2.17 + * 2.18 + * @return the properties key 2.19 + */ 2.20 + String nameKey() default "name"; 2.21 + 2.22 + /** 2.23 + * Returns the properties key for the module description. 2.24 + * 2.25 + * @return the properties key 2.26 + */ 2.27 + String descKey() default "description"; 2.28 + 2.29 + 2.30 + /** 2.31 * Returns the properties key for the menu label. 2.32 * 2.33 * Set this string to empty string, if the module should be hidden from 2.34 @@ -105,22 +120,26 @@ 2.35 * are proxied by this object. 2.36 */ 2.37 public static class ELProxy { 2.38 - private final String bundleBaseName, modulePath, menuKey, titleKey; 2.39 + private final String bundleBaseName, modulePath, menuKey, titleKey, nameKey, descKey; 2.40 2.41 public static ELProxy convert(LightPITModule annotation) { 2.42 return new ELProxy( 2.43 annotation.bundleBaseName(), 2.44 annotation.modulePath(), 2.45 annotation.menuKey(), 2.46 - annotation.titleKey() 2.47 + annotation.titleKey(), 2.48 + annotation.nameKey(), 2.49 + annotation.descKey() 2.50 ); 2.51 } 2.52 2.53 - private ELProxy(String bundleBaseName, String modulePath, String menuKey, String titleKey) { 2.54 + private ELProxy(String bundleBaseName, String modulePath, String menuKey, String titleKey, String nameKey, String descKey) { 2.55 this.bundleBaseName = bundleBaseName; 2.56 this.modulePath = modulePath; 2.57 this.menuKey = menuKey; 2.58 this.titleKey = titleKey; 2.59 + this.nameKey = nameKey; 2.60 + this.descKey = descKey; 2.61 } 2.62 2.63 public String getBundleBaseName() { 2.64 @@ -138,5 +157,14 @@ 2.65 public String getTitleKey() { 2.66 return titleKey; 2.67 } 2.68 + 2.69 + public String getNameKey() { 2.70 + return nameKey; 2.71 + } 2.72 + 2.73 + public String getDescKey() { 2.74 + return descKey; 2.75 + } 2.76 + 2.77 } 2.78 }
3.1 --- a/src/java/de/uapcore/lightpit/ModuleManager.java Sat Mar 31 19:35:04 2018 +0200 3.2 +++ b/src/java/de/uapcore/lightpit/ModuleManager.java Sun Apr 01 18:16:47 2018 +0200 3.3 @@ -28,11 +28,11 @@ 3.4 */ 3.5 package de.uapcore.lightpit; 3.6 3.7 +import de.uapcore.lightpit.entities.CoreDAOFactory; 3.8 +import de.uapcore.lightpit.entities.ModuleDao; 3.9 import java.sql.Connection; 3.10 -import java.sql.PreparedStatement; 3.11 -import java.sql.ResultSet; 3.12 import java.sql.SQLException; 3.13 -import java.util.ArrayList; 3.14 +import java.util.Collection; 3.15 import java.util.Collections; 3.16 import java.util.HashMap; 3.17 import java.util.List; 3.18 @@ -41,6 +41,7 @@ 3.19 import java.util.Optional; 3.20 import java.util.concurrent.CopyOnWriteArrayList; 3.21 import java.util.concurrent.atomic.AtomicBoolean; 3.22 +import java.util.stream.Collectors; 3.23 import javax.servlet.Registration; 3.24 import javax.servlet.ServletContext; 3.25 import javax.servlet.ServletContextEvent; 3.26 @@ -66,7 +67,7 @@ 3.27 /** 3.28 * This flag is true, when synchronization is needed. 3.29 */ 3.30 - private AtomicBoolean dirty = new AtomicBoolean(true); 3.31 + private final AtomicBoolean dirty = new AtomicBoolean(true); 3.32 3.33 private final CopyOnWriteArrayList<Menu> mainMenu = new CopyOnWriteArrayList<>(); 3.34 private final List<Menu> immutableMainMenu = Collections.unmodifiableList(mainMenu); 3.35 @@ -140,10 +141,12 @@ 3.36 * Scans for modules and reloads them all. 3.37 */ 3.38 public void reloadAll() { 3.39 + registeredModules.clear(); 3.40 sc.getServletRegistrations().forEach(this::handleServletRegistration); 3.41 3.42 // TODO: implement dependency resolver 3.43 3.44 + dirty.set(true); 3.45 LOG.info("Modules loaded."); 3.46 } 3.47 3.48 @@ -156,36 +159,20 @@ 3.49 if (dirty.compareAndSet(true, false)) { 3.50 if (db.getDataSource().isPresent()) { 3.51 try (Connection conn = db.getDataSource().get().getConnection()) { 3.52 - PreparedStatement 3.53 - check = conn.prepareStatement("SELECT visible FROM lpitcore_module WHERE classname = ?"), 3.54 - insert = conn.prepareStatement("INSERT INTO lpitcore_module (classname, visible) VALUES (?, ?)"); 3.55 - insert.setBoolean(2, true); 3.56 - // update/delete not required, we do this in the module management UI 3.57 + final ModuleDao moduleDao = CoreDAOFactory.getModuleDao(db.getSQLDialect()); 3.58 3.59 - final List<Menu> updatedMenu = new ArrayList<>(); 3.60 + final List<Entry<String, LightPITModule>> visibleModules = 3.61 + moduleDao.syncRegisteredModuleClasses(conn, registeredModules.entrySet()); 3.62 3.63 - for (Entry<String, LightPITModule> mod : registeredModules.entrySet()) { 3.64 - if (mod.getValue().systemModule()) continue; 3.65 - 3.66 - check.setString(1, mod.getKey()); 3.67 - try (ResultSet r = check.executeQuery()) { 3.68 - final boolean addToMenu; 3.69 - if (r.next()) { 3.70 - addToMenu = r.getBoolean(1); 3.71 - } else { 3.72 - insert.setString(1, mod.getKey()); 3.73 - insert.executeUpdate(); 3.74 - addToMenu = !mod.getValue().menuKey().isEmpty(); 3.75 - } 3.76 - if (addToMenu) { 3.77 - updatedMenu.add(new Menu( 3.78 - mod.getKey(), 3.79 - new ResourceKey(mod.getValue().bundleBaseName(), mod.getValue().menuKey()), 3.80 - mod.getValue().modulePath() 3.81 - )); 3.82 - } 3.83 - } 3.84 - } 3.85 + final List<Menu> updatedMenu = visibleModules 3.86 + .stream() 3.87 + .collect(Collectors.mapping( 3.88 + (mod) -> new Menu( 3.89 + mod.getKey(), 3.90 + new ResourceKey(mod.getValue().bundleBaseName(), mod.getValue().menuKey()), 3.91 + mod.getValue().modulePath()), 3.92 + Collectors.toList()) 3.93 + ); 3.94 3.95 mainMenu.removeIf((e) -> !updatedMenu.contains(e)); 3.96 mainMenu.addAllAbsent(updatedMenu); 3.97 @@ -205,6 +192,7 @@ 3.98 */ 3.99 public void unloadAll() { 3.100 mainMenu.clear(); 3.101 + registeredModules.clear(); 3.102 LOG.info("All modules unloaded."); 3.103 } 3.104 3.105 @@ -215,4 +203,15 @@ 3.106 public List<Menu> getMainMenu() { 3.107 return immutableMainMenu; 3.108 } 3.109 + 3.110 + /** 3.111 + * Returns an unmodifiable map of all registered modules. 3.112 + * 3.113 + * The key is the classname of the module. 3.114 + * 3.115 + * @return the map of registered modules 3.116 + */ 3.117 + public Map<String, LightPITModule> getRegisteredModules() { 3.118 + return Collections.unmodifiableMap(registeredModules); 3.119 + } 3.120 }
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 4.2 +++ b/src/java/de/uapcore/lightpit/entities/CoreDAOFactory.java Sun Apr 01 18:16:47 2018 +0200 4.3 @@ -0,0 +1,47 @@ 4.4 +/* 4.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 4.6 + * 4.7 + * Copyright 2017 Mike Becker. All rights reserved. 4.8 + * 4.9 + * Redistribution and use in source and binary forms, with or without 4.10 + * modification, are permitted provided that the following conditions are met: 4.11 + * 4.12 + * 1. Redistributions of source code must retain the above copyright 4.13 + * notice, this list of conditions and the following disclaimer. 4.14 + * 4.15 + * 2. Redistributions in binary form must reproduce the above copyright 4.16 + * notice, this list of conditions and the following disclaimer in the 4.17 + * documentation and/or other materials provided with the distribution. 4.18 + * 4.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 4.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 4.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 4.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 4.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 4.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 4.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 4.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 4.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 4.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 4.29 + * POSSIBILITY OF SUCH DAMAGE. 4.30 + * 4.31 + */ 4.32 +package de.uapcore.lightpit.entities; 4.33 + 4.34 +import de.uapcore.lightpit.DatabaseFacade; 4.35 + 4.36 +public final class CoreDAOFactory { 4.37 + 4.38 + private CoreDAOFactory() {} 4.39 + 4.40 + private static class PostgresDaos { 4.41 + static final ModuleDao MODULE_DAO = new PostgresModuleDao(); 4.42 + } 4.43 + 4.44 + public static ModuleDao getModuleDao(DatabaseFacade.Dialect dialect) { 4.45 + switch (dialect) { 4.46 + case Postgres: return PostgresDaos.MODULE_DAO; 4.47 + default: assert(false); return null; 4.48 + } 4.49 + } 4.50 +}
5.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 5.2 +++ b/src/java/de/uapcore/lightpit/entities/Module.java Sun Apr 01 18:16:47 2018 +0200 5.3 @@ -0,0 +1,90 @@ 5.4 +/* 5.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 5.6 + * 5.7 + * Copyright 2017 Mike Becker. All rights reserved. 5.8 + * 5.9 + * Redistribution and use in source and binary forms, with or without 5.10 + * modification, are permitted provided that the following conditions are met: 5.11 + * 5.12 + * 1. Redistributions of source code must retain the above copyright 5.13 + * notice, this list of conditions and the following disclaimer. 5.14 + * 5.15 + * 2. Redistributions in binary form must reproduce the above copyright 5.16 + * notice, this list of conditions and the following disclaimer in the 5.17 + * documentation and/or other materials provided with the distribution. 5.18 + * 5.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 5.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 5.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 5.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 5.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 5.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 5.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 5.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 5.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 5.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 5.29 + * POSSIBILITY OF SUCH DAMAGE. 5.30 + * 5.31 + */ 5.32 +package de.uapcore.lightpit.entities; 5.33 + 5.34 +import de.uapcore.lightpit.LightPITModule; 5.35 + 5.36 +public class Module { 5.37 + private int modID; 5.38 + private String classname; 5.39 + private boolean visible; 5.40 + 5.41 + private LightPITModule.ELProxy annotatedInfos; 5.42 + 5.43 + public int getModID() { 5.44 + return modID; 5.45 + } 5.46 + 5.47 + public void setModID(int modID) { 5.48 + this.modID = modID; 5.49 + } 5.50 + 5.51 + public String getClassname() { 5.52 + return classname; 5.53 + } 5.54 + 5.55 + public void setClassname(String classname) { 5.56 + this.classname = classname; 5.57 + } 5.58 + 5.59 + public boolean isVisible() { 5.60 + return visible; 5.61 + } 5.62 + 5.63 + public void setVisible(boolean visible) { 5.64 + this.visible = visible; 5.65 + } 5.66 + 5.67 + public LightPITModule.ELProxy getAnnotatedInfos() { 5.68 + return annotatedInfos; 5.69 + } 5.70 + 5.71 + public void setAnnotatedInfos(LightPITModule.ELProxy annotatedInfos) { 5.72 + this.annotatedInfos = annotatedInfos; 5.73 + } 5.74 + 5.75 + @Override 5.76 + public int hashCode() { 5.77 + int hash = 3; 5.78 + hash = 41 * hash + this.modID; 5.79 + return hash; 5.80 + } 5.81 + 5.82 + @Override 5.83 + public boolean equals(Object obj) { 5.84 + if (this == obj) { 5.85 + return true; 5.86 + } 5.87 + if (obj == null || getClass() != obj.getClass()) { 5.88 + return false; 5.89 + } else { 5.90 + return this.modID == ((Module) obj).modID; 5.91 + } 5.92 + } 5.93 +}
6.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 6.2 +++ b/src/java/de/uapcore/lightpit/entities/ModuleDao.java Sun Apr 01 18:16:47 2018 +0200 6.3 @@ -0,0 +1,147 @@ 6.4 +/* 6.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 6.6 + * 6.7 + * Copyright 2017 Mike Becker. All rights reserved. 6.8 + * 6.9 + * Redistribution and use in source and binary forms, with or without 6.10 + * modification, are permitted provided that the following conditions are met: 6.11 + * 6.12 + * 1. Redistributions of source code must retain the above copyright 6.13 + * notice, this list of conditions and the following disclaimer. 6.14 + * 6.15 + * 2. Redistributions in binary form must reproduce the above copyright 6.16 + * notice, this list of conditions and the following disclaimer in the 6.17 + * documentation and/or other materials provided with the distribution. 6.18 + * 6.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 6.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 6.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 6.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 6.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 6.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 6.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 6.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 6.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 6.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 6.29 + * POSSIBILITY OF SUCH DAMAGE. 6.30 + * 6.31 + */ 6.32 +package de.uapcore.lightpit.entities; 6.33 + 6.34 +import de.uapcore.lightpit.LightPITModule; 6.35 +import java.sql.Connection; 6.36 +import java.sql.PreparedStatement; 6.37 +import java.sql.ResultSet; 6.38 +import java.sql.SQLException; 6.39 +import java.sql.Statement; 6.40 +import java.util.AbstractMap; 6.41 +import java.util.ArrayList; 6.42 +import java.util.List; 6.43 +import java.util.Map; 6.44 +import java.util.Set; 6.45 + 6.46 +public abstract class ModuleDao { 6.47 + 6.48 + /** 6.49 + * Must return a prepared statement for a single object query with the specified properties. 6.50 + * 6.51 + * <ul> 6.52 + * <li>Parameter 1: classname</li> 6.53 + * <li>Result field 1: visible</li> 6.54 + * </ul> 6.55 + * 6.56 + * @param conn the connection to use 6.57 + * @return the prepared statement 6.58 + * @throws SQLException 6.59 + */ 6.60 + protected PreparedStatement moduleCheckStatement(Connection conn) throws SQLException { 6.61 + return conn.prepareStatement("SELECT visible FROM lpitcore_module WHERE classname = ?"); 6.62 + } 6.63 + 6.64 + /** 6.65 + * Must return a prepared statement for insertion with the specified properties. 6.66 + * 6.67 + * <ul> 6.68 + * <li>Parameter 1: classname</li> 6.69 + * <li>Parameter 2: visible</li> 6.70 + * </ul> 6.71 + * 6.72 + * @param conn the connection to use 6.73 + * @return the prepared statement 6.74 + * @throws SQLException 6.75 + */ 6.76 + protected PreparedStatement moduleInsertStatement(Connection conn) throws SQLException { 6.77 + return conn.prepareStatement("INSERT INTO lpitcore_module (classname, visible) VALUES (?, ?)"); 6.78 + } 6.79 + 6.80 + /** 6.81 + * Synchronizes a set of registered module classes with the database and gives a list of visible modules in return. 6.82 + * 6.83 + * Inserts module classes which are not known to the database and sets them to be visible by default. 6.84 + * Module classes known to the database, which are not in the given set, are ignored. 6.85 + * 6.86 + * @param conn the connection to use 6.87 + * @param moduleSet the module set to synchronize 6.88 + * @return a list of elements from the given set, which should be visible in the menu 6.89 + * @throws SQLException 6.90 + */ 6.91 + public final List<Map.Entry<String, LightPITModule>> 6.92 + syncRegisteredModuleClasses(Connection conn, Set<Map.Entry<String, LightPITModule>> moduleSet) throws SQLException { 6.93 + 6.94 + PreparedStatement 6.95 + check = moduleCheckStatement(conn), 6.96 + insert = moduleInsertStatement(conn); 6.97 + insert.setBoolean(2, true); 6.98 + // update/delete not required, we do this in the module management UI 6.99 + 6.100 + final List<Map.Entry<String, LightPITModule>> visibleModules = new ArrayList<>(); 6.101 + 6.102 + for (Map.Entry<String, LightPITModule> mod : moduleSet) { 6.103 + if (mod.getValue().systemModule()) continue; 6.104 + 6.105 + check.setString(1, mod.getKey()); 6.106 + try (ResultSet r = check.executeQuery()) { 6.107 + final boolean visible; 6.108 + if (r.next()) { 6.109 + visible = r.getBoolean(1); 6.110 + } else { 6.111 + insert.setString(1, mod.getKey()); 6.112 + insert.executeUpdate(); 6.113 + visible = !mod.getValue().menuKey().isEmpty(); 6.114 + } 6.115 + if (visible) { 6.116 + visibleModules.add(new AbstractMap.SimpleEntry<>( 6.117 + mod.getKey(), 6.118 + mod.getValue() 6.119 + )); 6.120 + } 6.121 + } 6.122 + } 6.123 + return visibleModules; 6.124 + } 6.125 + 6.126 + /** 6.127 + * Returns a list of all modules known by the database. 6.128 + * 6.129 + * Keep in mind, that system modules are never known to the database. 6.130 + * 6.131 + * @param conn the connection to use 6.132 + * @return a list of all modules known by the database 6.133 + * @throws SQLException 6.134 + */ 6.135 + public List<Module> listAll(Connection conn) throws SQLException { 6.136 + List<Module> list = new ArrayList<>(); 6.137 + try ( 6.138 + Statement stmt = conn.createStatement(); 6.139 + ResultSet result = stmt.executeQuery("SELECT * FROM lpitcore_module")) { 6.140 + while (result.next()) { 6.141 + final Module mod = new Module(); 6.142 + mod.setModID(result.getInt("modid")); 6.143 + mod.setClassname(result.getString("classname")); 6.144 + mod.setVisible(result.getBoolean("visible")); 6.145 + list.add(mod); 6.146 + } 6.147 + } 6.148 + return list; 6.149 + } 6.150 +}
7.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 7.2 +++ b/src/java/de/uapcore/lightpit/entities/PostgresModuleDao.java Sun Apr 01 18:16:47 2018 +0200 7.3 @@ -0,0 +1,33 @@ 7.4 +/* 7.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 7.6 + * 7.7 + * Copyright 2017 Mike Becker. All rights reserved. 7.8 + * 7.9 + * Redistribution and use in source and binary forms, with or without 7.10 + * modification, are permitted provided that the following conditions are met: 7.11 + * 7.12 + * 1. Redistributions of source code must retain the above copyright 7.13 + * notice, this list of conditions and the following disclaimer. 7.14 + * 7.15 + * 2. Redistributions in binary form must reproduce the above copyright 7.16 + * notice, this list of conditions and the following disclaimer in the 7.17 + * documentation and/or other materials provided with the distribution. 7.18 + * 7.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 7.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 7.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 7.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 7.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 7.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 7.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 7.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 7.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 7.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 7.29 + * POSSIBILITY OF SUCH DAMAGE. 7.30 + * 7.31 + */ 7.32 +package de.uapcore.lightpit.entities; 7.33 + 7.34 +public class PostgresModuleDao extends ModuleDao { 7.35 + // No overrides needed. 7.36 +}
8.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 8.2 +++ b/src/java/de/uapcore/lightpit/modules/ModuleManagerModule.java Sun Apr 01 18:16:47 2018 +0200 8.3 @@ -0,0 +1,94 @@ 8.4 +/* 8.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 8.6 + * 8.7 + * Copyright 2017 Mike Becker. All rights reserved. 8.8 + * 8.9 + * Redistribution and use in source and binary forms, with or without 8.10 + * modification, are permitted provided that the following conditions are met: 8.11 + * 8.12 + * 1. Redistributions of source code must retain the above copyright 8.13 + * notice, this list of conditions and the following disclaimer. 8.14 + * 8.15 + * 2. Redistributions in binary form must reproduce the above copyright 8.16 + * notice, this list of conditions and the following disclaimer in the 8.17 + * documentation and/or other materials provided with the distribution. 8.18 + * 8.19 + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 8.20 + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 8.21 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 8.22 + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 8.23 + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 8.24 + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 8.25 + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 8.26 + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 8.27 + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 8.28 + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 8.29 + * POSSIBILITY OF SUCH DAMAGE. 8.30 + * 8.31 + */ 8.32 +package de.uapcore.lightpit.modules; 8.33 + 8.34 +import de.uapcore.lightpit.LightPITModule; 8.35 +import de.uapcore.lightpit.AbstractLightPITServlet; 8.36 +import de.uapcore.lightpit.HttpMethod; 8.37 +import de.uapcore.lightpit.LightPITModule.ELProxy; 8.38 +import de.uapcore.lightpit.RequestMapping; 8.39 +import de.uapcore.lightpit.ResponseType; 8.40 +import de.uapcore.lightpit.entities.CoreDAOFactory; 8.41 +import de.uapcore.lightpit.entities.Module; 8.42 +import java.io.IOException; 8.43 +import java.sql.Connection; 8.44 +import java.sql.SQLException; 8.45 +import java.util.List; 8.46 +import java.util.Map; 8.47 +import java.util.Optional; 8.48 +import javax.servlet.annotation.WebServlet; 8.49 +import javax.servlet.http.HttpServletRequest; 8.50 +import javax.servlet.http.HttpServletResponse; 8.51 +import javax.sql.DataSource; 8.52 +import org.slf4j.Logger; 8.53 +import org.slf4j.LoggerFactory; 8.54 + 8.55 +/** 8.56 + * Entry point for the application. 8.57 + */ 8.58 +@LightPITModule( 8.59 + bundleBaseName = "de.uapcore.lightpit.resources.localization.modmgmt", 8.60 + modulePath = "modmgmt" 8.61 +) 8.62 +@WebServlet( 8.63 + name = "ModuleManagerModule", 8.64 + urlPatterns = "/modmgmt/*" 8.65 +) 8.66 +public final class ModuleManagerModule extends AbstractLightPITServlet { 8.67 + 8.68 + private static final Logger LOG = LoggerFactory.getLogger(ModuleManagerModule.class); 8.69 + 8.70 + private static final String REQ_ATTR_MODULES = "modules"; 8.71 + 8.72 + 8.73 + @RequestMapping(method = HttpMethod.GET) 8.74 + public ResponseType handle(HttpServletRequest req, HttpServletResponse resp) throws IOException { 8.75 + 8.76 + Optional<DataSource> ds = getDatabaseFacade().getDataSource(); 8.77 + if (ds.isPresent()) { 8.78 + try (Connection conn = ds.get().getConnection()) { 8.79 + final List<Module> modules = CoreDAOFactory.getModuleDao(getDatabaseFacade().getSQLDialect()).listAll(conn); 8.80 + 8.81 + final Map<String, LightPITModule> registeredModules = getModuleManager().getRegisteredModules(); 8.82 + modules.forEach((mod) -> mod.setAnnotatedInfos(ELProxy.convert(registeredModules.get(mod.getClassname())))); 8.83 + 8.84 + req.setAttribute(REQ_ATTR_MODULES, modules); 8.85 + setDynamicFragment(req, "modules"); 8.86 + return ResponseType.HTML_FULL; 8.87 + } catch (SQLException ex) { 8.88 + LOG.error("Unexpected SQL Exception", ex); 8.89 + resp.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR); 8.90 + return ResponseType.NONE; 8.91 + } 8.92 + } else { 8.93 + resp.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR); 8.94 + return ResponseType.NONE; 8.95 + } 8.96 + } 8.97 +}
9.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 9.2 +++ b/src/java/de/uapcore/lightpit/resources/localization/modmgmt.properties Sun Apr 01 18:16:47 2018 +0200 9.3 @@ -0,0 +1,24 @@ 9.4 +# Copyright 2017 Mike Becker. All rights reserved. 9.5 +# 9.6 +# Redistribution and use in source and binary forms, with or without 9.7 +# modification, are permitted provided that the following conditions are met: 9.8 +# 9.9 +# 1. Redistributions of source code must retain the above copyright 9.10 +# notice, this list of conditions and the following disclaimer. 9.11 +# 9.12 +# 2. Redistributions in binary form must reproduce the above copyright 9.13 +# notice, this list of conditions and the following disclaimer in the 9.14 +# documentation and/or other materials provided with the distribution. 9.15 +# 9.16 +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 9.17 +# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 9.18 +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 9.19 +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 9.20 +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 9.21 +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 9.22 +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 9.23 +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 9.24 +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 9.25 +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 9.26 + 9.27 +menuLabel = Modules
10.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 10.2 +++ b/src/java/de/uapcore/lightpit/resources/localization/modmgmt_de.properties Sun Apr 01 18:16:47 2018 +0200 10.3 @@ -0,0 +1,24 @@ 10.4 +# Copyright 2017 Mike Becker. All rights reserved. 10.5 +# 10.6 +# Redistribution and use in source and binary forms, with or without 10.7 +# modification, are permitted provided that the following conditions are met: 10.8 +# 10.9 +# 1. Redistributions of source code must retain the above copyright 10.10 +# notice, this list of conditions and the following disclaimer. 10.11 +# 10.12 +# 2. Redistributions in binary form must reproduce the above copyright 10.13 +# notice, this list of conditions and the following disclaimer in the 10.14 +# documentation and/or other materials provided with the distribution. 10.15 +# 10.16 +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 10.17 +# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 10.18 +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 10.19 +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 10.20 +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 10.21 +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 10.22 +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 10.23 +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 10.24 +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 10.25 +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 10.26 + 10.27 +menuLabel = Module
11.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 11.2 +++ b/web/WEB-INF/dynamic_fragments/modules.jsp Sun Apr 01 18:16:47 2018 +0200 11.3 @@ -0,0 +1,52 @@ 11.4 +<%-- 11.5 +DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. 11.6 + 11.7 +Copyright 2017 Mike Becker. All rights reserved. 11.8 + 11.9 +Redistribution and use in source and binary forms, with or without 11.10 +modification, are permitted provided that the following conditions are met: 11.11 + 11.12 +1. Redistributions of source code must retain the above copyright 11.13 +notice, this list of conditions and the following disclaimer. 11.14 + 11.15 +2. Redistributions in binary form must reproduce the above copyright 11.16 +notice, this list of conditions and the following disclaimer in the 11.17 +documentation and/or other materials provided with the distribution. 11.18 + 11.19 +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 11.20 +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 11.21 +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 11.22 +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 11.23 +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 11.24 +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 11.25 +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 11.26 +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 11.27 +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 11.28 +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 11.29 +--%> 11.30 +<%@page pageEncoding="UTF-8" session="true" %> 11.31 +<%@page import="de.uapcore.lightpit.Constants" %> 11.32 +<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> 11.33 +<%@taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %> 11.34 + 11.35 +<%-- TODO: a lot of work --%> 11.36 +<table> 11.37 + <tr> 11.38 + <th>Module</th> 11.39 + <th>Path</th> 11.40 + <th>Description</th> 11.41 + <th>Active</th> 11.42 + <th>Class</th> 11.43 + <th>Resource Bundle</th> 11.44 + </tr> 11.45 + <c:forEach items="${modules}" var="module"> 11.46 + <tr> 11.47 + <td>${module.annotatedInfos.nameKey}</td> 11.48 + <td>${module.annotatedInfos.modulePath}</td> 11.49 + <td>${module.annotatedInfos.descKey}</td> 11.50 + <td align="center">${module.visible}</td> 11.51 + <td>${module.classname}</td> 11.52 + <td>${module.annotatedInfos.bundleBaseName}</td> 11.53 + </tr> 11.54 + </c:forEach> 11.55 +</table> 11.56 \ No newline at end of file