head	1.17;
access;
symbols
	TIGRIS_0_8_4:1.14.0.2
	NEWHELM:1.1.1.1
	TIGRIS_NOV_12_2000:1.1.1
	OLDHELM:1.8.0.2
	TIGRIS_NOV_11_2000:1.8
	TIGRIS_SEP_13_2000:1.4.0.2
	TIGRIS_BASELINE:1.5;
locks; strict;
comment	@# @;


1.17
date	2000.12.14.23.43.53;	author dlr;	state dead;
branches;
next	1.16;

1.16
date	2000.12.13.22.34.07;	author dlr;	state Exp;
branches;
next	1.15;

1.15
date	2000.12.13.22.13.40;	author dlr;	state Exp;
branches;
next	1.14;

1.14
date	2000.11.30.23.56.41;	author leonardr;	state Exp;
branches;
next	1.13;

1.13
date	2000.11.17.18.44.32;	author leonardr;	state Exp;
branches;
next	1.12;

1.12
date	2000.11.17.18.33.34;	author edk;	state Exp;
branches;
next	1.11;

1.11
date	2000.11.17.00.29.21;	author leonardr;	state Exp;
branches;
next	1.10;

1.10
date	2000.11.15.19.39.16;	author leonardr;	state Exp;
branches;
next	1.9;

1.9
date	2000.11.12.22.57.31;	author dlr;	state Exp;
branches;
next	1.8;

1.8
date	2000.10.18.06.20.54;	author dlr;	state Exp;
branches;
next	1.7;

1.7
date	2000.10.03.21.34.56;	author leonardr;	state Exp;
branches;
next	1.6;

1.6
date	2000.09.29.19.55.46;	author dlr;	state Exp;
branches;
next	1.5;

1.5
date	2000.09.21.19.44.07;	author kmaples;	state Exp;
branches;
next	1.4;

1.4
date	2000.09.20.03.13.16;	author brian;	state Exp;
branches;
next	1.3;

1.3
date	2000.04.18.00.10.34;	author jrobbins;	state Exp;
branches;
next	1.2;

1.2
date	2000.02.03.04.21.32;	author jrobbins;	state Exp;
branches;
next	1.1;

1.1
date	2000.01.30.01.59.38;	author jrobbins;	state Exp;
branches
	1.1.1.1;
next	;

1.1.1.1
date	2000.11.12.21.14.59;	author dlr;	state Exp;
branches;
next	;


desc
@@


1.17
log
@No longer used.
@
text
@/* ================================================================
 * Copyright (c) 2000 CollabNet.  All rights reserved.
 * 
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met:
 * 
 * 1. Redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer.
 * 
 * 2. Redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the distribution.
 * 
 * 3. The end-user documentation included with the redistribution, if
 * any, must include the following acknowlegement: "This product includes
 * software developed by Collab.Net (http://www.Collab.Net/)."
 * Alternately, this acknowlegement may appear in the software itself, if
 * and wherever such third-party acknowlegements normally appear.
 * 
 * 4. The hosted project names must not be used to endorse or promote
 * products derived from this software without prior written
 * permission. For written permission, please contact info@@collab.net.
 * 
 * 5. Products derived from this software may not use the "Tigris" name
 * nor may "Tigris" appear in their names without prior written
 * permission of Collab.Net.
 * 
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
 * IN NO EVENT SHALL COLLAB.NET OR ITS CONTRIBUTORS BE LIABLE FOR ANY
 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
 * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 * ====================================================================
 * 
 * This software consists of voluntary contributions made by many
 * individuals on behalf of Collab.Net.
 */


package org.tigris.helm.database;

import java.sql.*;

import org.webmacro.util.*;

import com.workingdogs.village.*;

import org.joist.util.*;
import org.joist.database.TableManager;
import org.joist.database.DataManager;
import org.joist.database.JoistDatabaseException;

import org.tigris.helm.DoesNotExist;
import org.tigris.helm.tool.TigrisUpdate;
import org.tigris.helm.database.ProjectManager;
import org.tigris.helm.project.Project;

/**
 * This class deals with modules, and manages the proper database
 * activities related to their creation and deletion, ensuring
 * database integrity. 
 *
 * @@author <a href="mailto:akosut@@leland.stanford.edu">Alexi Kosut</a>
 * @@author <a href="mailto:jrobbins@@collab.net">Jason Robbins</a>
 * @@author <a href="mailto:leonardr@@collab.net">Leonard Richardson</a>
 * @@author <a href="mailto:dlr@@collab.net">Daniel Rall</a>
 */
public class ModuleManager extends TableManager
{
    /**
     * Open the log file.
     */
    private static Log log = new Log("modMgr", "ModuleManager");

