]> git.aero2k.de Git - tmp/jakarta-migration.git/commitdiff
CSPACE-448: ID Service returns 404, not 400, when an ID Generator is not found. Curre...
authorAron Roberts <aron@socrates.berkeley.edu>
Thu, 17 Sep 2009 03:19:21 +0000 (03:19 +0000)
committerAron Roberts <aron@socrates.berkeley.edu>
Thu, 17 Sep 2009 03:19:21 +0000 (03:19 +0000)
services/id/service/src/main/java/org/collectionspace/services/id/IDResource.java
services/id/service/src/main/java/org/collectionspace/services/id/IDService.java
services/id/service/src/main/java/org/collectionspace/services/id/IDServiceJdbcImpl.java
services/id/service/src/test/java/org/collectionspace/services/id/test/IDServiceJdbcImplTest.java

index 90932fbf0c9f98ff1bc3e2748de83931116e98e6..968e3be8cfd4ecde2169fb1bdb41b12b37f746e1 100644 (file)
@@ -23,6 +23,9 @@
   
 package org.collectionspace.services.id;
 
+import java.util.Collections;
+import java.util.List;
+
 import javax.ws.rs.Consumes;
 import javax.ws.rs.GET;
 import javax.ws.rs.Path;
@@ -34,6 +37,10 @@ import javax.ws.rs.core.Response;
 import javax.xml.bind.JAXBContext;
 import javax.xml.bind.Marshaller;
 
+// May at some point instead use
+// org.jboss.resteasy.spi.NotFoundException
+import org.collectionspace.services.common.repository.DocumentNotFoundException;
+
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -64,36 +71,13 @@ public class IDResource {
         // do nothing
     }
 
-
-    //////////////////////////////////////////////////////////////////////
-    /**
-    * Placeholder for retrieving list of available ID Generators.
-    * Currently returns an empty entity body.
-    * 
-    * Implemented to facilitate a HEAD method test in ServicesTest
-    *
-    * @return  An empty entity body (for now).
-    */
-    @GET
-    @Path("")
-    public Response getIDGenerators() {
-    
-      logger.debug("> in getIDGenerators()");
-        
-        // @TODO Replace this placeholder code.
-        Response response = Response.status(Response.Status.NO_CONTENT)
-              .entity("").type(MediaType.TEXT_PLAIN).build();
-                
-        return response;
-  }
-
     //////////////////////////////////////////////////////////////////////
     /**
     * Generates and returns a new ID, from the specified ID generator.
     *
     * @param  csid  An identifier for an ID generator.
     *
-    * @return  A new ID from the specified ID generator.
+    * @return  A new ID created ("generated") by the specified ID generator.
     */
     @POST
     @Path("/{csid}/ids")
