added additional functionality to the module manager

This commit is contained in:
Eric J. Bowersox 2003-06-19 06:36:29 +00:00
parent fbaf90e156
commit f1ceac134c
13 changed files with 658 additions and 18 deletions

View File

@ -48,8 +48,9 @@
<connection-point name="srm_proxy" interface="com.silverwrist.dynamo.db.UserProxyManagement"/> <connection-point name="srm_proxy" interface="com.silverwrist.dynamo.db.UserProxyManagement"/>
</object> </object>
<object name="module-manager" classname="com.silverwrist.dynamo.module.ModuleManager" priority="0"> <object name="module-manager" classname="com.silverwrist.dynamo.module.ModuleManager" priority="2">
<module-directory>${code.path}/modules</module-directory> <module-directory>${code.path}/modules</module-directory>
<database connection="data" namespaces="nscache"/>
</object> </object>
<!-- Data-driven objects --> <!-- Data-driven objects -->

View File

@ -48,8 +48,9 @@
<connection-point name="srm_proxy" interface="com.silverwrist.dynamo.db.UserProxyManagement"/> <connection-point name="srm_proxy" interface="com.silverwrist.dynamo.db.UserProxyManagement"/>
</object> </object>
<object name="module-manager" classname="com.silverwrist.dynamo.module.ModuleManager" priority="0"> <object name="module-manager" classname="com.silverwrist.dynamo.module.ModuleManager" priority="2">
<module-directory>${code.path}/modules</module-directory> <module-directory>${code.path}/modules</module-directory>
<database connection="data" namespaces="nscache"/>
</object> </object>
<!-- Data-driven objects --> <!-- Data-driven objects -->

View File

@ -339,6 +339,14 @@ CREATE TABLE ndx_locks (
PRIMARY KEY (ndxid, name) PRIMARY KEY (ndxid, name)
); );
# Table indicating which modules have been installed.
CREATE TABLE modinstall (
filename VARCHAR(255) BINARY NOT NULL PRIMARY KEY, # file name relative to module directory
mod_nsid INT NOT NULL, # namespaceID of module name
mod_name VARCHAR(255) BINARY NOT NULL, # module name within namespace
UNIQUE INDEX by_name (mod_nsid, mod_name)
);
############################ following this line are Venice-specific tables ############################ ############################ following this line are Venice-specific tables ############################
# The table which defines menus. # The table which defines menus.

View File