    /**
     * Whether to log debugging information.
     */
    private static final boolean debug = true;

    /**
     * The name of the database table that this <code>TableManager</code> 
     * manages.
     */
    public static final String TABLE_NAME = "HELM_MODULE";

    /**
     * The primary database key field.
     */
    public static final String MODULE_ID = "MODULE_ID";

    /**
     * The field containing the project with which this module is
     * associated.  
     */
    public static final String PROJECT_ID = "PROJECT_ID";

    /**
     * The module's name field.
     */
    public static final String MODULE_NAME = "NAME";

    /**
     * The module's description field.
     */
    public static final String MODULE_DESCRIPTION = "DESCRIPTION";

    /**
     * Field indicating whether the module is a web module.  Used when 
     * deciding whether to publish to the web site after a commit.
     */
    public static final String MODULE_IS_WEB = "IS_WEB";

    /**
     * Creates a new instance.
     *
     * @@param dataMgr The associated <code>DataManager</code>.
     */
    public ModuleManager(DataManager dataMgr)
    {
        super(dataMgr);
    }
    
    /**
     * Updates an existing module or adds a new module to the database 
     * (depending on whether given a <code>moduleID</code> or not).
     *
     * TODO: Updating a module via this method doesn't yet call the
     * scripts.
     *
     * @@param connection  The JDBC database connection to use.
     * @@param moduleID    The database key of the module to update, or 
     *                     <code>null</code> if the module is new.
     * @@param projectID   The ID of the project associated with the module
     * @@param module      The name of the module
     * @@param description A brief description of the module
     * @@param isWeb       Whether or not the module contains Web content
     *
     * @@return	          The system-assigned module ID for the module.
     *
     * @@exception SQLException
     * @@exception DataSetException
     */
    public Record updateModule (Connection connection, String moduleID,
                                String projectID, String name, 
                                String description, boolean isWeb)
	throws SQLException, DataSetException
    {
	Record module = null;

        String action = 
            (moduleID == null ? "Adding Module: " : "Updating Module: ");
        TableDataSet modules = null;
	try
	{
            modules = new TableDataSet(connection, TABLE_NAME,
                    new KeyDef().addAttrib(MODULE_ID));
            if (moduleID != null) {
                modules.where(buildWhereClause(moduleID, projectID, name,
                            description, isWeb==true?"1":"0"));
                modules.fetchRecords();
                if (debug) log.info("Updating record for existing module");
                module = modules.getRecord(0);
            } else {
                if (debug) log.info("Adding record for new module");
                module = modules.addRecord();
            }

            module.setValue(PROJECT_ID, projectID);
            module.setValue(MODULE_NAME, name);
            module.setValue(MODULE_DESCRIPTION, description);
            module.setValue(MODULE_IS_WEB, isWeb);
            module.save();
            if (moduleID == null)
            {
                // NOTE: There is no way to refresh a Village Record which has
                // been created using TableDataSet.addRecord().
                module.setValue(MODULE_ID, getLastInsertedID(connection)
                                .toString());
            }
        }
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.warning(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.warning(action + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
        
	return module;
    }

    /**
     * Deletes an existing module from the database
     *
     * @@param	  connection    the JDBC database connection
     * @@param	  moduleID       the ID of the module to delete
     * @@exception SQLException
     */
    public void  deleteModule (Connection connection, String moduleID)
	throws SQLException, DataSetException, JoistDatabaseException,
               DoesNotExist
    {
        String action = "Deleting module: ";
	try
	{
            Record r = getModule(connection, moduleID);
            String projectID = r.getValue(ModuleManager.PROJECT_ID).toString();
        
            String moduleName = r.getValue(MODULE_NAME).toString();
            r.markToBeDeleted();
            r.save();

            Project project = new Project(connection, getDataManager(),
                                          projectID);
            TigrisUpdate.deleteModule(connection, getDataManager(), null, 
                                      project, moduleName);
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.error(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.error(action + e.getMessage());
	    throw e;
	}
    }

    /**
     * Deletes all of a project's modules.
     *
     * @@param	  connection    the JDBC database connection
     * @@param	  projectID     the ID of the project to clear out
     * @@exception SQLException
     * @@exception DataSetException
     */
    public void  deleteModulesForProject (Connection connection, String 
                                          projectID)
	throws SQLException, DataSetException, JoistDatabaseException,
               DoesNotExist
    {
        String action = "Deleting Modules for Project: ";       

        String moduleName = null;
	TableDataSet modules = null;
	try
	{
            KeyDef kd = new KeyDef().addAttrib(MODULE_ID);
	    modules = new TableDataSet(connection, TABLE_NAME,kd);
	    modules.where(buildWhereClause(null,projectID,null,null,null));
	    modules.fetchRecords();
            for (int i = 0; i < modules.size(); i++)
	    {
                Record r = modules.getRecord(i);
                moduleName = r.getValue(ModuleManager.MODULE_NAME).toString();
                r.markToBeDeleted();
                r.save();

                Project p = new Project(connection, getDataManager(),
                                        projectID);
                TigrisUpdate.deleteModule(connection, getDataManager(), null,
                                          p, moduleName);
	    }
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.error(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.error(action + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
    }

    /**
     *  Retrieves a module with known ID from the database.
     *
     * @@param	connection    A JDBC database connection
     * @@param	moduleID       The moduleID to obtain 
     * @@return	 a Record
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public Record getModule (Connection connection, String moduleID)
	throws SQLException, DataSetException, JoistDatabaseException
    {
        TableDataSet modules = 
            getModules(connection, moduleID, null, null, null, null);
        if (modules != null && modules.containsRecord(0))
        {
            return modules.getRecord(0);
        }
        else
        {
            throw new JoistDatabaseException ("No such module: " + moduleID);
        }
    }

    /**
     * Retrieves the ID for a module with known name
     *
     * @@param	connection    A JDBC database connection
     * @@param	moduleName     The module name to identify
     * @@return	 a String
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public String getModuleID (Connection connection, String moduleName)
	throws SQLException, DataSetException, JoistDatabaseException
    {
        TableDataSet modules = 
            getModules(connection, null, null, moduleName, null, null);
        if (modules.containsRecord(0))
        {
            return modules.getRecord(0).getValue(MODULE_ID).asString();
        }
        else
        {
            throw new JoistDatabaseException ("No such module: " + moduleName);
        }
    }

    /**
     *  Retrieves a list of modules for a given project
     *
     * @@param	connection    A JDBC database connection
     * @@param   projectID     A project ID
     * @@return	 a DataSet
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public final DataSet getModulesForProject (Connection connection, 
                                               String projectID)
	throws SQLException, DataSetException
    {
        return getModules(connection, null, projectID, null, null, null);
    }    

    /**
     *  Retrieves modules by any of their fields
     *
     * @@param	connection    A JDBC database connection
     * @@param   moduleID      A module ID (can be null)
     * @@param   projectID     A project ID (can be null)
     * @@param   name          A module name (can be null)
     * @@param   description   A module description (can be null)
     * @@param   isWeb         "Y", "N", or null
     * @@return	 a DataSet
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public TableDataSet getModules(Connection connection,
                                   String moduleID,
                                   String projectID,
                                   String name,
                                   String description,
                                   String isWeb)
        throws SQLException, DataSetException
    {
        TableDataSet modules = null;

        try
        {
            modules = new TableDataSet(connection, TABLE_NAME);
            modules.where(buildWhereClause(moduleID, projectID, name, 
                                           description, isWeb));
            modules.fetchRecords();
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.error("Getting Module: " + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.error("Getting Module: " + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}

        return modules;
    }

    /**
     * Creates a SQL <code>where</code> clause.
     */
    protected static String buildWhereClause (String moduleID, 
                                              String projectID,
                                              String name,
                                              String description,
                                              String isWeb)
    {
        StringBuffer whereClause = new StringBuffer();
        boolean firstClause = true;
        
        if (moduleID != null)
        {
            whereClause.append(MODULE_ID).append('=').append(moduleID);
            firstClause = false;
        }

        if (projectID != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(PROJECT_ID).append('=').append(projectID);
        }

        if (name != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(MODULE_NAME).append('=');
            whereClause.append(escapeAndQuoteSQL(name));
        }

        if (description != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(MODULE_DESCRIPTION).append('=');
            whereClause.append
                (escapeAndQuoteSQL(description));
        }

        if (isWeb != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            
            whereClause.append(MODULE_IS_WEB).append('=');
            whereClause.append(escapeAndQuoteSQL(isWeb));
        }

        return whereClause.toString();
    }
}
@


1.16
log
@ugh, messy
@
text
@@


1.15
log
@Debugging trace cleanup and JavaDoc addition.
@
text
@d146 1
a146 1
     * @@return	         The system-assigned module ID for the module.
d148 1
a148 1
     * @@exception	SQLException
@


1.14
log
@Mega patch which makes script data persistent and which provides a general framework for tasks to be run (which will be used by anzu eventually)
@
text
@d116 2
a117 1
     * The module "is Web module" field.
a130 1
    
d230 2
a231 1
            Project project = new Project(connection, getDataManager(), projectID);
d238 1
a238 1
	    if (debug) log.debug(action + e.getMessage());
d244 1
a244 1
	    if (debug) log.debug(action + e.getMessage());
d279 2
a280 1
                Project p = new Project(connection, getDataManager(), projectID);
d288 1
a288 1
	    if (debug) log.debug(action + e.getMessage());
d294 1
a294 1
	    if (debug) log.debug(action + e.getMessage());
d400 1
a400 1
	    if (debug) log.debug("Getting Module: " + e.getMessage());
d406 1
a406 1
	    if (debug) log.debug("Getting Module: " + e.getMessage());
@


1.13
log
@Can't proprietarize approved open source projects.
@
text
@d64 1
a220 5
        String projectID = getModule(connection, moduleID)
            .getValue(ModuleManager.PROJECT_ID).toString();
        
        String moduleName = null;
	TableDataSet modules = null;
d223 10
a232 13
	    modules = new TableDataSet(connection, TABLE_NAME);
	    modules.where(buildWhereClause(moduleID,null,null,null,null));
	    modules.fetchRecords();
	    if (modules.containsRecord(0)) 
	    {
                Record r = modules.getRecord(0);
                moduleName = r.getValue(MODULE_NAME).toString();
                r.markToBeDeleted();
                r.save();

                TigrisUpdate.deleteModule(getDataManager(), connection, 
                                          projectID, moduleName);
	    }
a245 4
	finally
	{
	    registerToClose(modules);
	}
d278 3
a280 2
                TigrisUpdate.deleteModule(getDataManager(), connection, 
                                          projectID, moduleName);
@


1.12
log
@we can't call getLastInsertedID() until after we've saved this record ...
@
text
@d186 1
a186 9
            }        

            /* TODO: How is this to be handled?
               if (isWeb)
               {
               s.executeUpdate("INSERT INTO module_website (project,module," +
               "vhost,root) VALUES ('" + project + "','www','Y','/')");
               }
            */
@


1.11
log
@Made the TigrisUpdate stuff saner with the use of business objects.
@
text
@a174 8
            if (moduleID == null)
            {
                // NOTE: There is no way to refresh a Village Record which has
                // been created using TableDataSet.addRecord().
                Integer newID = getLastInsertedID(connection);
                module.setValue(MODULE_ID, newID.toString());
            }        

@


1.10
log
@Modernized ProjectEdit; began to get rid of superfluous UpdateException handling.
@
text
@d61 1
d232 2
a233 1
	throws SQLException, DataSetException, JoistDatabaseException
d285 2
a286 1
	throws SQLException, DataSetException, JoistDatabaseException
@


1.9
log
@Resolved merge conflicts.
@
text
@a61 1
import org.tigris.helm.tool.UpdateException;
d231 1
a231 2
	throws SQLException, DataSetException, JoistDatabaseException, 
               UpdateException
d283 1
a283 2
	throws SQLException, DataSetException, JoistDatabaseException, 
               UpdateException
a312 6
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	catch (UpdateException e)
@


1.8
log
@Applied patch by Tod Matola <matola@@oclc.org> to correct SQL
generation.  Thanks Tod.
@
text
@d50 1
a50 6
import org.webmacro.servlet.*;
import org.webmacro.engine.*;
import org.webmacro.broker.*;

import javax.servlet.*;
import javax.servlet.http.*;
d52 1
a52 3
import com.sun.java.util.collections.ArrayList;
import com.sun.java.util.collections.List;
import java.sql.*;
d59 1
d63 1
a63 3


//TODO: Make ModuleManager look more like a TableManager
d70 4
d75 54
a128 6
public class ModuleManager extends TableManager {
  /**
   * This exception indicates that the given module already exists.
   */
  public static class AlreadyExists extends Exception {
    private String project, module;
d131 15
a145 1
     * Create a new "project already exists" exception
d147 2
a148 2
     * @@param project the project the module is in
     * @@param module the module that already exists
d150 72
a221 4
    public AlreadyExists(String project, String module) {
      super("Project " + project + '/' + module + " already exists");
      this.project = project;
      this.module = module;
d225 5
a229 1
     * Return the project of the module
d231 42
a272 2
    public String getProject() {
      return project;
d276 6
a281 1
     * The module that already exists
d283 48
a330 2
    public String getModule() {
      return module;
a331 1
  } /* end class AlreadyExists */
d333 23
a355 5
  /**
   * A module entry from the Tigris database
   */
  public static class Entry {
    private String project, module, longname;
d358 7
a364 5
     * Create a new module entry with the given module and long name
     * 
     * @@param project the project this module belongs to
     * @@param module the module
     * @@param longname a longer name for the module, or null if none
d366 13
a378 5
    public Entry(String project, String module,
                 String longname) {
      this.project = project;
      this.module = module;
      this.longname = (longname != null) ? longname : module;
d381 15
a395 3
    public String getProject() {
      return project;
    }
d397 46
a442 3
    public String getModule() {
      return module;
    }
d444 1
a444 2
    public String getLongName() {
      return longname;
a445 1
  } /* end class Entry */
d447 62
d510 1
a510 104
  /** Constructor */
  public ModuleManager(DataManager dataMgr) {
    super(dataMgr);
  }
    
    
  /**
   * Add a new module to the database. This should set up all the
   * tables and such that any other database accessor will expect to
   * find.
   *
   * @@param tigris the Tigris context
   * @@param project the project to add the module to
   * @@param module the name to give to the module in the project
   * @@param longName a longer, descriptive, name
   *
   * @@exception SQLException if there was a database error
   * @@exception UpdateException if the update program could not be run
   * @@exception AlreadyExists if a module by this name already exists
   */
  public static void addModule(Connection connection, String domain,
			       String project, String module, String longName,
                               boolean isWeb)
    throws SQLException, UpdateException, AlreadyExists {
    addModuleNoUpdate(connection, domain, project, module, longName, isWeb);
    TigrisUpdate.addModule(connection, domain, project, module, longName, isWeb);
  }

  /**
   * Add a module, like addModule(), but do not run the update
   * program afterwards. Useful when adding a module as part
   * of a larger context of database modification. Be sure and call
   * TigrisUpdate.update() when done.
   *
   * @@see TigrisUpdate
   */
  static void addModuleNoUpdate(Connection connection, String domain,
				String project, String module, 
				String longName, boolean isWeb)
    throws SQLException, AlreadyExists {


    Statement s = connection.createStatement();
	
    // Check to see if the module does not already exist
    ResultSet r = s.executeQuery("SELECT module FROM "
                                 + "project_modules WHERE project = '"
                                 + project + "' AND module = '" + module
                                 + "'");
	
    // If any rows are found, the module is already taken
    if (r.next())
      throw new AlreadyExists(project, module);

    s.executeUpdate("INSERT INTO project_modules "
                    + "(project,module,long_name) VALUES ('"
                    + project + "','" + module + "','" + longName
                    + "')");
  }

  /**
   * Remove a module from the database.
   *
   * @@param tigris The Tigris context to operate in
   * @@param project The name of the project the module resides in
   * @@param module The name of the module to delete
   *
   * @@exception SQLException if there was a database error
   * @@exception UpdateException if the update program could not be run
   */
  public static void deleteModule(Connection connection, String project,
                                  String module)
    throws SQLException, UpdateException {
    Statement s = connection.createStatement();
	
    // Delete project from all rows
    String whereQuery = " WHERE project = '" + project
      + "' AND module = '" + module + '\'';
    s.executeUpdate("DELETE FROM project_modules" + whereQuery);
    s.executeUpdate("DELETE FROM module_website" + whereQuery);
    s.executeUpdate("DELETE FROM module_privs" + whereQuery);
	
    // Update the config files based on the database
    TigrisUpdate.update(connection);
  }

  /**
   * Retrive a list of modules from the database.
   *
   * @@param tigris the Tigris context
   * @@param project the project to list modules from
   * @@return a List of Module.Entry objects representing all the modules
   *         in the project, ordered alphabetically by project name
   */
  public static List getModules(Connection connection, String project)
    throws SQLException {
    ArrayList modules = new ArrayList();

    Statement s = connection.createStatement();
    ResultSet r = s.executeQuery("SELECT module,long_name FROM "
                                 + "project_modules WHERE project = '"
                                 + project + "' ORDER BY module");
    while (r.next()) {
      modules.add(new Entry(project, r.getString(1), r.getString(2)));
d512 1
a512 5

    return modules;
  }

} /* end class ModuleManager */
@


1.7
log
@Got rid of privateModule altogether.
@
text
@d204 1
a204 1
                    + "'," + ")");
@


1.6
log
@Collab.Net --> CollabNet in copyright.
@
text
@a161 3
   * @@param privateModule whether or not the module should be
   *        private to the project (private modules require special
   *        privileges to access, not just project privileges)
d169 1
a169 1
                               boolean isWeb, boolean privateModule)
d171 2
a172 2
    addModuleNoUpdate(connection, domain, project, module, longName, isWeb, privateModule);
    TigrisUpdate.addModule(connection, domain, project, module, longName, isWeb, privateModule);
d185 1
a185 2
				String longName, boolean isWeb,
				boolean privateModule)
d202 1
a202 1
                    + "(project,module,long_name,private) VALUES ('"
d204 1
a204 1
                    + "'," + (privateModule ? "'Y'" : "'N'") + ")");
@


1.5
log
@Added SelfServeProjectAdd servlet, factoring out project creation
logic into ProjectCreator tool class. Big update to TigrisUpdate to
make it run kmaples' Perl scripts directly. Also updates to
{Project,Module}{Add,Manager}.
@
text
@d2 1
a2 1
 * Copyright (c) 2000 Collab.Net.  All rights reserved.
@


1.4
log
@
Obtained from:
Submitted by:
Reviewed by:

Moved from org.helm to org.tigris.helm
Moved from org/helm to org/tigris/helm

perl -pi.bak -e, how I love thee

note: this update was done POST-CVS-REPOSITORY surgury.  In order to
get this right, you may need to remove the directories

$CVSROOT/helm/java/org/helm
$CVSROOT/helm/data/htdoc/look/www/org/helm
$CVSROOT/helm/templates/org/helm

before doing the "CVS update" call, since those directories don't
exist anymore and CVS will try to create lockfiles for you in them,
giving you an error.
@
text
@d170 3
a172 3
  public static void addModule(Connection connection, String project,
                               String module, String longName,
                               boolean privateModule)
d174 2
a175 2
    addModuleNoUpdate(connection, project, module, longName, privateModule);
    TigrisUpdate.update(connection);
d186 4
a189 3
  static void addModuleNoUpdate(Connection connection, String project,
                                String module, String longName,
                                boolean privateModule)
@


1.3
log
@switched from collections2.jar to collections.jar
@
text
@d48 1
a48 1
package org.helm.database;
d67 2
a68 2
import org.helm.tool.TigrisUpdate;
import org.helm.tool.UpdateException;
@


1.2
log
@Added tigris.org license
PR:
Obtained from:
Submitted by:
Reviewed by:
@
text
@d57 2
a58 2
import java.util.ArrayList;
import java.util.List;
@


1.1
log
@initial checking
@
text
@d1 46
a46 1
// Copyright (c) 2000 Collab.Net, Inc. All Rights Reserved.
@


1.1.1.1
log
@Merging newhelm tree into helm, as per IZ issue #557.  Previous major version of helm is tagged TIGRIS_NOV_11_2000.
@
text
@d1 3
a3 45
/* ================================================================
 * Copyright (c) 2000 CollabNet.  All rights reserved.
 * 
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met:
 * 
 * 1. Redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer.
 * 
 * 2. Redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the distribution.
 * 
 * 3. The end-user documentation included with the redistribution, if
 * any, must include the following acknowlegement: "This product includes
 * software developed by Collab.Net (http://www.Collab.Net/)."
 * Alternately, this acknowlegement may appear in the software itself, if
 * and wherever such third-party acknowlegements normally appear.
 * 
 * 4. The hosted project names must not be used to endorse or promote
 * products derived from this software without prior written
 * permission. For written permission, please contact info@@collab.net.
 * 
 * 5. Products derived from this software may not use the "Tigris" name
 * nor may "Tigris" appear in their names without prior written
 * permission of Collab.Net.
 * 
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
 * IN NO EVENT SHALL COLLAB.NET OR ITS CONTRIBUTORS BE LIABLE FOR ANY
 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
 * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 * ====================================================================
 * 
 * This software consists of voluntary contributions made by many
 * individuals on behalf of Collab.Net.
 */
d5 3
d9 2
a10 1
package org.tigris.helm.database;
d12 2
a15 2
import org.webmacro.util.*;

a20 1
import org.joist.database.JoistDatabaseException;
d22 5
a26 3
import org.tigris.helm.tool.TigrisUpdate;
import org.tigris.helm.tool.UpdateException;
import org.tigris.helm.database.ProjectManager;
a32 4
 * @@author <a href="mailto:akosut@@leland.stanford.edu">Alexi Kosut</a>
 * @@author <a href="mailto:jrobbins@@collab.net">Jason Robbins</a>
 * @@author <a href="mailto:leonardr@@collab.net">Leonard Richardson</a>
 * @@author <a href="mailto:dlr@@collab.net">Daniel Rall</a>
d34 6
a39 54
public class ModuleManager extends TableManager
{
    /**
     * Open the log file.
     */
    private static Log log = new Log("modMgr", "ModuleManager");

    /**
     * Whether to log debugging information.
     */
    private static final boolean debug = true;

    /**
     * The name of the database table that this <code>TableManager</code> 
     * manages.
     */
    public static final String TABLE_NAME = "HELM_MODULE";

    /**
     * The primary database key field.
     */
    public static final String MODULE_ID = "MODULE_ID";

    /**
     * The field containing the project with which this module is
     * associated.  
     */
    public static final String PROJECT_ID = "PROJECT_ID";

    /**
     * The module's name field.
     */
    public static final String MODULE_NAME = "NAME";

    /**
     * The module's description field.
     */
    public static final String MODULE_DESCRIPTION = "DESCRIPTION";

    /**
     * The module "is Web module" field.
     */
    public static final String MODULE_IS_WEB = "IS_WEB";

    /**
     * Creates a new instance.
     *
     * @@param dataMgr The associated <code>DataManager</code>.
     */
    public ModuleManager(DataManager dataMgr)
    {
        super(dataMgr);
    }
    
d42 1
a42 13
     * Updates an existing module or adds a new module to the database 
     * (depending on whether given a <code>moduleID</code> or not).
     *
     * TODO: Updating a module via this method doesn't yet call the
     * scripts.
     *
     * @@param connection  The JDBC database connection to use.
     * @@param moduleID    The database key of the module to update, or 
     *                     <code>null</code> if the module is new.
     * @@param projectID   The ID of the project associated with the module
     * @@param module      The name of the module
     * @@param description A brief description of the module
     * @@param isWeb       Whether or not the module contains Web content
d44 2
a45 4
     * @@return	         The system-assigned module ID for the module.
     *
     * @@exception	SQLException
     * @@exception DataSetException
d47 4
a50 72
    public Record updateModule (Connection connection, String moduleID,
                                String projectID, String name, 
                                String description, boolean isWeb)
	throws SQLException, DataSetException
    {
	Record module = null;

        String action = 
            (moduleID == null ? "Adding Module: " : "Updating Module: ");
        TableDataSet modules = null;
	try
	{
            modules = new TableDataSet(connection, TABLE_NAME,
                    new KeyDef().addAttrib(MODULE_ID));
            if (moduleID != null) {
                modules.where(buildWhereClause(moduleID, projectID, name,
                            description, isWeb==true?"1":"0"));
                modules.fetchRecords();
                if (debug) log.info("Updating record for existing module");
                module = modules.getRecord(0);
            } else {
                if (debug) log.info("Adding record for new module");
                module = modules.addRecord();
            }

            if (moduleID == null)
            {
                // NOTE: There is no way to refresh a Village Record which has
                // been created using TableDataSet.addRecord().
                Integer newID = getLastInsertedID(connection);
                module.setValue(MODULE_ID, newID.toString());
            }        

            module.setValue(PROJECT_ID, projectID);
            module.setValue(MODULE_NAME, name);
            module.setValue(MODULE_DESCRIPTION, description);
            module.setValue(MODULE_IS_WEB, isWeb);
            module.save();
            if (moduleID == null)
            {
                // NOTE: There is no way to refresh a Village Record which has
                // been created using TableDataSet.addRecord().
                module.setValue(MODULE_ID, getLastInsertedID(connection)
                                .toString());
            }        

            /* TODO: How is this to be handled?
               if (isWeb)
               {
               s.executeUpdate("INSERT INTO module_website (project,module," +
               "vhost,root) VALUES ('" + project + "','www','Y','/')");
               }
            */
        }
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.warning(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.warning(action + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
        
	return module;
d54 1
a54 5
     * Deletes an existing module from the database
     *
     * @@param	  connection    the JDBC database connection
     * @@param	  moduleID       the ID of the module to delete
     * @@exception SQLException
d56 2
a57 42
    public void  deleteModule (Connection connection, String moduleID)
	throws SQLException, DataSetException, JoistDatabaseException, 
               UpdateException
    {
        String action = "Deleting module: ";
        String projectID = getModule(connection, moduleID)
            .getValue(ModuleManager.PROJECT_ID).toString();
        
        String moduleName = null;
	TableDataSet modules = null;
	try
	{
	    modules = new TableDataSet(connection, TABLE_NAME);
	    modules.where(buildWhereClause(moduleID,null,null,null,null));
	    modules.fetchRecords();
	    if (modules.containsRecord(0)) 
	    {
                Record r = modules.getRecord(0);
                moduleName = r.getValue(MODULE_NAME).toString();
                r.markToBeDeleted();
                r.save();

                TigrisUpdate.deleteModule(getDataManager(), connection, 
                                          projectID, moduleName);
	    }
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
d61 1
a61 6
     * Deletes all of a project's modules.
     *
     * @@param	  connection    the JDBC database connection
     * @@param	  projectID     the ID of the project to clear out
     * @@exception SQLException
     * @@exception DataSetException
d63 2
a64 48
    public void  deleteModulesForProject (Connection connection, String 
                                          projectID)
	throws SQLException, DataSetException, JoistDatabaseException, 
               UpdateException
    {
        String action = "Deleting Modules for Project: ";       

        String moduleName = null;
	TableDataSet modules = null;
	try
	{
            KeyDef kd = new KeyDef().addAttrib(MODULE_ID);
	    modules = new TableDataSet(connection, TABLE_NAME,kd);
	    modules.where(buildWhereClause(null,projectID,null,null,null));
	    modules.fetchRecords();
            for (int i = 0; i < modules.size(); i++)
	    {
                Record r = modules.getRecord(i);
                moduleName = r.getValue(ModuleManager.MODULE_NAME).toString();
                r.markToBeDeleted();
                r.save();

                TigrisUpdate.deleteModule(getDataManager(), connection, 
                                          projectID, moduleName);
	    }
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	catch (UpdateException e)
	{
	    log.exception(e);
	    if (debug) log.debug(action + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
d66 7
d75 5
a79 7
     *  Retrieves a module with known ID from the database.
     *
     * @@param	connection    A JDBC database connection
     * @@param	moduleID       The moduleID to obtain 
     * @@return	 a Record
     * @@exception	SQLException
     * @@exception	DataSetException
d81 5
a85 13
    public Record getModule (Connection connection, String moduleID)
	throws SQLException, DataSetException, JoistDatabaseException
    {
        TableDataSet modules = 
            getModules(connection, moduleID, null, null, null, null);
        if (modules != null && modules.containsRecord(0))
        {
            return modules.getRecord(0);
        }
        else
        {
            throw new JoistDatabaseException ("No such module: " + moduleID);
        }
d88 2
a89 22
    /**
     * Retrieves the ID for a module with known name
     *
     * @@param	connection    A JDBC database connection
     * @@param	moduleName     The module name to identify
     * @@return	 a String
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public String getModuleID (Connection connection, String moduleName)
	throws SQLException, DataSetException, JoistDatabaseException
    {
        TableDataSet modules = 
            getModules(connection, null, null, moduleName, null, null);
        if (modules.containsRecord(0))
        {
            return modules.getRecord(0).getValue(MODULE_ID).asString();
        }
        else
        {
            throw new JoistDatabaseException ("No such module: " + moduleName);
        }
d92 3
a94 62
    /**
     *  Retrieves a list of modules for a given project
     *
     * @@param	connection    A JDBC database connection
     * @@param   projectID     A project ID
     * @@return	 a DataSet
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public final DataSet getModulesForProject (Connection connection, 
                                               String projectID)
	throws SQLException, DataSetException
    {
        return getModules(connection, null, projectID, null, null, null);
    }    

    /**
     *  Retrieves modules by any of their fields
     *
     * @@param	connection    A JDBC database connection
     * @@param   moduleID      A module ID (can be null)
     * @@param   projectID     A project ID (can be null)
     * @@param   name          A module name (can be null)
     * @@param   description   A module description (can be null)
     * @@param   isWeb         "Y", "N", or null
     * @@return	 a DataSet
     * @@exception	SQLException
     * @@exception	DataSetException
     */
    public TableDataSet getModules(Connection connection,
                                   String moduleID,
                                   String projectID,
                                   String name,
                                   String description,
                                   String isWeb)
        throws SQLException, DataSetException
    {
        TableDataSet modules = null;

        try
        {
            modules = new TableDataSet(connection, TABLE_NAME);
            modules.where(buildWhereClause(moduleID, projectID, name, 
                                           description, isWeb));
            modules.fetchRecords();
	}
	catch (DataSetException e)
	{
	    log.exception(e);
	    if (debug) log.debug("Getting Module: " + e.getMessage());
	    throw e;
	}
	catch (SQLException e)
	{
	    log.exception(e);
	    if (debug) log.debug("Getting Module: " + e.getMessage());
	    throw e;
	}
	finally
	{
	    registerToClose(modules);
	}
d96 2
a97 1
        return modules;
d99 1
a100 62
    /**
     * Creates a SQL <code>where</code> clause.
     */
    protected static String buildWhereClause (String moduleID, 
                                              String projectID,
                                              String name,
                                              String description,
                                              String isWeb)
    {
        StringBuffer whereClause = new StringBuffer();
        boolean firstClause = true;
        
        if (moduleID != null)
        {
            whereClause.append(MODULE_ID).append('=').append(moduleID);
            firstClause = false;
        }

        if (projectID != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(PROJECT_ID).append('=').append(projectID);
        }

        if (name != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(MODULE_NAME).append('=');
            whereClause.append(escapeAndQuoteSQL(name));
        }

        if (description != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            whereClause.append(MODULE_DESCRIPTION).append('=');
            whereClause.append
                (escapeAndQuoteSQL(description));
        }

        if (isWeb != null)
        {
            if (!firstClause)
            {
                whereClause.append(" AND ");
            }
            firstClause = false;
            
            whereClause.append(MODULE_IS_WEB).append('=');
            whereClause.append(escapeAndQuoteSQL(isWeb));
        }
d102 107
a208 1
        return whereClause.toString();
d211 4
a214 1
}
@


