Tony CHEMIT pushed to branch develop at ultreiaio / ird-observe Commits: 5c3ce96f by Tony Chemit at 2022-02-19T17:07:17+01:00 Revoir le démarrage du serveur web - Closes #2170 - - - - - 9 changed files: - client/configuration/src/main/java/fr/ird/observe/client/configuration/ClientConfig.java - core/api/dto/pom.xml - + core/api/dto/src/main/java/fr/ird/observe/spi/ConfigHelper.java - server/configuration/src/main/config/Server.ini - server/configuration/src/main/i18n/getters/config.getter - server/configuration/src/main/java/fr/ird/observe/server/configuration/ServerConfig.java - server/runner/src/main/i18n/translations/server-runner_en_GB.properties - server/runner/src/main/i18n/translations/server-runner_es_ES.properties - server/runner/src/main/i18n/translations/server-runner_fr_FR.properties Changes: ===================================== client/configuration/src/main/java/fr/ird/observe/client/configuration/ClientConfig.java ===================================== @@ -42,6 +42,7 @@ import fr.ird.observe.navigation.tree.selection.SelectionTreeConfig; import fr.ird.observe.security.WithPermission; import fr.ird.observe.services.ObserveServiceInitializerConfig; import fr.ird.observe.services.service.CleanTemporaryFilesTaskConfiguration; +import fr.ird.observe.spi.ConfigHelper; import fr.ird.observe.spi.decoration.DecoratorService; import fr.ird.observe.spi.json.DtoGsonSupplier; import fr.ird.observe.spi.json.guava.ImmutableListAdapter; @@ -54,7 +55,6 @@ import io.ultreia.java4all.bean.definition.JavaBeanDefinition; import io.ultreia.java4all.bean.definition.JavaBeanDefinitionStore; import io.ultreia.java4all.bean.spi.GenerateJavaBeanDefinition; import io.ultreia.java4all.config.ApplicationConfig; -import io.ultreia.java4all.config.ApplicationConfigSaveException; import io.ultreia.java4all.config.ArgumentsParserException; import io.ultreia.java4all.config.ConfigResource; import io.ultreia.java4all.config.spi.ApplicationConfigInit; @@ -83,7 +83,6 @@ import java.awt.RenderingHints; import java.awt.image.BufferedImage; import java.beans.PropertyChangeListener; import java.io.BufferedReader; -import java.io.BufferedWriter; import java.io.File; import java.io.IOException; import java.nio.file.Files; @@ -106,7 +105,6 @@ import java.util.Properties; import java.util.ServiceLoader; import java.util.Set; import java.util.function.Supplier; -import java.util.stream.Collectors; import static io.ultreia.java4all.i18n.I18n.t; import static org.nuiton.jaxx.runtime.swing.SwingUtil.ICON_PREFIX; @@ -675,36 +673,9 @@ public class ClientConfig extends GeneratedClientConfig implements TripMapConfig } public void saveForUser() { - log.info(t("observe.ui.message.save.configuration", get().getExtraConfigFile())); - Properties propertiesToSave = get().getPropertiesToSave(false, doNotSave); - List<String> propertyNames = propertiesToSave.stringPropertyNames().stream().sorted().collect(Collectors.toList()); - for (ClientConfigOption option : options()) { - String optionKey = option.getKey(); - if (propertyNames.contains(optionKey)) { - String property = propertiesToSave.getProperty(optionKey); - if (Objects.equals(property, option.getDefaultValue())) { - // use default value - propertyNames.remove(optionKey); - } - } - } - log.info(String.format("Property names to save: %s", propertyNames)); - try (BufferedWriter writer = Files.newBufferedWriter(get().getExtraConfigFile().toPath())) { - List<String> lines = ClientResources.CONFIG.readLines(); - for (String line : lines) { - if (line.startsWith("#")) { - for (String propertyName : propertyNames) { - if (line.startsWith("#" + propertyName + "=")) { - line = String.format("%s=%s", propertyName, propertiesToSave.getProperty(propertyName)); - } - } - } - writer.write(line); - writer.newLine(); - } - } catch (IOException e) { - throw new ApplicationConfigSaveException(e); - } + File file = get().getExtraConfigFile(); + log.info(t("observe.ui.message.save.configuration", file)); + ConfigHelper.save(get(), file, doNotSave, ClientResources.CONFIG, options()); } public Project getNavigationEditModel() { ===================================== core/api/dto/pom.xml ===================================== @@ -69,6 +69,14 @@ <groupId>io.ultreia.java4all.decorator</groupId> <artifactId>decorator-api</artifactId> </dependency> + <dependency> + <groupId>io.ultreia.java4all.config</groupId> + <artifactId>config-api</artifactId> + </dependency> + <dependency> + <groupId>io.ultreia.java4all.config</groupId> + <artifactId>config-spi</artifactId> + </dependency> <dependency> <groupId>io.ultreia.java4all.decorator</groupId> <artifactId>decorator-spi</artifactId> ===================================== core/api/dto/src/main/java/fr/ird/observe/spi/ConfigHelper.java ===================================== @@ -0,0 +1,86 @@ +package fr.ird.observe.spi; + +/*- + * #%L + * ObServe Core :: API :: Dto + * %% + * Copyright (C) 2008 - 2022 IRD, Code Lutin, Ultreia.io + * %% + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public + * License along with this program. If not, see + * <http://www.gnu.org/licenses/gpl-3.0.html>. + * #L% + */ + +import io.ultreia.java4all.config.ApplicationConfig; +import io.ultreia.java4all.config.ApplicationConfigSaveException; +import io.ultreia.java4all.config.ConfigResource; +import io.ultreia.java4all.config.spi.ConfigOptionDef; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import java.io.BufferedWriter; +import java.io.File; +import java.io.IOException; +import java.nio.file.Files; +import java.util.List; +import java.util.Objects; +import java.util.Properties; +import java.util.stream.Collectors; + +/** + * FIXME Move this to config project. + * Created on 19/02/2022. + * + * @author Tony Chemit - dev@tchemit.fr + * @since 9.0.0 + */ +public class ConfigHelper { + + private static final Logger log = LogManager.getLogger(ConfigHelper.class); + + public static void save(ApplicationConfig applicationConfig, File file, String[] doNotSave, ConfigResource resource, ConfigOptionDef[] options) { + log.info(String.format("Save configuration to %s", file)); + Properties propertiesToSave = applicationConfig.getPropertiesToSave(false, doNotSave); + List<String> propertyNames = propertiesToSave.stringPropertyNames().stream().sorted().collect(Collectors.toList()); + for (ConfigOptionDef option : options) { + String optionKey = option.getKey(); + if (propertyNames.contains(optionKey)) { + String property = propertiesToSave.getProperty(optionKey); + if (Objects.equals(property, option.getDefaultValue())) { + // use default value + propertyNames.remove(optionKey); + } + } + } + + log.info(String.format("Property names to save: %s", propertyNames)); + try (BufferedWriter writer = Files.newBufferedWriter(file.toPath())) { + List<String> lines = resource.readLines(); + for (String line : lines) { + if (line.startsWith("#")) { + for (String propertyName : propertyNames) { + if (line.startsWith("#" + propertyName + "=")) { + line = String.format("%s=%s", propertyName, propertiesToSave.getProperty(propertyName)); + } + } + } + writer.write(line); + writer.newLine(); + } + } catch (IOException e) { + throw new ApplicationConfigSaveException(e); + } + } + +} ===================================== server/configuration/src/main/config/Server.ini ===================================== @@ -43,6 +43,11 @@ key = common.directory.config type = file defaultValue = ${common.directory.instances}/.conf/${build.version.major} +[option commonConfigurationFile] +key = common.directory.config.file +type = file +defaultValue = ${common.directory.config}/observe-server.conf + [option commonLog4jConfigurationFile] key = common.directory.config.file.log type = file ===================================== server/configuration/src/main/i18n/getters/config.getter ===================================== @@ -5,6 +5,7 @@ application.config.option.build.version.major application.config.option.build.version.persistence server.config.name server.config.option.common.directory.config +server.config.option.common.directory.config.file server.config.option.common.directory.config.file.log server.config.option.common.directory.config.file.server server.config.option.common.directory.instances ===================================== server/configuration/src/main/java/fr/ird/observe/server/configuration/ServerConfig.java ===================================== @@ -25,6 +25,7 @@ package fr.ird.observe.server.configuration; import fr.ird.observe.dto.ObserveUtil; import fr.ird.observe.dto.referential.ReferentialLocale; import fr.ird.observe.services.service.CleanTemporaryFilesTaskConfiguration; +import fr.ird.observe.spi.ConfigHelper; import io.ultreia.java4all.application.context.spi.ApplicationComponentInstantiateStrategy; import io.ultreia.java4all.application.context.spi.GenerateApplicationComponent; import io.ultreia.java4all.application.template.TemplateGeneratorConfig; @@ -60,38 +61,70 @@ public class ServerConfig extends GeneratedServerConfig implements CleanTemporar "observeweb.httpTimeout", "instance.timeout.http", "observeweb.sessionExpirationDelay", "instance.timeout.session", "observeweb.sessionMaximumSize", "instance.session.maximum.size" - ); + ); private static Logger log = LogManager.getLogger(ServerConfig.class); private ReferentialLocale referentialLocale; + protected static ApplicationConfigInit setConfigFileName(ApplicationConfigInit init) { + return init.setConfigFileName(DEFAULT_OBSERVE_WEB_CONFIGURATION_FILENAME); + } + + protected static ApplicationConfigInit setInstanceExtraConfigDirectory(ApplicationConfigInit init) { + return init.setExtraConfigDirectory("${instance.directory}"); + } + + protected static ApplicationConfigInit setCommonExtraConfigDirectory(ApplicationConfigInit init) { + return init.setExtraConfigDirectory("${common.directory.config}"); + } + public static ServerConfig fromContextPath(String contextPath) { - ServerConfig config = new ServerConfig(ApplicationConfigInit - .defaultInit() - .addDefaults(ServerConfigOption.CONTEXT_PATH.getKey(), contextPath)); - config.init(); + + // load a first configuration with /etc authorized (and only him) + // using extra config directory as common configuration directory + // if default configuration does not exist, generate it and migrates from /etc + + ApplicationConfigInit init = ApplicationConfigInit.forAllScopesWithout(ApplicationConfigScope.HOME, ApplicationConfigScope.ENV) + .addDefaults(ServerConfigOption.CONTEXT_PATH.getKey(), contextPath); + + ServerConfig fakeConfig = new ServerConfig(setCommonExtraConfigDirectory(setConfigFileName(init)), true); + fakeConfig.initFirst(); + + // Now that common files are ready, starts a normal configuration without system file and without migration possible + ApplicationConfigInit realInit = ApplicationConfigInit.forAllScopesWithout(ApplicationConfigScope.HOME, ApplicationConfigScope.ENV, ApplicationConfigScope.SYSTEM) + .addDefaults(ServerConfigOption.CONTEXT_PATH.getKey(), contextPath); + + ServerConfig config = new ServerConfig(setInstanceExtraConfigDirectory(setConfigFileName(realInit))); + config.init(true); return config; } public static ServerConfig forTest() throws IOException { Files.createDirectories(new File(System.getProperty("java.io.tmpdir")).toPath()); Path directory = Files.createTempDirectory("taiste"); - ServerConfig config = new ServerConfig(ApplicationConfigInit - .forAllScopesWithout(ApplicationConfigScope.CURRENT, - ApplicationConfigScope.HOME, - ApplicationConfigScope.ENV, - ApplicationConfigScope.JVM, - ApplicationConfigScope.CLASS_PATH, - ApplicationConfigScope.SYSTEM) - .addDefaults(ServerConfigOption.CONTEXT_PATH.getKey(), "observe-${build.version}") - .addDefaults(ServerConfigOption.COMMON_CONFIG_DIRECTORY.getKey(), String.format("%s/${build.version.major}", directory.resolve("conf"))) - .addDefaults(ServerConfigOption.COMMON_INSTANCES_DIRECTORY.getKey(), directory.resolve("instances").toString())); - config.init(); + ApplicationConfigInit init = ApplicationConfigInit + .forAllScopesWithout(ApplicationConfigScope.CURRENT, + ApplicationConfigScope.HOME, + ApplicationConfigScope.ENV, + ApplicationConfigScope.JVM, + ApplicationConfigScope.CLASS_PATH, + ApplicationConfigScope.SYSTEM) + .addDefaults(ServerConfigOption.CONTEXT_PATH.getKey(), "observe-${build.version}") + .addDefaults(ServerConfigOption.COMMON_CONFIG_DIRECTORY.getKey(), String.format("%s/${build.version.major}", directory.resolve("conf"))) + .addDefaults(ServerConfigOption.COMMON_INSTANCES_DIRECTORY.getKey(), directory.resolve("instances").toString()); + ServerConfig config = new ServerConfig(setInstanceExtraConfigDirectory(setConfigFileName(init))); + config.init(false); return config; } private ServerConfig(ApplicationConfigInit init) { - super(init.setConfigFileName(DEFAULT_OBSERVE_WEB_CONFIGURATION_FILENAME).setExtraConfigDirectory("${instance.directory}")); - get().setPropertiesMigration(V9_MIGRATION); + this(init, false); + } + + private ServerConfig(ApplicationConfigInit init, boolean acceptMigration) { + super(init); + if (acceptMigration) { + get().setPropertiesMigration(V9_MIGRATION); + } } @Override @@ -99,13 +132,31 @@ public class ServerConfig extends GeneratedServerConfig implements CleanTemporar return Collections.singletonMap(getTemporaryDirectory().toPath(), getTemporaryFilesTimeout()); } - public void init(String... args) { - log.info("Starts to init ObServe server configuration..."); - try { - get().parse(args); - } catch (ArgumentsParserException e) { - throw new ObserveWebApplicationConfigInitException("could not parse configuration", e); + public void initFirst() { + log.info("Starts to init ObServe fake server configuration (to generate default directories and common files..."); + + parse(); + + Path baseDirectory = getCommonConfigDirectory().toPath(); + createDirectories(baseDirectory, "Impossible de créer le répertoire principal de l'application (%s)"); + + File extraConfigFile = get().getExtraConfigFile(); + if (Files.notExists(extraConfigFile.toPath())) { + log.info(String.format("Save common configuration file to: %s", extraConfigFile)); + ConfigHelper.save(get(), extraConfigFile, new String[0], ServerResources.CONFIG, options()); + } + + File log4jConfigurationFile = getCommonLog4jConfigurationFile(); + if (!log4jConfigurationFile.exists()) { + ServerResources.LOG_CONFIGURATION_FILE.copyResource(log4jConfigurationFile); + log.info(String.format("Generate empty log4j configuration file to: %s", log4jConfigurationFile)); } + } + + public void init(boolean strict) { + log.info("Starts to init ObServe server configuration..."); + + parse(); Path baseDirectory = getBaseDirectory().toPath(); log.info(getConfigurationDescription()); @@ -113,8 +164,12 @@ public class ServerConfig extends GeneratedServerConfig implements CleanTemporar File extraConfigFile = get().getExtraConfigFile(); if (Files.notExists(extraConfigFile.toPath())) { - ServerResources.CONFIG.copyResource(extraConfigFile); - log.info(String.format("Generate empty configuration file to: %s", extraConfigFile)); + boolean generated = ServerResources.CONFIG.copyResource(getCommonConfigurationFile().toPath(), extraConfigFile); + if (generated) { + log.info(String.format("Generate empty configuration file to: %s", extraConfigFile)); + } else { + log.info(String.format("Create symbolic link from common configuration file to: %s", extraConfigFile)); + } } Path temporaryDirectory = getTemporaryDirectory().toPath(); @@ -122,7 +177,11 @@ public class ServerConfig extends GeneratedServerConfig implements CleanTemporar File securityConfigurationFile = getSecurityConfigurationFile(); if (!securityConfigurationFile.exists()) { - boolean generated = ServerResources.SECURITY.copyResource(getCommonSecurityConfigurationFile().toPath(), securityConfigurationFile); + File commonSecurityConfigurationFile = getCommonSecurityConfigurationFile(); + if (strict && !commonSecurityConfigurationFile.exists()) { + throw new IllegalStateException(String.format("Can not start application. Could not find security.yml file.\n\nPlease add it to one of this places:\n\t%s\n\t%s", commonSecurityConfigurationFile, securityConfigurationFile)); + } + boolean generated = ServerResources.SECURITY.copyResource(commonSecurityConfigurationFile.toPath(), securityConfigurationFile); if (generated) { log.info("Generate default security.yml"); } else { @@ -133,6 +192,15 @@ public class ServerConfig extends GeneratedServerConfig implements CleanTemporar log.info("ObServe server configuration init done."); } + private void parse() { + try { + get().parse(); + } catch (ArgumentsParserException e) { + throw new ObserveWebApplicationConfigInitException("could not parse configuration", e); + } + + } + private void initLog() { File logFile = getLog4jConfigurationFile(); log.info(String.format("Chargement du fichier de log : %s", logFile)); ===================================== server/runner/src/main/i18n/translations/server-runner_en_GB.properties ===================================== @@ -1,5 +1,6 @@ server.config.name=ObServe Web configuration server.config.option.common.directory.config=Common config directory +server.config.option.common.directory.config.file=Common config file server.config.option.common.directory.config.file.log=Common config log file server.config.option.common.directory.config.file.server=Common config databases file server.config.option.common.directory.instances=Instances directory ===================================== server/runner/src/main/i18n/translations/server-runner_es_ES.properties ===================================== @@ -1,5 +1,6 @@ server.config.name=Configuración de Observe web server.config.option.common.directory.config=Common directory +server.config.option.common.directory.config.file=Common config file server.config.option.common.directory.config.file.log=Common config log file server.config.option.common.directory.config.file.server=Common config databases file server.config.option.common.directory.instances=Instances directory ===================================== server/runner/src/main/i18n/translations/server-runner_fr_FR.properties ===================================== @@ -1,5 +1,6 @@ server.config.name=Observe web Configuration server.config.option.common.directory.config=Répertoire des configurations partagées +server.config.option.common.directory.config.file=Chemin vers le fichier commun de configuration server.config.option.common.directory.config.file.log=Chemin vers le fichier commun de configuration des logs server.config.option.common.directory.config.file.server=Chemin vers le fichier commun de configuration des bases server.config.option.common.directory.instances=Chemin des instances View it on GitLab: https://gitlab.com/ultreiaio/ird-observe/-/commit/5c3ce96f5e4a5fec67fc7f93f1... -- View it on GitLab: https://gitlab.com/ultreiaio/ird-observe/-/commit/5c3ce96f5e4a5fec67fc7f93f1... You're receiving this email because of your account on gitlab.com.