@ -18,6 +18,7 @@
package com.silverwrist.dynamo.iface; package com.silverwrist.dynamo.iface;
import java.security.Principal; import java.security.Principal;
import com.silverwrist.dynamo.except.DatabaseException;
import com.silverwrist.dynamo.except.ModuleException; import com.silverwrist.dynamo.except.ModuleException;
import com.silverwrist.dynamo.util.QualifiedNameKey; import com.silverwrist.dynamo.util.QualifiedNameKey;
@ -25,9 +26,9 @@ public interface Module
{ {
public QualifiedNameKey getModuleID(); public QualifiedNameKey getModuleID();
public void install(ServiceProvider services, Principal installer) throws ModuleException; public void install(Principal installer) throws DatabaseException, ModuleException;
public void uninstall(ServiceProvider services, Principal uninstaller) throws ModuleException; public void uninstall(Principal uninstaller) throws DatabaseException, ModuleException;
public DynamicObject getProvidedObject(String namespace, String name) throws ModuleException; public DynamicObject getProvidedObject(String namespace, String name) throws ModuleException;

View File

@ -0,0 +1,256 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (the "License"); you may not use this file except in compliance with the License.
* You may obtain a copy of the License at <http://www.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2003 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.module;
import java.util.*;
import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*;
import com.silverwrist.dynamo.util.*;
class InstallServiceManager
{
/*--------------------------------------------------------------------------------
* Internal class implementing the install service provider
*--------------------------------------------------------------------------------
*/
private class Services extends BaseDelegatingServiceProvider
{
/*====================================================================
* Constructors
*====================================================================
*/
Services()
{
super("Module Initialization Services");
} // end constructor
Services(ServiceProvider delegate)
{
super("Module Initialization Services",delegate);
} // end constructor
/*====================================================================
* Overrides from class BaseDelegatingServiceProvider
*====================================================================
*/
/**
* Queries this object for a specified service.
*
* @param klass The class of the object that should be returned as a service.
* @return A service object. The service object is guaranteed to be of the class
* specified by <CODE>klass</CODE>; that is, if <CODE>queryService(klass)</CODE>
* yields some object <CODE>x</CODE>, then the expression <CODE>klass.isInstance(x)</CODE>
* is true.
* @exception com.silverwrist.dynamo.except.NoSuchServiceException If no service is available in
* the specified class.
*/
public Object queryService(Class klass)
{
Object rc = m_service_cache.get(klass);
if (rc!=null)
return rc;
for (int i=(m_service_hooks.size()-1); i>=0; i--)
{ // call the hooks
try
{ // get hooks in reverse order of installation and try them
ServiceProvider sp = (ServiceProvider)(m_service_hooks.get(i));
rc = sp.queryService(klass);
m_service_cache.put(klass,rc);
return rc;
} // end try
catch (NoSuchServiceException e)
{ // cycle around and keep trying
} // end catch
} // end for
rc = m_services.get(klass);
if (rc!=null)
{ // cache the service
m_service_cache.put(klass,rc);
return rc;
} // end if
return super.queryService(klass);
} // end queryService
/**
* Queries this object for a specified service.
*
* @param klass The class of the object that should be returned as a service.
* @param serviceid ID for the service to be requested, to further discriminate between requests.
* @return A service object. The service object is guaranteed to be of the class
* specified by <CODE>klass</CODE>; that is, if <CODE>queryService(klass)</CODE>
* yields some object <CODE>x</CODE>, then the expression <CODE>klass.isInstance(x)</CODE>
* is true.
* @exception com.silverwrist.dynamo.except.NoSuchServiceException If no service is available in
* the specified class.
*/
public Object queryService(Class klass, String serviceid)
{
ServiceKey key = new ServiceKey(klass,serviceid);
Object rc = m_service_cache.get(key);
if (rc!=null)
return rc;
for (int i=(m_service_hooks.size()-1); i>=0; i--)
{ // call the hooks
try
{ // get hooks in reverse order of installation and try them
ServiceProvider sp = (ServiceProvider)(m_service_hooks.get(i));
rc = sp.queryService(klass,serviceid);
m_service_cache.put(key,rc);
return rc;
} // end try
catch (NoSuchServiceException e)
{ // cycle around and keep trying
} // end catch
} // end for
try
{ // call through to superclass
return super.queryService(klass,serviceid);
} // end try
catch (NoSuchServiceException e)
{ // OK, try it without the service ID
rc = queryService(klass);
m_service_cache.put(key,rc);
return rc;
} // end catch
} // end queryService
} // end class Services
/*--------------------------------------------------------------------------------
* Internal class for removing hooks
*--------------------------------------------------------------------------------
*/
private class RemoveHook implements ComponentShutdown
{
/*====================================================================
* Attributes
*====================================================================
*/
private ServiceProvider m_sp;
/*====================================================================
* Constructor
*====================================================================
*/
RemoveHook(ServiceProvider sp)
{
m_sp = sp;
} // end constructor
/*====================================================================
* Implementations from interface ComponentShutdown
*====================================================================
*/
public void shutdown()
{
m_service_hooks.remove(m_sp);
m_service_cache.clear();
} // end shutdown
} // end class RemoveHook
/*--------------------------------------------------------------------------------
* Attributes
*--------------------------------------------------------------------------------
*/
private Hashtable m_services = new Hashtable();
private Vector m_service_hooks = new Vector();
private Hashtable m_service_cache = new Hashtable();
private ServiceProvider m_base = null;
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
InstallServiceManager()
{ // do nothing
} // end constructor
/*--------------------------------------------------------------------------------
* External operations
*--------------------------------------------------------------------------------
*/
void addService(Class klass, Object svc)
{
m_services.put(klass,svc);
} // end addService
synchronized ServiceProvider getServiceProvider()
{
if (m_base==null)
m_base = new Services();
return m_base;
} // end getServiceProvider
ServiceProvider getServiceProvider(ServiceProvider delegate)
{
if (delegate==null)
return this.getServiceProvider();
else
return new Services(delegate);
} // end getServiceProvider
ComponentShutdown hook(ServiceProvider sp)
{
m_service_hooks.add(sp);
m_service_cache.clear();
return new RemoveHook(sp);
} // end hook
void dispose()
{
m_services.clear();
m_service_hooks.clear();
m_service_cache.clear();
m_base = null;
} // end dispose
} // end class InstallServiceManager

View File

@ -0,0 +1,62 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (the "License"); you may not use this file except in compliance with the License.
* You may obtain a copy of the License at <http://www.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2003 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.module;
import java.util.*;
import com.silverwrist.dynamo.db.OpsBase;
import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*;
abstract class ModuleDBOps extends OpsBase
{
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
protected ModuleDBOps(DBConnectionPool pool)
{
super(pool);
} // end constructor
/*--------------------------------------------------------------------------------
* Abstract operations
*--------------------------------------------------------------------------------
*/
abstract boolean isModuleInstalled(String filename) throws DatabaseException;
abstract Set getInstalledModules() throws DatabaseException;
abstract void markInstalled(String filename, int nsid, String name) throws DatabaseException;
abstract void unmarkInstalled(String filename) throws DatabaseException;
/*--------------------------------------------------------------------------------
* External static operations
*--------------------------------------------------------------------------------
*/
static ModuleDBOps get(DBConnectionPool pool) throws ConfigException
{
return (ModuleDBOps)get(pool,ModuleDBOps.class.getClassLoader(),ModuleDBOps.class.getName() + "_","ModuleDBOps");
} // end get
} // end class ModuleDBOps

View File

@ -0,0 +1,186 @@
/*
* The contents of this file are subject to the Mozilla Public License Version 1.1
* (the "License"); you may not use this file except in compliance with the License.
* You may obtain a copy of the License at <http://www.mozilla.org/MPL/>.
*
* Software distributed under the License is distributed on an "AS IS" basis, WITHOUT
* WARRANTY OF ANY KIND, either express or implied. See the License for the specific
* language governing rights and limitations under the License.
*
* The Original Code is the Venice Web Communities System.
*
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2003 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
*
* Contributor(s):
*/
package com.silverwrist.dynamo.module;
import java.sql.*;
import java.util.*;
import com.silverwrist.util.*;
import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*;
public class ModuleDBOps_mysql extends ModuleDBOps
{
/*--------------------------------------------------------------------------------
* Constructor
*--------------------------------------------------------------------------------
*/
public ModuleDBOps_mysql(DBConnectionPool pool)
{
super(pool);
} // end constructor
/*--------------------------------------------------------------------------------
* Abstract implementations from class ModuleDBOps
*--------------------------------------------------------------------------------
*/
boolean isModuleInstalled(String filename) throws DatabaseException
{
Connection conn = null;
PreparedStatement stmt = null;
ResultSet rs = null;
try
{ // get a connection
conn = getConnection();
// prepare and execute the query
stmt = conn.prepareStatement("SELECT mod_nsid FROM modinstall WHERE filename = ?;");
stmt.setString(1,filename);
rs = stmt.executeQuery();
return rs.next();
} // end try
catch (SQLException e)
{ // translate to a general DatabaseException
throw generalException(e);
} // end catch
finally
{ // shut everything down
SQLUtils.shutdown(rs);
SQLUtils.shutdown(stmt);
SQLUtils.shutdown(conn);
} // end finally
} // end isModuleInstalled
Set getInstalledModules() throws DatabaseException
{
Connection conn = null;
PreparedStatement stmt = null;
ResultSet rs = null;
try
{ // get a connection
conn = getConnection();
// prepare and execute the query
stmt = conn.prepareStatement("SELECT filename FROM modinstall ORDER BY filename;");
rs = stmt.executeQuery();
// output the set in sorted order
TreeSet rc = new TreeSet();
while (rs.next())
rc.add(rs.getString(1));
return Collections.unmodifiableSet(rc);
} // end try
catch (SQLException e)
{ // translate to a general DatabaseException
throw generalException(e);
} // end catch
finally
{ // shut everything down
SQLUtils.shutdown(rs);
SQLUtils.shutdown(stmt);
SQLUtils.shutdown(conn);
} // end finally
} // end getInstalledModules
void markInstalled(String filename, int nsid, String name) throws DatabaseException
{
Connection conn = null;
PreparedStatement stmt = null;
Statement stmt2 = null;
ResultSet rs = null;
try
{ // get a connection
conn = getConnection();
// lock the database table
stmt2 = conn.createStatement();
stmt2.executeUpdate("LOCK TABLES modinstall WRITE;");
// execute the update
stmt = conn.prepareStatement("INSERT INTO modinstall (filename, mod_nsid, mod_name) VALUES (?, ?, ?);");
stmt.setString(1,filename);
stmt.setInt(2,nsid);
stmt.setString(3,name);
stmt.executeUpdate();
} // end try
catch (SQLException e)
{ // translate to a general DatabaseException
throw generalException(e);
} // end catch
finally
{ // shut everything down
MySQLUtils.unlockTables(conn);
SQLUtils.shutdown(rs);
SQLUtils.shutdown(stmt);
SQLUtils.shutdown(stmt2);
SQLUtils.shutdown(conn);
} // end finally
} // end markInstalled
void unmarkInstalled(String filename) throws DatabaseException
{
Connection conn = null;
PreparedStatement stmt = null;
Statement stmt2 = null;
ResultSet rs = null;
try
{ // get a connection
conn = getConnection();
// lock the database table
stmt2 = conn.createStatement();
stmt2.executeUpdate("LOCK TABLES modinstall WRITE;");
// execute the update
stmt = conn.prepareStatement("DELETE FROM modinstall WHERE filename = ?;");
stmt.setString(1,filename);
stmt.executeUpdate();
} // end try
catch (SQLException e)
{ // translate to a general DatabaseException
throw generalException(e);
} // end catch
finally
{ // shut everything down
MySQLUtils.unlockTables(conn);
SQLUtils.shutdown(rs);
SQLUtils.shutdown(stmt);
SQLUtils.shutdown(stmt2);
SQLUtils.shutdown(conn);
} // end finally
} // end unmarkInstalled
} // end class ModuleDBOps_mysql

View File

@ -22,6 +22,7 @@ import java.net.*;
import java.security.Principal; import java.security.Principal;
import java.util.jar.*; import java.util.jar.*;
import org.apache.log4j.Logger; import org.apache.log4j.Logger;
import com.silverwrist.dynamo.db.NamespaceCache;
import com.silverwrist.dynamo.except.*; import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*; import com.silverwrist.dynamo.iface.*;
import com.silverwrist.dynamo.util.*; import com.silverwrist.dynamo.util.*;
@ -112,6 +113,9 @@ class ModuleLoader extends URLClassLoader implements Module
*-------------------------------------------------------------------------------- *--------------------------------------------------------------------------------
*/ */
private ModuleDBOps m_ops; // module operations
private NamespaceCache m_nscache; // namespace cache
private ServiceProvider m_install_svcs; // reference to installer services
private URL m_jar_url; // URL to the module JAR file private URL m_jar_url; // URL to the module JAR file
private String m_filename; // filename of the original JAR file relative to module directory private String m_filename; // filename of the original JAR file relative to module directory
private String m_resource_path; // resource path for the JAR file private String m_resource_path; // resource path for the JAR file
@ -123,11 +127,15 @@ class ModuleLoader extends URLClassLoader implements Module
*-------------------------------------------------------------------------------- *--------------------------------------------------------------------------------
*/ */
ModuleLoader(File modfile, String filename) throws ModuleException, MalformedURLException ModuleLoader(File modfile, String filename, ModuleDBOps ops, NamespaceCache nscache, ServiceProvider install_svcs)
throws ModuleException, MalformedURLException
{ {
super(new URL[] { modfile.toURL() },ModuleLoader.class.getClassLoader()); super(new URL[] { modfile.toURL() },ModuleLoader.class.getClassLoader());
logger.info("Loading module " + modfile.getAbsolutePath()); logger.info("Loading module " + modfile.getAbsolutePath());
m_filename = filename; m_filename = filename;
m_ops = ops;
m_nscache = nscache;
m_install_svcs = install_svcs;
String main_class_name = null; String main_class_name = null;
try try
{ // create a JAR URL and use it to get the JAR attributes { // create a JAR URL and use it to get the JAR attributes
@ -276,9 +284,12 @@ class ModuleLoader extends URLClassLoader implements Module
} // end getModuleID } // end getModuleID
public void install(ServiceProvider services, Principal installer) throws ModuleException public synchronized void install(Principal installer) throws DatabaseException, ModuleException
{ {
if (!(m_modfuncs.canInstall(services,installer))) if (m_ops.isModuleInstalled(m_filename))
return; // already installed
if (!(m_modfuncs.canInstall(m_install_svcs,installer)))
{ // you are not permitted to install or uninstall modules { // you are not permitted to install or uninstall modules
ModuleException me = new ModuleException(ModuleLoader.class,"ModuleMessages","module.noAuth"); ModuleException me = new ModuleException(ModuleLoader.class,"ModuleMessages","module.noAuth");
me.setParameter(0,m_modfuncs.getModuleID().toString()); me.setParameter(0,m_modfuncs.getModuleID().toString());
@ -295,15 +306,20 @@ class ModuleLoader extends URLClassLoader implements Module
} // end if } // end if
ModuleSite s = new Site(); ModuleSite s = new Site();
m_modfuncs.install(s,services,installer); m_modfuncs.install(s,m_install_svcs,installer);
m_modfuncs.initialize(s,services); QualifiedNameKey name = m_modfuncs.getModuleID();
m_ops.markInstalled(m_filename,m_nscache.namespaceNameToId(name.getNamespace()),name.getName());
m_modfuncs.initialize(s,m_install_svcs);
m_initialized = true; m_initialized = true;
} // end install } // end install
public void uninstall(ServiceProvider services, Principal uninstaller) throws ModuleException public synchronized void uninstall(Principal uninstaller) throws DatabaseException, ModuleException
{ {
if (!(m_modfuncs.canInstall(services,uninstaller))) if (!(m_ops.isModuleInstalled(m_filename)))
return; // already uninstalled
if (!(m_modfuncs.canInstall(m_install_svcs,uninstaller)))
{ // you are not permitted to install or uninstall modules { // you are not permitted to install or uninstall modules
ModuleException me = new ModuleException(ModuleLoader.class,"ModuleMessages","module.noAuth"); ModuleException me = new ModuleException(ModuleLoader.class,"ModuleMessages","module.noAuth");
me.setParameter(0,m_modfuncs.getModuleID().toString()); me.setParameter(0,m_modfuncs.getModuleID().toString());
@ -318,7 +334,8 @@ class ModuleLoader extends URLClassLoader implements Module
} // end if } // end if
m_modfuncs.uninstall(new Site(),services,uninstaller); m_modfuncs.uninstall(new Site(),m_install_svcs,uninstaller);
m_ops.unmarkInstalled(m_filename);
} // end uninstall } // end uninstall
@ -347,6 +364,14 @@ class ModuleLoader extends URLClassLoader implements Module
} // end shutdown } // end shutdown
void dispose()
{
m_ops = null;
m_nscache = null;
m_modfuncs = null;
} // end dispose
boolean isInitialized() boolean isInitialized()
{ {
return m_initialized; return m_initialized;

View File

@ -21,16 +21,25 @@ import java.io.*;
import java.net.MalformedURLException; import java.net.MalformedURLException;
import java.util.*; import java.util.*;
import java.util.jar.*; import java.util.jar.*;
import org.apache.log4j.Logger;
import org.w3c.dom.*; import org.w3c.dom.*;
import com.silverwrist.util.xml.*; import com.silverwrist.util.xml.*;
import com.silverwrist.dynamo.Namespaces; import com.silverwrist.dynamo.Namespaces;
import com.silverwrist.dynamo.app.ApplicationContainer; import com.silverwrist.dynamo.app.ApplicationContainer;
import com.silverwrist.dynamo.db.NamespaceCache;
import com.silverwrist.dynamo.except.*; import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*; import com.silverwrist.dynamo.iface.*;
import com.silverwrist.dynamo.util.*; import com.silverwrist.dynamo.util.*;
public class ModuleManager implements NamedObject, ComponentInitialize, ComponentShutdown, ModuleOperations public class ModuleManager implements NamedObject, ComponentInitialize, ComponentShutdown, ModuleOperations
{ {
/*--------------------------------------------------------------------------------
* Static data members
*--------------------------------------------------------------------------------
*/
private static Logger logger = Logger.getLogger(ModuleManager.class);
/*-------------------------------------------------------------------------------- /*--------------------------------------------------------------------------------
* Attributes * Attributes
*-------------------------------------------------------------------------------- *--------------------------------------------------------------------------------
@ -38,9 +47,13 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
private String m_name; private String m_name;
private ApplicationContainer m_appcon; private ApplicationContainer m_appcon;
private NamespaceCache m_nscache;
private ModuleDBOps m_ops;
private File m_mod_dir; private File m_mod_dir;
private HashMap m_jar_to_module = new HashMap(); private HashMap m_jar_to_module = new HashMap();
private HashMap m_qname_to_module = new HashMap(); private HashMap m_qname_to_module = new HashMap();
private InstallServiceManager m_instservice;
private ServiceProvider m_install_services;
private ComponentShutdown m_shut1; private ComponentShutdown m_shut1;
private ComponentShutdown m_shut2; private ComponentShutdown m_shut2;
private ComponentShutdown m_shut3; private ComponentShutdown m_shut3;
@ -140,7 +153,7 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
public void initialize(Element config_root, ServiceProvider services) throws ConfigException public void initialize(Element config_root, ServiceProvider services) throws ConfigException
{ {
XMLLoader loader = XMLLoader.get(); XMLLoader loader = XMLLoader.get();
String mod_dir = null; String mod_dir = null, conn_name = null, nscache_name = null;
try try
{ // verify the right node name { // verify the right node name
loader.verifyNodeName(config_root,"object"); loader.verifyNodeName(config_root,"object");
@ -151,6 +164,12 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
// get the raw template directory // get the raw template directory
mod_dir = loader.getSubElementText(config_root,"module-directory"); mod_dir = loader.getSubElementText(config_root,"module-directory");
// get the database configuration connection
DOMElementHelper config_root_h = new DOMElementHelper(config_root);
Element elt = loader.getSubElement(config_root_h,"database");
conn_name = loader.getAttribute(elt,"connection");
nscache_name = loader.getAttribute(elt,"namespaces");
} // end try } // end try
catch (XMLLoadException e) catch (XMLLoadException e)
{ // error loading XML config data { // error loading XML config data
@ -158,6 +177,14 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
} // end catch } // end catch
// Get the database connection pool and namespace cache.
DBConnectionPool pool = GetObjectUtils.getDatabaseConnection(services,conn_name);
m_nscache =
(NamespaceCache)(GetObjectUtils.getDynamoComponent(services,NamespaceCache.class,nscache_name));
// Get the database operations object.
m_ops = ModuleDBOps.get(pool);
// Get the application container. // Get the application container.
ObjectProvider op = (ObjectProvider)(services.queryService(ObjectProvider.class)); ObjectProvider op = (ObjectProvider)(services.queryService(ObjectProvider.class));
m_appcon = (ApplicationContainer)(op.getObject(Namespaces.DYNAMO_APPLICATION_NAMESPACE,"__container__")); m_appcon = (ApplicationContainer)(op.getObject(Namespaces.DYNAMO_APPLICATION_NAMESPACE,"__container__"));
@ -172,6 +199,10 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
} // end if } // end if
// Get the install service manager and set up the install service provider.
m_instservice = new InstallServiceManager();
m_install_services = m_instservice.getServiceProvider(m_appcon.getInitServices());
// Hook this into the service providers. // Hook this into the service providers.
SingletonServiceProvider ssp = new SingletonServiceProvider("ModuleManager",ModuleOperations.class,this); SingletonServiceProvider ssp = new SingletonServiceProvider("ModuleManager",ModuleOperations.class,this);
HookServiceProviders hooker = (HookServiceProviders)(services.queryService(HookServiceProviders.class)); HookServiceProviders hooker = (HookServiceProviders)(services.queryService(HookServiceProviders.class));
@ -199,6 +230,7 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
ModuleLoader ml = (ModuleLoader)(tmp.removeFirst()); ModuleLoader ml = (ModuleLoader)(tmp.removeFirst());
if (ml.isInitialized()) if (ml.isInitialized())
ml.shutdown(); ml.shutdown();
ml.dispose();
} // end while } // end while
@ -209,6 +241,12 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
m_shut2 = null; m_shut2 = null;
m_shut1.shutdown(); m_shut1.shutdown();
m_shut1 = null; m_shut1 = null;
m_install_services = null;
m_instservice.dispose();
m_instservice = null;
m_ops.dispose();
m_ops = null;
m_nscache = null;
m_appcon = null; m_appcon = null;
} // end shutdown } // end shutdown
@ -254,7 +292,7 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
try try
{ // create a new ModuleLoader { // create a new ModuleLoader
rc = new ModuleLoader(mod_file,name); rc = new ModuleLoader(mod_file,name,m_ops,m_nscache,m_install_services);
} // end try } // end try
catch (MalformedURLException e) catch (MalformedURLException e)
@ -304,6 +342,7 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
m_qname_to_module.remove(ntry.getValue()); m_qname_to_module.remove(ntry.getValue());
if (ml.isInitialized()) if (ml.isInitialized())
ml.shutdown(); ml.shutdown();
ml.dispose();
} // end while } // end while
@ -340,4 +379,31 @@ public class ModuleManager implements NamedObject, ComponentInitialize, Componen
} // end listAllModuleNames } // end listAllModuleNames
public Set listInstalledModuleNames() throws DatabaseException
{
return m_ops.getInstalledModules();
} // end listInstalledModuleNames
public void loadInstalledModules() throws DatabaseException, ModuleException
{
Set set = m_ops.getInstalledModules();
logger.info("loadInstalledModules(): " + set.size() + " module(s) to load");
Iterator it = set.iterator();
while (it.hasNext())
{ // load each of the installed modules in turn
String mod_filename = (String)(it.next());
logger.info("loadInstalledModules(): loading " + mod_filename);
this.loadModule(mod_filename,true);
} // end while
} // end loadInstalledModules
public ComponentShutdown hookInstallServices(ServiceProvider sp)
{
return m_instservice.hook(sp);
} // end hookInstallServices
} // end class ModuleManager } // end class ModuleManager

View File

@ -18,8 +18,12 @@
package com.silverwrist.dynamo.module; package com.silverwrist.dynamo.module;
import java.util.List; import java.util.List;
import java.util.Set;
import com.silverwrist.dynamo.except.DatabaseException;
import com.silverwrist.dynamo.except.ModuleException; import com.silverwrist.dynamo.except.ModuleException;
import com.silverwrist.dynamo.iface.ComponentShutdown;
import com.silverwrist.dynamo.iface.Module; import com.silverwrist.dynamo.iface.Module;
import com.silverwrist.dynamo.iface.ServiceProvider;
public interface ModuleOperations public interface ModuleOperations
{ {
@ -31,4 +35,10 @@ public interface ModuleOperations
public List listAllModuleNames(); public List listAllModuleNames();
public Set listInstalledModuleNames() throws DatabaseException;
public void loadInstalledModules() throws DatabaseException, ModuleException;
public ComponentShutdown hookInstallServices(ServiceProvider sp);
} // end interface ModuleOperations } // end interface ModuleOperations

View File

@ -11,13 +11,13 @@
* *
* The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>, * The Initial Developer of the Original Code is Eric J. Bowersox <erbo@silcom.com>,
* for Silverwrist Design Studios. Portions created by Eric J. Bowersox are * for Silverwrist Design Studios. Portions created by Eric J. Bowersox are
* Copyright (C) 2002 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved. * Copyright (C) 2002-03 Eric J. Bowersox/Silverwrist Design Studios. All Rights Reserved.
* *
* Contributor(s): * Contributor(s):
*/ */
package com.silverwrist.dynamo.app; package com.silverwrist.dynamo.util;
class ServiceKey public class ServiceKey
{ {
/*-------------------------------------------------------------------------------- /*--------------------------------------------------------------------------------
* Attributes * Attributes
@ -32,7 +32,7 @@ class ServiceKey
*-------------------------------------------------------------------------------- *--------------------------------------------------------------------------------
*/ */
ServiceKey(Class klass, String serviceid) public ServiceKey(Class klass, String serviceid)
{ {
m_class = klass; m_class = klass;
m_serviceid = serviceid; m_serviceid = serviceid;

View File

@ -26,3 +26,5 @@ xtitle.mail=Mail Error
xtitle.script=Scripting Error xtitle.script=Scripting Error
xtitle.style=Style Sheet Error xtitle.style=Style Sheet Error
xtitle.valid=Validation Error xtitle.valid=Validation Error
module.dbfail=Unable to retrieve the installed module names from the database: {0}
module.initfail=Module initialization failure: {0}

View File

@ -25,6 +25,7 @@ import com.silverwrist.dynamo.db.UserPropertyTranslator;
import com.silverwrist.dynamo.db.UserPropertyTranslatorInstall; import com.silverwrist.dynamo.db.UserPropertyTranslatorInstall;
import com.silverwrist.dynamo.except.*; import com.silverwrist.dynamo.except.*;
import com.silverwrist.dynamo.iface.*; import com.silverwrist.dynamo.iface.*;
import com.silverwrist.dynamo.module.ModuleOperations;
import com.silverwrist.dynamo.util.*; import com.silverwrist.dynamo.util.*;
import com.silverwrist.dynamo.velocity.VelocityRendererConfig; import com.silverwrist.dynamo.velocity.VelocityRendererConfig;
import com.silverwrist.venice.VeniceNamespaces; import com.silverwrist.venice.VeniceNamespaces;
@ -112,6 +113,27 @@ public class VeniceApplication implements ComponentShutdown, Application, Styles
(VelocityRendererConfig)(services.queryService(VelocityRendererConfig.class)); (VelocityRendererConfig)(services.queryService(VelocityRendererConfig.class));
m_shutdown_list.addFirst(vrcon.addStandardComponentClass("datefmt",DateFormatterTopHalf.class)); m_shutdown_list.addFirst(vrcon.addStandardComponentClass("datefmt",DateFormatterTopHalf.class));
try
{ // Call down to the module manager to load and initialize all installed modules.
ModuleOperations modops = (ModuleOperations)(services.queryService(ModuleOperations.class));
modops.loadInstalledModules();
} // end try
catch (DatabaseException de)
{ // error in database
ConfigException ce = new ConfigException(VeniceApplication.class,"VeniceAppMessages","module.dbfail",de);
ce.setParameter(0,de.getMessage());
throw ce;
} // end catch
catch (ModuleException me)
{ // error initializing the modules
ConfigException ce = new ConfigException(VeniceApplication.class,"VeniceAppMessages","module.initfail",me);
ce.setParameter(0,me.getMessage());
throw ce;
} // end catch
// Done with initialization // Done with initialization
logger.info("Venice application '" + m_name + "' initialization done"); logger.info("Venice application '" + m_name + "' initialization done");