@@ -131,7 +115,7 @@ public class IDResource {
         
             // Obtain a new ID from the specified ID generator,
             // and return it in the entity body of the response.
-            newId = service.newID(csid);
+            newId = service.createID(csid);
                 
             if (newId == null || newId.equals("")) {
                 response = Response.status(Response.Status.INTERNAL_SERVER_ERROR)
@@ -144,13 +128,17 @@ public class IDResource {
             response = Response.status(Response.Status.OK)
               .entity(newId).type(MediaType.TEXT_PLAIN).build();
                 
-            // @TODO Return an XML-based error results format with the
-            // responses below.
-            
-            // @TODO An IllegalStateException often indicates an overflow
-            // of an IDPart.  Consider whether returning a 400 Bad Request
-            // status code is still warranted, or whether returning some other
-            // status would be more appropriate.
+        // @TODO Return an XML-based error results format with the
+        // responses below.
+        
+        // @TODO An IllegalStateException often indicates an overflow
+        // of an IDPart.  Consider whether returning a 400 Bad Request
+        // status code is still warranted, or whether returning some other
+        // status would be more appropriate.
+        
+        } catch (DocumentNotFoundException dnfe) {
+            response = Response.status(Response.Status.NOT_FOUND)
+              .entity(dnfe.getMessage()).type(MediaType.TEXT_PLAIN).build();
         
         } catch (IllegalStateException ise) {
           response = Response.status(Response.Status.BAD_REQUEST)
@@ -170,4 +158,132 @@ public class IDResource {
      
     }
 
+    //////////////////////////////////////////////////////////////////////
+    /**
+    * Creates a new ID generator.
+    *
+    * @param  generatorRepresentation  A representation of an ID generator.
+    */
+    @POST
+    @Path("")
+    @Consumes(MediaType.APPLICATION_XML)
+    public Response createIDGenerator() {
+    
+        logger.debug("> in createIDGenerator(String)");
+        
+        // @TODO Implement this stubbed method
+
+        // @TODO Replace this placeholder code.
+        Response response = Response.status(Response.Status.CREATED)
+              .entity("").type(MediaType.TEXT_PLAIN).build();
+
+/*      
+        // @TODO Replace this placeholder code.
+        // Return a URL for the newly-created resource in the
+        // Location header
+        String csid = "TEST-1";
+        String url = "/idgenerators/" + csid;
+        List locationList = Collections.singletonList(url);
+        response.getMetadata()
+            .get("Location")
+            .putSingle("Location", locationList);
+*/
+
+        return response;
+        
+    }
+
+    //////////////////////////////////////////////////////////////////////
+    /**
+    * Returns a representation of a single ID Generator resource.
+    *
+    * @param    csid  An identifier for an ID generator.
+    *
+    * @return  A representation of an ID generator resource.
+    */
+    @GET
+    @Path("/{csid}")
+    @Produces(MediaType.APPLICATION_XML)
+    public Response readIDGenerator(@PathParam("csid") String csid) {
+    
+      logger.debug("> in readIDGenerator(String)");
+
+/*        
+        // @TODO Replace this placeholder code.
+        Response response = Response.status(Response.Status.NO_CONTENT)
+              .entity("").type(MediaType.TEXT_PLAIN).build();
+                
+        return response;
+*/
+        Response response = null;
+        response = response.ok().build();
+        String resourceRepresentation = "";
+        
+        try {
+        
+            resourceRepresentation = service.readIDGenerator(csid);
+            
+            if (resourceRepresentation == null ||
+                resourceRepresentation.equals("")) {
+                response = Response.status(Response.Status.INTERNAL_SERVER_ERROR)
+                    .entity("ID Service returned null or empty ID Generator")
+                    .type(MediaType.TEXT_PLAIN)
+                    .build();
+                return response;
+            }
+                    
+            response = Response.status(Response.Status.OK)
+              .entity(resourceRepresentation)
+              .type(MediaType.APPLICATION_XML)
+              .build();
+                
+        // @TODO Return an XML-based error results format with the
+        // responses below.
+        
+        } catch (DocumentNotFoundException dnfe) {
+            response = Response.status(Response.Status.NOT_FOUND)
+              .entity(dnfe.getMessage()).type(MediaType.TEXT_PLAIN).build();
+
+        } catch (IllegalStateException ise) {
+          response = Response.status(Response.Status.BAD_REQUEST)
+              .entity(ise.getMessage()).type(MediaType.TEXT_PLAIN).build();
+        
+        } catch (IllegalArgumentException iae) {
+            response = Response.status(Response.Status.BAD_REQUEST)
+              .entity(iae.getMessage()).type(MediaType.TEXT_PLAIN).build();
+        
+        // This is guard code that should never be reached.
+        } catch (Exception e) {
+          response = Response.status(Response.Status.INTERNAL_SERVER_ERROR)
+              .entity(e.getMessage()).type(MediaType.TEXT_PLAIN).build();
+        }
+        
+        return response;
+
+    }
+
+    //////////////////////////////////////////////////////////////////////
+    /**
+    * Placeholder for retrieving a list of available ID Generator resources.
+    * Currently returns an empty entity body.
+    * 
+    * Implemented to facilitate a HEAD method test in ServiceLayerTest.
+    *
+    * @return  An empty entity body (for now).
+    */
+    @GET
+    @Path("")
+    @Produces(MediaType.APPLICATION_XML)
+    public Response readIDGeneratorsList() {
+    
+      logger.debug("> in readIDGeneratorsList()");
+        
+        // @TODO Replace this placeholder code.
+        Response response = Response.status(Response.Status.NO_CONTENT)
+              .entity("").type(MediaType.TEXT_PLAIN).build();
+                
+        return response;
+  }
+
+
 }
index c437d7c8d0fcd2461c311c0d9023211d61b34481..783c85ce9a358a26ffd2e362d582ceddd36e3cd4 100644 (file)
  
 package org.collectionspace.services.id;
 
+// May at some point instead use
+// org.jboss.resteasy.spi.NotFoundException
+import org.collectionspace.services.common.repository.DocumentNotFoundException;
+
+
 /**
  * IDService
  *
@@ -37,11 +42,11 @@ public interface IDService {
     // Read single object
     
     // Generates and returns a new ID from the specified ID generator.
-    public String newID(String csid)
-      throws IllegalArgumentException, IllegalStateException;
+    public String createID(String csid) throws DocumentNotFoundException,
+      IllegalArgumentException, IllegalStateException;
     
     // Returns the last-generated ID associated with the specified ID generator.
-    public String getLastID(String csid)
+    public String readLastID(String csid)
         throws IllegalArgumentException, IllegalStateException;
 
     // Read a list of objects (aka read multiple)
@@ -53,12 +58,12 @@ public interface IDService {
     // Create
     
     // Adds a new ID generator.
-    public void addIDGenerator(String csid, String serializedIDGenerator)
+    public void createIDGenerator(String csid, String serializedIDGenerator)
         throws IllegalArgumentException, IllegalStateException;
     
     // Read single object
-    public String getIDGenerator(String csid)
-        throws IllegalArgumentException, IllegalStateException;
+    public String readIDGenerator(String csid) throws DocumentNotFoundException,
+        IllegalArgumentException, IllegalStateException;
     
     // Read a list of objects (aka read multiple)
     
index 68e07065fcc1e62d16995c57b546100a1ec98738..2e7b1b5c61432906fa8a3e245ad9abf0116202b2 100644 (file)
@@ -29,7 +29,8 @@
 // in ways that are not consistent with their original semantic meaning.
 
 // @TODO Get the JDBC driver classname and database URL from configuration;
-// better yet, substitute Hibernate for JDBC for accessing database-managed persistence.
+// better yet, substitute JPA or Hibernate for JDBC for accessing
+// database-managed persistence.
 
 // @TODO Remove any hard-coded dependencies on MySQL.
 
@@ -72,6 +73,7 @@
 // - "save/read" (appears to be used by Hibernate),
 // - "persist/find" (used by JPA)
 // - or?
+// For now have used CRUD-like names, consistent with other classes.
 
 package org.collectionspace.services.id;
 
@@ -82,6 +84,10 @@ import java.sql.SQLException;
 import java.sql.PreparedStatement;
 import java.sql.Statement;
 
+// May at some point instead use
+// org.jboss.resteasy.spi.NotFoundException
+import org.collectionspace.services.common.repository.DocumentNotFoundException;
+
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -161,98 +167,11 @@ public class IDServiceJdbcImpl implements IDService {
                }
        
        }
+
+       // -----------------
+    // Operations on IDs
+    // -----------------
        
-       //////////////////////////////////////////////////////////////////////
-   /**
-       * Creates a new instance of the specified JDBC driver class.
-       *
-       * @param   jdbcDriverClassname  The name of a JDBC driver class.
-       *
-       * @throws  IllegalStateException if a new instance of the specified
-       *          JDBC driver class cannot be created.
-       */
-       public void instantiateJdbcDriver(String jdbcDriverClassname)
-       throws IllegalStateException {
-       
-               logger.debug("> in instantiateJdbcDriver(String)");
-       
-               try {
-                       Class.forName(jdbcDriverClassname).newInstance();
-               } catch (ClassNotFoundException e) {
-                       throw new IllegalStateException(
-                               "Error finding JDBC driver class '" +
-                               JDBC_DRIVER_CLASSNAME +
-                               "' to set up database connection.");
-               } catch (InstantiationException e) {
-                       throw new IllegalStateException(
-                               "Error instantiating JDBC driver class '" +
-                               JDBC_DRIVER_CLASSNAME +
-                               "' to set up database connection.");
-               } catch (IllegalAccessException e) {
-                       throw new IllegalStateException(
-                               "Error accessing JDBC driver class '" +
-                               JDBC_DRIVER_CLASSNAME +
-                               "' to set up database connection.");
-               }
-         
-       }
-       
-    //////////////////////////////////////////////////////////////////////
-   /**
-       * Identifies whether a specified table exists in the database.
-       *
-       * @param   tablename  The name of a database table.
-       *
-       * @return  True if the specified table exists in the database;
-       *          false if the specified table does not exist in the database.
-       *
-       * @throws  IllegalStateException if an error occurs while checking for the
-       *          existence of the specified table.
-       */
-       public boolean hasTable(String tablename) throws IllegalStateException {
-       
-               logger.debug("> in hasTable");
-       
-               if (tablename == null || tablename.equals("")) {
-                       return false;
-               }
-         
-               Connection conn = null;
-               try {
-               
-                       conn = getJdbcConnection();
-                       
-                       // Retrieve a list of tables in the current database. 
-                       final String CATALOG_NAME = null;
-                       final String SCHEMA_NAME_PATTERN = null;
-                       final String[] TABLE_TYPES = null;
-                       ResultSet tablesMatchingTableName =
-                               conn.getMetaData().getTables(
-                                       CATALOG_NAME, SCHEMA_NAME_PATTERN, tablename, TABLE_TYPES);
-               
-                       // Check whether a table with the specified name is in that list. 
-                       boolean moreRows = tablesMatchingTableName.next();
-                       if (! moreRows) {
-                               return false;
-                       } else {
-                               return true;
-                       }
-               
-               } catch (SQLException e) {
-                       throw new IllegalStateException(
-                               "Error while checking for existence of tablebase table: " + e.getMessage());
-               } finally {
-                       try {
-                               if (conn != null) {
-                                       conn.close();
-                               }
-                       } catch(SQLException e) {
-                               // Do nothing here
-                       }
-               }
-       
-       }
-               
        //////////////////////////////////////////////////////////////////////
    /**
        * Generates and returns a new ID associated with a specified ID generator.
@@ -269,10 +188,11 @@ public class IDServiceJdbcImpl implements IDService {
        *
        * @throws  IllegalStateException if a storage-related error occurred.
        */
-       public String newID(String csid) throws
+       @Override
+       public String createID(String csid) throws DocumentNotFoundException,
                IllegalArgumentException, IllegalStateException {
                
-               logger.debug("> in newID");
+               logger.debug("> in createID");
                
                // @TODO Where relevant, implement logic to check for ID availability,
                // after generating a candidate ID.
@@ -283,13 +203,15 @@ public class IDServiceJdbcImpl implements IDService {
                String lastId = "";
                
                if (csid == null || csid.equals("")) {
-                       throw new IllegalArgumentException(
+                       throw new DocumentNotFoundException(
                                "Identifier for ID generator must not be null or empty.");
                }
                
                String serializedGenerator = "";
                try {
-                       serializedGenerator = getIDGenerator(csid);
+                       serializedGenerator = readIDGenerator(csid);
+               } catch (DocumentNotFoundException e ) {
+                       throw e;
                } catch (IllegalArgumentException e ) {
                        throw e;
                } catch (IllegalStateException e ) {
@@ -313,7 +235,7 @@ public class IDServiceJdbcImpl implements IDService {
                
                        // Retrieve the last ID associated with this generator
                        // from persistent storage.
-                       lastId = getLastID(csid);
+                       lastId = readLastID(csid);
                        
                        // If there was no last generated ID associated with this generator,
                        // get a new ID.
@@ -382,15 +304,15 @@ public class IDServiceJdbcImpl implements IDService {
                          
                        if (rowsUpdated != 1) {
                                throw new IllegalStateException(
-                                       "Error updating last-generated ID in the database for ID generator '" +
-                                       csid + "'");
+                                       "Error updating last-generated ID in the database " +
+                                       "for ID generator '" + csid + "'");
                        }
                
                  logger.debug("> successfully updated last-generated ID: " + lastId);
                
                } catch (SQLException e) {
-                       throw new IllegalStateException("Error updating last-generated ID in the database: " +
-                       e.getMessage());
+                       throw new IllegalStateException("Error updating last-generated " +
+                           "ID in the database: " + e.getMessage());
                } finally {
                        try {
                                if (conn != null) {
@@ -416,10 +338,11 @@ public class IDServiceJdbcImpl implements IDService {
        *
        * @throws  IllegalStateException if a storage-related error occurred.
        */
-       public String getLastID(String csid) throws IllegalArgumentException,
+    @Override
+       public String readLastID(String csid) throws IllegalArgumentException,
                IllegalStateException {
        
-               logger.debug("> in getLastID");
+               logger.debug("> in readLastID");
                
                // @TODO Where relevant, implement logic to check for ID availability,
                // after generating a candidate ID.
@@ -434,7 +357,8 @@ public class IDServiceJdbcImpl implements IDService {
                        Statement stmt = conn.createStatement();
                        
                        ResultSet rs = stmt.executeQuery(
-                         "SELECT last_generated_id FROM id_generators WHERE id_generator_csid='" + csid + "'");
+                         "SELECT last_generated_id FROM id_generators " + 
+                         "WHERE id_generator_csid='" + csid + "'");
                          
                        boolean moreRows = rs.next();
                        if (! moreRows) {
@@ -448,8 +372,8 @@ public class IDServiceJdbcImpl implements IDService {
                        rs.close();
                
                } catch (SQLException e) {
-                       throw new IllegalStateException("Error retrieving last ID from the database: " +
-                       e.getMessage());
+                       throw new IllegalStateException("Error retrieving last ID " + 
+                           "from the database: " + e.getMessage());
                } finally {
                        try {
                                if (conn != null) {
@@ -465,6 +389,10 @@ public class IDServiceJdbcImpl implements IDService {
                return lastId;
        
        }
+
+       // ---------------------------
+    // Operations on ID Generators
+    // ---------------------------
        
        //////////////////////////////////////////////////////////////////////
    /**
@@ -477,15 +405,16 @@ public class IDServiceJdbcImpl implements IDService {
        *
        * @throws  IllegalStateException if a storage-related error occurred.
        */
-       public void addIDGenerator(String csid, SettableIDGenerator generator)
+       public void createIDGenerator(String csid, SettableIDGenerator generator)
          throws IllegalArgumentException, IllegalStateException {
        
-               logger.debug("> in addIDGenerator(String, SettableIDGenerator)");
+               logger.debug("> in createIDGenerator(String, SettableIDGenerator)");
        
                // @TODO: Add checks for authorization to perform this operation.
                
                if (generator == null) {
-                       throw new IllegalArgumentException("New ID generator to add cannot be null.");
+                       throw new IllegalArgumentException("New ID generator " + 
+                           "to add cannot be null.");
                }
                
                String serializedGenerator = "";
@@ -496,7 +425,7 @@ public class IDServiceJdbcImpl implements IDService {
                }
                
                try {
-                       addIDGenerator(csid, serializedGenerator);
+                       createIDGenerator(csid, serializedGenerator);
                } catch (IllegalArgumentException e) {
                        throw e;
                } catch (IllegalStateException e) {
@@ -521,16 +450,18 @@ public class IDServiceJdbcImpl implements IDService {
        *
        * @throws  IllegalStateException if a storage-related error occurred.
        */
-       public void addIDGenerator(String csid, String serializedGenerator)
+       @Override
+       public void createIDGenerator(String csid, String serializedGenerator)
          throws IllegalArgumentException, IllegalStateException {
        
-               logger.debug("> in addIDGenerator(String, String)");
+               logger.debug("> in createIDGenerator(String, String)");
        
                // @TODO Add checks for authorization to perform this operation.
                        
                if (serializedGenerator == null || serializedGenerator.equals("")) {
                        throw new IllegalArgumentException(
-                               "Could not understand or parse this representation of an ID generator.");
+                               "Could not understand or parse this representation " + 
+                               "of an ID generator.");
                }
                
                Connection conn = null;
@@ -541,10 +472,12 @@ public class IDServiceJdbcImpl implements IDService {
                        
                        // Test whether this ID generator already exists in the database.
                        //
-                       // @TODO This check should extend further, to other aspects of the generator,
-                       // such as its URI, if any, and its structure.
+                       // @TODO This check should extend further, to other aspects
+                       // of the generator, such as its URI, if any, and its structure,
+                       // so we avoid duplication based on content as well as identifier.
                        ResultSet rs = stmt.executeQuery(
-                         "SELECT id_generator_csid FROM id_generators WHERE id_generator_csid='" + csid + "'");
+                         "SELECT id_generator_csid FROM id_generators " + 
+                         "WHERE id_generator_csid='" + csid + "'");
                          
                        boolean moreRows = rs.next();
                        
@@ -553,10 +486,12 @@ public class IDServiceJdbcImpl implements IDService {
                                idGeneratorFound = false;
                        }
                                
-                       // If this ID generator already exists in the database, throw an Exception.
+                       // If this ID generator already exists in the database,
+                       // throw an Exception.
                        //
-                       // @TODO This exception needs to convey the meaning that a conflict has
-                       // occurred, so that this status can be reported to the client.
+                       // @TODO This exception needs to convey the meaning that a
+                       // conflict has occurred, so that this status can be reported
+                       // to the client.
                        if (idGeneratorFound) {
                                throw new IllegalStateException(
                                        "Conflict with existing generator when attempting to add " +
@@ -584,7 +519,8 @@ public class IDServiceJdbcImpl implements IDService {
                                int rowsUpdated = ps.executeUpdate();
                                if (rowsUpdated != 1) {
                                        throw new IllegalStateException(
-                                               "Error adding new ID generator '" + csid + "'" + " to the database.");
+                                               "Error adding new ID generator '" + csid +
+                                               "'" + " to the database.");
                                }
                        
                        } // end if (idGeneratorFound)
@@ -592,8 +528,8 @@ public class IDServiceJdbcImpl implements IDService {
                          logger.debug("> successfully added ID generator: " + csid);
                        
                        } catch (SQLException e) {
-                               throw new IllegalStateException("Error adding new ID generator to the database: " +
-                               e.getMessage());
+                               throw new IllegalStateException("Error adding new ID " +
+                                   "generator to the database: " + e.getMessage());
                        } finally {
                                try {
                                        if (conn != null) {
@@ -605,6 +541,70 @@ public class IDServiceJdbcImpl implements IDService {
                        }
        
        }
+
+       //////////////////////////////////////////////////////////////////////
+       /**
+       * Returns a requested ID generator from persistent storage.
+       *
+       * @param  csid  An identifier for an ID generator.
+       *
+       * @return  A serialized representation of the requested ID generator.
+       *
+       * @throws  IllegalArgumentException if the requested ID generator could
+       *          not be found.
+       *
+       * @throws  IllegalStateException if a storage-related error occurred.
+       */
+       public String readIDGenerator (String csid) throws
+           DocumentNotFoundException, IllegalArgumentException,
+           IllegalStateException {
+       
+               logger.debug("> in readIDGenerator");
+               
+               String serializedGenerator = null;
+               
+               Connection conn = null;
+               try {
+               
+                       conn = getJdbcConnection();
+                       Statement stmt = conn.createStatement();
+                       
+                       ResultSet rs = stmt.executeQuery(
+                         "SELECT id_generator_state FROM id_generators " + 
+                         "WHERE id_generator_csid='" + csid + "'");
+                         
+                       boolean moreRows = rs.next();
+                       if (! moreRows) {
+                               throw new DocumentNotFoundException(
+                                   "ID generator with ID " +
+                                   "\'" + csid + "\'" +
+                                   " could not be found.");
+                       }
+               
+                       serializedGenerator = rs.getString(1);
+                       
+                       rs.close();
+               
+               } catch (SQLException e) {
+                       throw new IllegalStateException(
+                               "Error retrieving ID generator " +
+                               "\'" + csid + "\'" +
+                               " from database: " + e.getMessage());
+               } finally {
+                       try {
+                               if (conn != null) {
+                                       conn.close();
+                               }
+                       } catch(SQLException e) {
+                               // Do nothing here
+                       }
+               }
+               
+               logger.debug("> retrieved SettableIDGenerator: " + serializedGenerator);
+               
+               return serializedGenerator;
+                 
+       }
        
        //////////////////////////////////////////////////////////////////////
        /**
@@ -655,13 +655,15 @@ public class IDServiceJdbcImpl implements IDService {
        * dependencies.  Currently, this method expects serialization via XStream's
        * out-of-the-box serializer, without custom configuration.
        *
-       * @param  csid     An identifier for an ID generator.
+       * @param  csid  An identifier for an ID generator.
        *
-       * @param  serializedGenerator  A serialized ID generator, reflecting its current state,
-       *                            including the values of its constituent parts.
+       * @param  serializedGenerator
+       *           A serialized ID generator, reflecting its current state,
+       *           including the values of its constituent parts.
        *
        * @throws  IllegalStateException if a storage-related error occurred.
        */
+       @Override
        public void updateIDGenerator(String csid, String serializedGenerator)
          throws IllegalArgumentException, IllegalStateException {
        
@@ -682,7 +684,8 @@ public class IDServiceJdbcImpl implements IDService {
                
                        // Test whether this ID generator already exists in the database.
                        ResultSet rs = stmt.executeQuery(
-                               "SELECT id_generator_csid FROM id_generators WHERE id_generator_csid='" +
+                               "SELECT id_generator_csid FROM id_generators " +
+                               "WHERE id_generator_csid='" +
                                csid + "'");
                                  
                        boolean moreRows = rs.next();
@@ -692,7 +695,8 @@ public class IDServiceJdbcImpl implements IDService {
                                idGeneratorFound = false;
                        }
                                
-                       // If this ID generator already exists in the database, update its record.
+                       // If this ID generator already exists in the database,
+                       // update its record.
                        if (idGeneratorFound) {
        
                        final String SQL_STATEMENT_STRING =
@@ -717,7 +721,8 @@ public class IDServiceJdbcImpl implements IDService {
                                int rowsUpdated = ps.executeUpdate();
                                if (rowsUpdated != 1) {
                                        throw new IllegalStateException(
-                                               "Error updating ID generator '" + csid + "'" + " in the database.");
+                                               "Error updating ID generator '" + csid +
+                                               "'" + " in the database.");
                                }
                                
                        // Otherwise, throw an exception, which indicates that the requested
@@ -768,7 +773,8 @@ public class IDServiceJdbcImpl implements IDService {
                        
                        // Test whether this ID generator already exists in the database.
                        ResultSet rs = stmt.executeQuery(
-                         "SELECT id_generator_csid FROM id_generators WHERE id_generator_csid='" +
+                         "SELECT id_generator_csid FROM id_generators " +
+                         "WHERE id_generator_csid='" +
                          csid + "'");
                        boolean moreRows = rs.next();
                        
@@ -777,7 +783,8 @@ public class IDServiceJdbcImpl implements IDService {
                                idGeneratorFound = false;
                        }
                        
-                       // If this ID generator already exists in the database, update its record.
+                       // If this ID generator already exists in the database,
+                       // update its record.
                        if (idGeneratorFound) {
                
                           final String SQL_STATEMENT_STRING =
@@ -789,7 +796,8 @@ public class IDServiceJdbcImpl implements IDService {
                                int rowsUpdated = ps.executeUpdate();
                                if (rowsUpdated != 1) {
                                throw new IllegalStateException(
-                                       "Error deleting ID generator '" + csid + "'" + " in the database.");
+                                       "Error deleting ID generator '" + csid +
+                                       "'" + " in the database.");
                                }
                
                        // Otherwise, throw an exception, which indicates that the requested
@@ -817,6 +825,45 @@ public class IDServiceJdbcImpl implements IDService {
        
        }
        
+       // -------------------
+    // Database operations
+    // -------------------
+    
+   //////////////////////////////////////////////////////////////////////
+   /**
+       * Creates a new instance of the specified JDBC driver class.
+       *
+       * @param   jdbcDriverClassname  The name of a JDBC driver class.
+       *
+       * @throws  IllegalStateException if a new instance of the specified
+       *          JDBC driver class cannot be created.
+       */
+       public void instantiateJdbcDriver(String jdbcDriverClassname)
+       throws IllegalStateException {
+       
+               logger.debug("> in instantiateJdbcDriver(String)");
+       
+               try {
+                       Class.forName(jdbcDriverClassname).newInstance();
+               } catch (ClassNotFoundException e) {
+                       throw new IllegalStateException(
+                               "Error finding JDBC driver class '" +
+                               JDBC_DRIVER_CLASSNAME +
+                               "' to set up database connection.");
+               } catch (InstantiationException e) {
+                       throw new IllegalStateException(
+                               "Error instantiating JDBC driver class '" +
+                               JDBC_DRIVER_CLASSNAME +
+                               "' to set up database connection.");
+               } catch (IllegalAccessException e) {
+                       throw new IllegalStateException(
+                               "Error accessing JDBC driver class '" +
+                               JDBC_DRIVER_CLASSNAME +
+                               "' to set up database connection.");
+               }
+         
+       }
+
        //////////////////////////////////////////////////////////////////////
        /**
        * Opens a connection to the database and returns a JDBC Connection object.
@@ -831,58 +878,60 @@ public class IDServiceJdbcImpl implements IDService {
                
                Connection conn = null;
                try {
-                       conn = DriverManager.getConnection(DATABASE_URL, DATABASE_USERNAME, DATABASE_PASSWORD);
+                       conn = DriverManager.getConnection(DATABASE_URL,
+                           DATABASE_USERNAME, DATABASE_PASSWORD);
                } catch (SQLException e) {
                        throw e;
                }
                return conn;
        
        }
-       
-       //////////////////////////////////////////////////////////////////////
-       /**
-       * Returns a requested ID generator from persistent storage.
-       *
-       * @param  csid  An identifier for an ID generator.
+               
+    //////////////////////////////////////////////////////////////////////
+   /**
+       * Identifies whether a specified table exists in the database.
        *
-       * @return  A serialized representation of the requested ID generator.
+       * @param   tablename  The name of a database table.
        *
-       * @throws  IllegalArgumentException if the requested ID generator could not be found.
+       * @return  True if the specified table exists in the database;
+       *          false if the specified table does not exist in the database.
        *
-       * @throws  IllegalStateException if a storage-related error occurred.
+       * @throws  IllegalStateException if an error occurs while checking for the
+       *          existence of the specified table.
        */
-       public String getIDGenerator (String csid) throws IllegalArgumentException, IllegalStateException {
+       public boolean hasTable(String tablename) throws IllegalStateException {
        
-               logger.debug("> in getIDGenerator");
-               
-               String serializedGenerator = null;
-               
+               logger.debug("> in hasTable");
+       
+               if (tablename == null || tablename.equals("")) {
+                       return false;
+               }
+         
                Connection conn = null;
                try {
                
                        conn = getJdbcConnection();
-                       Statement stmt = conn.createStatement();
                        
-                       ResultSet rs = stmt.executeQuery(
-                         "SELECT id_generator_state FROM id_generators WHERE id_generator_csid='" + csid + "'");
-                         
-                       boolean moreRows = rs.next();
+                       // Retrieve a list of tables in the current database. 
+                       final String CATALOG_NAME = null;
+                       final String SCHEMA_NAME_PATTERN = null;
+                       final String[] TABLE_TYPES = null;
+                       ResultSet tablesMatchingTableName =
+                               conn.getMetaData().getTables(
+                                       CATALOG_NAME, SCHEMA_NAME_PATTERN, tablename, TABLE_TYPES);
+               
+                       // Check whether a table with the specified name is in that list. 
+                       boolean moreRows = tablesMatchingTableName.next();
                        if (! moreRows) {
-                               throw new IllegalArgumentException(
-                                   "ID generator with ID " +
-                                   "\'" + csid + "\'" +
-                                   " could not be found.");
+                               return false;
+                       } else {
+                               return true;
                        }
                
-                       serializedGenerator = rs.getString(1);
-                       
-                       rs.close();
-               
                } catch (SQLException e) {
                        throw new IllegalStateException(
-                               "Error retrieving ID generator " +
-                               "\'" + csid + "\'" +
-                               " from database: " + e.getMessage());
+                               "Error while checking for existence of tablebase table: " +
+                               e.getMessage());
                } finally {
                        try {
                                if (conn != null) {
@@ -892,11 +941,7 @@ public class IDServiceJdbcImpl implements IDService {
                                // Do nothing here
                        }
                }
-               
-               logger.debug("> retrieved SettableIDGenerator: " + serializedGenerator);
-               
-               return serializedGenerator;
        
-               }
-         
        }
+               
+}
\ No newline at end of file
index aa9cf422fed148cd40c58a1ae02aa2a27a499675..adf4d1384274a0196864797ffe9e13915b0a8f3c 100644 (file)
 
 package org.collectionspace.services.id.test;
 
+// May at some point instead use
+// org.jboss.resteasy.spi.NotFoundException
+import org.collectionspace.services.common.repository.DocumentNotFoundException;
+
 import org.collectionspace.services.id.*;
 
 import org.testng.Assert;
@@ -63,55 +67,59 @@ public class IDServiceJdbcImplTest {
     }
 
     @Test(dependsOnMethods = {"hasRequiredDatabaseTable"})
-    public void addIDGenerator() {
+    public void createIDGenerator() throws DocumentNotFoundException,
+        IllegalArgumentException, IllegalStateException {
         try {
             jdbc.deleteIDGenerator(DEFAULT_CSID);
         } catch (Exception e) {
                // Fail silently; this is guard code.
         }
-        jdbc.addIDGenerator(DEFAULT_CSID, getSpectrumEntryNumberGenerator());
+        jdbc.createIDGenerator(DEFAULT_CSID, getSpectrumEntryNumberGenerator());
     }
 
-    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "addIDGenerator"})
-    public void readIDGenerator() {
+    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "createIDGenerator"})
+    public void readIDGenerator() throws DocumentNotFoundException,
+        IllegalArgumentException, IllegalStateException {
 
-        serializedGenerator = jdbc.getIDGenerator(DEFAULT_CSID);
+        serializedGenerator = jdbc.readIDGenerator(DEFAULT_CSID);
         generator = IDGeneratorSerializer.deserialize(serializedGenerator);
         Assert.assertEquals(generator.getCsid(), DEFAULT_CSID);
         
     }
 
-    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "addIDGenerator",
+    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "createIDGenerator",
         "readIDGenerator"})
-    public void updateIDGenerator() {
+    public void updateIDGenerator() throws DocumentNotFoundException,
+        IllegalArgumentException, IllegalStateException {
 
         final String NEW_DESCRIPTION = "new description";
         
         // Retrieve an existing generator, deserialize it,
         // update its contents, serialize it, and write it back.
-        serializedGenerator = jdbc.getIDGenerator(DEFAULT_CSID);
+        serializedGenerator = jdbc.readIDGenerator(DEFAULT_CSID);
         generator = IDGeneratorSerializer.deserialize(serializedGenerator);
         generator.setDescription(NEW_DESCRIPTION);
         serializedGenerator = IDGeneratorSerializer.serialize(generator);
         
         jdbc.updateIDGenerator(DEFAULT_CSID, serializedGenerator);
         
-        serializedGenerator = jdbc.getIDGenerator(DEFAULT_CSID);
+        serializedGenerator = jdbc.readIDGenerator(DEFAULT_CSID);
         generator = IDGeneratorSerializer.deserialize(serializedGenerator);
         
         Assert.assertEquals(generator.getDescription(), NEW_DESCRIPTION);
         
     }
 
-    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "addIDGenerator",
+    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "createIDGenerator",
        "readIDGenerator", "updateIDGenerator"})
     public void deleteIDGenerator() {
         jdbc.deleteIDGenerator(DEFAULT_CSID);
     }
 
-    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "addIDGenerator",
+    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "createIDGenerator",
         "readIDGenerator", "updateIDGenerator", "deleteIDGenerator"})
-        public void newID() {
+        public void createID() throws DocumentNotFoundException,
+            IllegalArgumentException, IllegalStateException {
                 
         try {
             jdbc.deleteIDGenerator(DEFAULT_CSID);
@@ -121,11 +129,11 @@ public class IDServiceJdbcImplTest {
                // exists in the database. 
         }
 
-        jdbc.addIDGenerator(DEFAULT_CSID, getSpectrumEntryNumberGenerator());
+        jdbc.createIDGenerator(DEFAULT_CSID, getSpectrumEntryNumberGenerator());
 
-        Assert.assertEquals(service.newID(DEFAULT_CSID), "E1");
-        Assert.assertEquals(service.newID(DEFAULT_CSID), "E2");
-        Assert.assertEquals(service.newID(DEFAULT_CSID), "E3");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), "E1");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), "E2");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), "E3");
         
         try {
             jdbc.deleteIDGenerator(DEFAULT_CSID);
@@ -133,11 +141,11 @@ public class IDServiceJdbcImplTest {
             Assert.fail("Could not delete ID generator '" + DEFAULT_CSID + "'.");
         }
         
-        jdbc.addIDGenerator(DEFAULT_CSID, getChinAccessionNumberGenerator());
+        jdbc.createIDGenerator(DEFAULT_CSID, getChinAccessionNumberGenerator());
 
-        Assert.assertEquals(service.newID(DEFAULT_CSID), CURRENT_YEAR + ".1.1");
-        Assert.assertEquals(service.newID(DEFAULT_CSID), CURRENT_YEAR + ".1.2");
-        Assert.assertEquals(service.newID(DEFAULT_CSID), CURRENT_YEAR + ".1.3");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), CURRENT_YEAR + ".1.1");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), CURRENT_YEAR + ".1.2");
+        Assert.assertEquals(service.createID(DEFAULT_CSID), CURRENT_YEAR + ".1.3");
 
         try {
             jdbc.deleteIDGenerator(DEFAULT_CSID);
@@ -152,10 +160,11 @@ public class IDServiceJdbcImplTest {
     // 1. The ID Service is running and accessible to this test; and
     // 2. There is no ID generator retrievable through that service
     //        with the identifier 'non-existent identifier'.
-    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "newID"}, 
-        expectedExceptions = IllegalArgumentException.class)
-    public void newIDNonExistentGenerator() {
-        nextId = service.newID("non-existent identifier");                
+    @Test(dependsOnMethods = {"hasRequiredDatabaseTable", "createID"}, 
+        expectedExceptions = DocumentNotFoundException.class)
+    public void createIDNonExistentGenerator() throws DocumentNotFoundException,
+        IllegalArgumentException, IllegalStateException {
+        nextId = service.createID("non-existent identifier");                
     }
 
     // ---------------------------------------------------------------