src/java/de/uapcore/lightpit/ModuleManager.java

changeset 27
1f2a96efa69f
parent 24
8137ec335416
     1.1 --- a/src/java/de/uapcore/lightpit/ModuleManager.java	Sun Apr 08 15:34:11 2018 +0200
     1.2 +++ b/src/java/de/uapcore/lightpit/ModuleManager.java	Sun Apr 08 16:41:02 2018 +0200
     1.3 @@ -29,6 +29,7 @@
     1.4  package de.uapcore.lightpit;
     1.5  
     1.6  import de.uapcore.lightpit.entities.CoreDAOFactory;
     1.7 +import de.uapcore.lightpit.entities.Module;
     1.8  import de.uapcore.lightpit.entities.ModuleDao;
     1.9  import java.sql.Connection;
    1.10  import java.sql.SQLException;
    1.11 @@ -36,9 +37,7 @@
    1.12  import java.util.HashMap;
    1.13  import java.util.List;
    1.14  import java.util.Map;
    1.15 -import java.util.Map.Entry;
    1.16  import java.util.Optional;
    1.17 -import java.util.concurrent.CopyOnWriteArrayList;
    1.18  import java.util.concurrent.atomic.AtomicBoolean;
    1.19  import java.util.stream.Collectors;
    1.20  import javax.servlet.Registration;
    1.21 @@ -64,18 +63,15 @@
    1.22      private ServletContext sc;
    1.23      
    1.24      /**
    1.25 +     * Maps class names to module information.
    1.26 +     */
    1.27 +    private final Map<String, LightPITModule> registeredModules = new HashMap<>();
    1.28 +    
    1.29 +    /**
    1.30       * This flag is true, when synchronization is needed.
    1.31       */
    1.32      private final AtomicBoolean dirty = new AtomicBoolean(true);
    1.33      
    1.34 -    private final CopyOnWriteArrayList<Menu> mainMenu = new CopyOnWriteArrayList<>();
    1.35 -    private final List<Menu> immutableMainMenu = Collections.unmodifiableList(mainMenu);
    1.36 -    
    1.37 -    /**
    1.38 -     * Maps class names to module information.
    1.39 -     */
    1.40 -    private final Map<String, LightPITModule> registeredModules = new HashMap<>();
    1.41 -    
    1.42      @Override
    1.43      public void contextInitialized(ServletContextEvent sce) {
    1.44          sc = sce.getServletContext();
    1.45 @@ -152,6 +148,13 @@
    1.46      /**
    1.47       * Synchronizes module information with the database.
    1.48       * 
    1.49 +     * This must be called from the {@link AbstractLightPITServlet}.
    1.50 +     * Admittedly the call will perform the synchronization once after reload
    1.51 +     * and be a no-op, afterwards.
    1.52 +     * However, we since the DatabaseFacade might be loaded after the module
    1.53 +     * manager, we must defer the synchronization to the first request
    1.54 +     * handled by the Servlet.
    1.55 +     * 
    1.56       * @param db interface to the database
    1.57       */
    1.58      public void syncWithDatabase(DatabaseFacade db) {
    1.59 @@ -159,27 +162,12 @@
    1.60              if (db.getDataSource().isPresent()) {
    1.61                  try (Connection conn = db.getDataSource().get().getConnection()) {
    1.62                      final ModuleDao moduleDao = CoreDAOFactory.getModuleDao(db.getSQLDialect());
    1.63 -                    
    1.64 -                    final List<Entry<String, LightPITModule>> visibleModules =
    1.65 -                            moduleDao.syncRegisteredModuleClasses(conn, registeredModules.entrySet());
    1.66 -                    
    1.67 -                    final List<Menu> updatedMenu = visibleModules
    1.68 -                            .stream()
    1.69 -                            .collect(Collectors.mapping(
    1.70 -                                    (mod) -> new Menu(
    1.71 -                                            mod.getKey(),
    1.72 -                                            new ResourceKey(mod.getValue().bundleBaseName(), mod.getValue().menuKey()),
    1.73 -                                            mod.getValue().modulePath()),
    1.74 -                                    Collectors.toList())
    1.75 -                            );
    1.76 -                    
    1.77 -                    mainMenu.removeIf((e) -> !updatedMenu.contains(e));
    1.78 -                    mainMenu.addAllAbsent(updatedMenu);
    1.79 +                    moduleDao.syncRegisteredModuleClasses(conn, registeredModules.entrySet());
    1.80                  } catch (SQLException ex) {
    1.81                      LOG.error("Unexpected SQL Exception", ex);
    1.82                  }
    1.83              } else {
    1.84 -                LOG.warn("No datasource present. Cannot sync module information with database.");
    1.85 +                LOG.error("No datasource present. Cannot sync module information with database.");
    1.86              }
    1.87          } else {
    1.88              LOG.trace("Module information clean - no synchronization required.");
    1.89 @@ -190,17 +178,44 @@
    1.90       * Unloads all found modules.
    1.91       */
    1.92      public void unloadAll() {
    1.93 -        mainMenu.clear();
    1.94          registeredModules.clear();
    1.95          LOG.info("All modules unloaded.");
    1.96      }
    1.97  
    1.98      /**
    1.99       * Returns the main menu.
   1.100 +     * 
   1.101 +     * @param db the interface to the database
   1.102       * @return a list of menus belonging to the main menu
   1.103       */
   1.104 -    public List<Menu> getMainMenu() {
   1.105 -        return immutableMainMenu;
   1.106 +    public List<Menu> getMainMenu(DatabaseFacade db) {
   1.107 +        // TODO: user specific menu
   1.108 +        
   1.109 +        if (db.getDataSource().isPresent()) {
   1.110 +            try (Connection conn = db.getDataSource().get().getConnection()) {
   1.111 +                final ModuleDao dao = CoreDAOFactory.getModuleDao(db.getSQLDialect());
   1.112 +                final List<Module> modules = dao.listAll(conn);
   1.113 +                
   1.114 +                final List<Menu> menu = modules
   1.115 +                    .stream()
   1.116 +                    .filter((mod) -> mod.isVisible())
   1.117 +                    .collect(Collectors.mapping(
   1.118 +                            (mod) -> new Menu(
   1.119 +                                    mod.getClassname(),
   1.120 +                                    new ResourceKey(
   1.121 +                                            registeredModules.get(mod.getClassname()).bundleBaseName(),
   1.122 +                                            registeredModules.get(mod.getClassname()).menuKey()),
   1.123 +                                    registeredModules.get(mod.getClassname()).modulePath()),
   1.124 +                            Collectors.toList())
   1.125 +                    );
   1.126 +                return menu;
   1.127 +            } catch (SQLException ex) {
   1.128 +                LOG.error("Unexpected SQLException when loading the main menu", ex);
   1.129 +                return Collections.emptyList();
   1.130 +            }
   1.131 +        } else {
   1.132 +            return Collections.emptyList();
   1.133 +        }
   1.134      }
   1.135      
   1.136      /**

mercurial