EMPIREDB-319
add new method for partial record reading
diff --git a/empire-db/src/main/java/org/apache/empire/db/DBRecord.java b/empire-db/src/main/java/org/apache/empire/db/DBRecord.java
index 0f337be..54a64a4 100644
--- a/empire-db/src/main/java/org/apache/empire/db/DBRecord.java
+++ b/empire-db/src/main/java/org/apache/empire/db/DBRecord.java
@@ -34,6 +34,7 @@
import org.apache.empire.data.ColumnExpr;
import org.apache.empire.data.Record;
import org.apache.empire.db.exceptions.FieldIsReadOnlyException;
+import org.apache.empire.db.exceptions.FieldValueNotFetchedException;
import org.apache.empire.db.expr.compare.DBCompareExpr;
import org.apache.empire.exceptions.BeanPropertyGetException;
import org.apache.empire.exceptions.InvalidArgumentException;
@@ -519,7 +520,7 @@
throw new InvalidArgumentException("index", index);
// Special check for NO_VALUE
if (fields[index] == ObjectUtils.NO_VALUE)
- return null;
+ throw new FieldValueNotFetchedException(getColumn(index));
// Return field value
return fields[index];
}
@@ -580,6 +581,9 @@
{ // Check valid
if (state == State.Invalid)
throw new ObjectNotValidException(this);
+ // must have been fetched
+ if (fields[i]==ObjectUtils.NO_VALUE)
+ throw new FieldValueNotFetchedException(getColumn(i));
// Init original values
if (modified == null)
{ // Save all original values
@@ -587,11 +591,9 @@
for (int j = 0; j < fields.length; j++)
modified[j] = false;
}
- // Set Modified
- if (fields[i]!=ObjectUtils.NO_VALUE || value!=null)
- modified[i] = true;
- // Set Value
+ // Set Value and Modified
fields[i] = value;
+ modified[i] = true;
// Set State
if (state.isLess(State.Modified))
changeState(State.Modified);
diff --git a/empire-db/src/main/java/org/apache/empire/db/DBRowSet.java b/empire-db/src/main/java/org/apache/empire/db/DBRowSet.java
index 891c04f..c9daf7d 100644
--- a/empire-db/src/main/java/org/apache/empire/db/DBRowSet.java
+++ b/empire-db/src/main/java/org/apache/empire/db/DBRowSet.java
@@ -66,6 +66,12 @@
{
private final static long serialVersionUID = 1L;
+ public enum PartialMode
+ {
+ INCLUDE,
+ EXCLUDE;
+ }
+
/**
* This class is used to set the auto generated key of a record if the database does not support sequences.
* It is used with the executeSQL function and only required for insert statements
@@ -667,6 +673,53 @@
throw new RecordNotFoundException(this, key);
}
}
+
+ /**
+ * Reads the partial record for a given primary key from the database
+ * @param rec the DBRecord object which will hold the record data
+ * @param key the primary key values
+ * @param conn a valid JDBC connection.
+ * @param mode flag whether to include only the given columns or whether to add all but the given columns
+ * @param columns the columns to include or exclude (depending on mode)
+ */
+ public void readRecord(DBRecord rec, Object[] key, Connection conn, PartialMode mode, DBColumn... columns)
+ {
+ // Check Arguments
+ if (conn == null || rec == null)
+ throw new InvalidArgumentException("conn|rec", null);
+ // create command
+ DBCommand cmd = db.createCommand();
+ for (DBColumn column : this.columns)
+ { // key column?
+ if (isKeyColumn(column))
+ { // always select key column
+ cmd.select(column);
+ continue;
+ }
+ // find in column list
+ for (int i=0; i<columns.length; i++)
+ { // compare column
+ if (column.equals(columns[i]))
+ { // found: add for INCLUDE
+ if (mode==PartialMode.INCLUDE)
+ cmd.select(column);
+ }
+ else if (mode==PartialMode.EXCLUDE)
+ { // not found: add for EXCLUDE
+ cmd.select(column);
+ }
+ }
+ }
+ // Set key constraints
+ setKeyConstraints(cmd, key);
+ try {
+ // Read Record
+ readRecord(rec, cmd, conn);
+ } catch (QueryNoResultException e) {
+ // Translate exception
+ throw new RecordNotFoundException(this, key);
+ }
+ }
/**
* Returns true if the record exists in the database or false otherwise.
diff --git a/empire-db/src/main/java/org/apache/empire/db/exceptions/FieldValueNotFetchedException.java b/empire-db/src/main/java/org/apache/empire/db/exceptions/FieldValueNotFetchedException.java
new file mode 100644
index 0000000..3db7f54
--- /dev/null
+++ b/empire-db/src/main/java/org/apache/empire/db/exceptions/FieldValueNotFetchedException.java
@@ -0,0 +1,37 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.empire.db.exceptions;
+
+import org.apache.empire.commons.ErrorType;
+import org.apache.empire.data.Column;
+
+public class FieldValueNotFetchedException extends FieldValueException
+{
+ /**
+ * Comment for <code>serialVersionUID</code>
+ */
+ private static final long serialVersionUID = 1L;
+
+ public static final ErrorType errorType = new ErrorType("error.db.fieldValueNotFetched", "The field {0} has not been fetched for this record.");
+
+ public FieldValueNotFetchedException(Column col)
+ {
+ super(col, errorType, new String[] { getColumnTitle(col) });
+ }
+}