Index: topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationService.java
diff -u topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationService.java:1.1 topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationService.java:1.2
--- topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationService.java:1.1 Mon Apr 2 14:24:37 2007
+++ topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationService.java Wed Nov 14 17:36:11 2007
@@ -19,6 +19,7 @@
package org.codelutin.topia.migration;
import org.codelutin.topia.framework.TopiaService;
+import org.codelutin.topia.migration.callback.MigrationCallbackHandler;
import org.hibernate.cfg.Configuration;
/**
@@ -28,62 +29,71 @@
* @author Chevallereau Benjamin
* @author Eon Sébastien
* @author Trève Vincent
- * @version $Revision: 1.1 $
+ * @version $Revision: 1.2 $
*
- * Last update : $Date: 2007-04-02 14:24:37 $
+ * Last update : $Date: 2007-11-14 17:36:11 $
*/
public interface TopiaMigrationService extends TopiaService {
+ /**
+ * Nom du service
+ */
public static final String SERVICE_NAME = "migration";
/**
* Renvoie le chemin du ficier de configuration utilise
* @return Chemin du fichier de configuration
*/
- public abstract String getConfigurationFile();
+ public String getConfigurationFile();
/**
* Modifie le fichier de configuration
* @param configurationFile Chemin du fichier de configuration d'hibernate
*/
- public abstract void setConfigurationFile(String configurationFile);
+ public void setConfigurationFile(String configurationFile);
/**
* Retourne la configuration
* @return la configuration
* @see org.hibernate.cfg.Configuration
*/
- public abstract Configuration getConfiguration();
+ public Configuration getConfiguration();
/**
* Renseigne la configuration
* @param configuration la configuration
* @see org.hibernate.cfg.Configuration
*/
- public abstract void setConfiguration(Configuration configuration);
+ public void setConfiguration(Configuration configuration);
/**
* Retourne le repertoire des anciens schemas
* @return Le repertoire des anciens schemas
*/
- public abstract String getMappingsDirectory();
+ public String getMappingsDirectory();
/**
* Modifie le chemin du dossier des anciens schemas
* @param mappingsDirectory Le chemin du dossier des anciens schemas
*/
- public abstract void setMappingsDirectory(String mappingsDirectory);
+ public void setMappingsDirectory(String mappingsDirectory);
/**
* Change la version courante
* @param version la version
*/
- public abstract void setApplicationVersion(String version);
+ public void setApplicationVersion(String version);
/**
+ * Ajoute un callbackhandler pour la migration
+ */
+ public void addMigrationCallbackHandler(MigrationCallbackHandler callbackHandler);
+
+ /**
* Migrate the schema
*
+ * @return true si la migration a ete effectuee et s'est bien passee, false sinon
* @throws TopiaMigrationServiceException dans le cas ou le schema ne peut pas etre mis a jour
*/
- public abstract void migrateSchema() throws TopiaMigrationServiceException;
+ public boolean migrateSchema() throws TopiaMigrationServiceException;
}
\ No newline at end of file
Index: topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationServiceImpl.java
diff -u topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationServiceImpl.java:1.7 topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationServiceImpl.java:1.8
--- topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationServiceImpl.java:1.7 Fri Nov 9 16:35:45 2007
+++ topia-service/src/java/org/codelutin/topia/migration/TopiaMigrationServiceImpl.java Wed Nov 14 17:36:11 2007
@@ -21,6 +21,7 @@
import java.io.File;
import java.net.URL;
import java.util.HashMap;
+import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Properties;
@@ -33,6 +34,7 @@
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.codelutin.topia.framework.TopiaContextImplementor;
+import org.codelutin.topia.migration.callback.MigrationCallbackHandler;
import org.codelutin.topia.migration.common.Version;
import org.codelutin.topia.migration.kernel.ConfigurationAdapter;
import org.codelutin.topia.migration.kernel.ConfigurationHelper;
@@ -47,46 +49,52 @@
*
* @author Chatellier Eric
* @author Chevallereau Benjamin
- * @author Eon Sébastien
- * @author Trève Vincent
- * @version $Revision: 1.7 $
+ * @author Eon S�bastien
+ * @author Tr�ve Vincent
+ * @version $Revision: 1.8 $
*
- * Last update : $Date: 2007-11-09 16:35:45 $
+ * Last update : $Date: 2007-11-14 17:36:11 $
*/
public class TopiaMigrationServiceImpl implements TopiaMigrationService {
/**
* Nom des proprietes
*/
- static private final String MIGRATION_APPLICATION_VERSION = "topia.service.migration.version";
- static private final String MIGRATION_PREVIOUS_MAPPING_DIRECTORY = "topia.service.migration.mappingsdir";
- static private final String MIGRATION_PREVIOUS_MODEL_NAME = "topia.service.migration.modelnames";
+ static public final String MIGRATION_APPLICATION_VERSION = "topia.service.migration.version";
+ static public final String MIGRATION_PREVIOUS_MAPPING_DIRECTORY = "topia.service.migration.mappingsdir";
+ static public final String MIGRATION_MODEL_NAMES = "topia.service.migration.modelnames";
+ static public final String MIGRATION_CALLBACKHANDLERS = "topia.service.migration.callbackhandlers";
/**
* C'est la meme, mais ca vire des dependances
*/
- static final private String TOPIA_PERSISTENCE_DIRECTORIES = "topia.persistence.directories";
- static final private String TOPIA_PERSISTENCE_CLASSES = "topia.persistence.classes";
+ static final protected String TOPIA_PERSISTENCE_DIRECTORIES = "topia.persistence.directories";
+ static final protected String TOPIA_PERSISTENCE_CLASSES = "topia.persistence.classes";
/**
* Nom courant du fichier de configuration.
*/
- private String currentHibernateConfigurationFile;
+ protected String currentHibernateConfigurationFile;
/**
* Configuration hibernate courante utilisee par l'application
*/
- private Configuration currentApplicationConfiguration;
+ protected Configuration currentApplicationConfiguration;
/**
* Chemin du dossier contenant les schema de touts les versions
*/
- private String mappingsDirectory;
+ protected String mappingsDirectory;
/**
* Version courante de l'application
*/
- private Version currentApplicationVersion;
+ protected Version currentApplicationVersion;
+
+ /**
+ * CallbackHandler list
+ */
+ protected List migrationCallBackHandlers;
/**
* Logger (common-logging)
@@ -106,16 +114,28 @@
currentHibernateConfigurationFile = null;
// init configuration
currentApplicationConfiguration = null;
+
+ // init callbask list
+ migrationCallBackHandlers = new LinkedList();
}
+ /* (non-Javadoc)
+ * @see org.codelutin.topia.framework.TopiaService#getPersistenceClasses()
+ */
public Class [] getPersistenceClasses() {
return null;
}
+ /* (non-Javadoc)
+ * @see org.codelutin.topia.framework.TopiaService#getServiceName()
+ */
public String getServiceName() {
return TopiaMigrationService.SERVICE_NAME;
}
+ /* (non-Javadoc)
+ * @see org.codelutin.topia.framework.TopiaService#preInit(org.codelutin.topia.framework.TopiaContextImplementor)
+ */
public void preInit(TopiaContextImplementor context) {
Properties config = context.getConfig();
@@ -182,6 +202,33 @@
}
+ // ajout des callbackhandlers
+ String callbackHandlers = config.getProperty(MIGRATION_CALLBACKHANDLERS,"");
+
+ String[] tabCallbackHandlers = callbackHandlers.split(",");
+ for(String callbackHandler : tabCallbackHandlers) {
+ callbackHandler = callbackHandler.trim();
+ if (!"".equals(callbackHandler)) {
+ Class clazz;
+ try {
+ clazz = (Class)Class.forName(callbackHandler);
+ MigrationCallbackHandler instance = clazz.newInstance();
+ addMigrationCallbackHandler(instance);
+ } catch (ClassNotFoundException e) {
+ logger.error(
+ "CallbackHandler Class " + callbackHandler
+ + " not found",e);
+ } catch (InstantiationException e) {
+ logger.error(
+ "CallbackHandler class " + callbackHandler
+ + " cannot be instanciated",e);
+ } catch (IllegalAccessException e) {
+ logger.error(
+ "CallbackHandler class " + callbackHandler
+ + " cannot be accessed",e);
+ }
+ }
+ }
// test mappingdir null
@@ -194,7 +241,7 @@
if(applicationversion != null) {
// effectue la migration de tous les modeles
String modelnamesList = config.getProperty(
- MIGRATION_PREVIOUS_MODEL_NAME, "");
+ MIGRATION_MODEL_NAMES, "");
String[] modelnames = modelnamesList.split(",");
for(String modelname : modelnames) {
@@ -212,6 +259,9 @@
}
}
+ /* (non-Javadoc)
+ * @see org.codelutin.topia.framework.TopiaService#postInit(org.codelutin.topia.framework.TopiaContextImplementor)
+ */
public void postInit(TopiaContextImplementor context) {
}
@@ -265,10 +315,18 @@
currentApplicationVersion = new Version(version);
}
+ /* (non-Javadoc)
+ * @see org.codelutin.topia.migration.TopiaMigrationService#addMigrationCallbackHandler(org.codelutin.topia.migration.callback.MigrationCallbackHandler)
+ */
+ public void addMigrationCallbackHandler(
+ MigrationCallbackHandler callbackHandler) {
+ migrationCallBackHandlers.add(callbackHandler);
+ }
+
/**
* Charge la configuration locale si elle n'est pas deja ete fournit
*/
- private void loadApplicationConfiguration() {
+ protected void loadApplicationConfiguration() {
// configuration pas deja fournit
if(this.currentApplicationConfiguration == null) {
@@ -297,8 +355,13 @@
/* (non-Javadoc)
* @see org.codelutin.topia.migration.TopiaMigrationService#migrateSchema()
*/
- public void migrateSchema() throws TopiaMigrationServiceException {
+ public boolean migrateSchema() throws TopiaMigrationServiceException {
+ /*temp*/long timeBegin = System.currentTimeMillis();
+
+ // return flag
+ boolean schemaMigrated = false;
+
// log
logger.info("Starting Topia Migration Service");
@@ -338,11 +401,33 @@
}
logger.info("Application version : " + currentApplicationVersion.getVersion() + ", database version : " + vdbVersion.getVersion());
-
+
+ /*temp*/long timeEnd = System.currentTimeMillis();
+
+ /*temp*/logger.error("[Time] get db version took : " + (timeEnd - timeBegin) + " ms");
+
+ // ask handler for migration
+ boolean doMigration;
// vdbVersion < currentApplicationVersion
if(vdbVersion.compareTo(currentApplicationVersion) < 0) {
+ logger.info("Database need update");
+
+ doMigration = askHandlerForMigration(vdbVersion.getVersion(),currentApplicationVersion.getVersion());
+
+ schemaMigrated = doMigration;
+ }
+ else {
+ doMigration = false;
+ schemaMigrated = true; // normal behaviour
+ logger.info("Database is up to date, no migration needed.");
+ }
+
+ // si la migration doit etre faite
+ if(doMigration) {
- logger.info("Database need update");
+ /*temp*/timeBegin = System.currentTimeMillis();
+
+ logger.info("Database need update");
// ici, on charge toutes les configuration, entre >= vdbVersion et < currentApplicationVersion
Map mVersionAndConfigurationMap = loadOldConfigurations(vdbVersion);
@@ -432,21 +517,42 @@
// all done
logger.info("All done, migration complete");
- }
- else {
- logger.info("Database is up to date, exiting.");
+ /*temp*/timeEnd = System.currentTimeMillis();
+ /*temp*/logger.error("[Time] migration took : " + (timeEnd - timeBegin) + " ms");
+
}
// ferme la connexion a la base
dbManager.disconnect();
+
+ return schemaMigrated;
}
/**
+ * Ask handler for migration.
+ *
+ * Return true if all handler return true, or if there is no handler
+ *
+ * @return true or false
+ */
+ protected boolean askHandlerForMigration(String databaseVersion, String applicationVersion) {
+
+ // true par defaut, s'il n'y a pas de handlers
+ boolean result = true;
+
+ for(MigrationCallbackHandler callback : migrationCallBackHandlers) {
+ result &= callback.doMigration(databaseVersion, applicationVersion);
+ }
+
+ return result;
+ }
+
+ /**
* Charge les configurations de version a partir de vdbVersion
* jusqu'a currentApplicationVersion "non compris"
* @param vdbVersion la version de depart
*/
- private Map loadOldConfigurations(Version vdbVersion) {
+ protected Map loadOldConfigurations(Version vdbVersion) {
// schema des noms de dossier de version
final Pattern pattern = Pattern.compile(mappingsDirectory + File.separator + "([0-9]+(\\.[0-9]+)*)");