Author: awhite
Date: Thu Sep 14 12:36:09 2006
New Revision: 443447
URL: http://svn.apache.org/viewvc?view=rev&rev=443447
Log:
Allow null discriminator values when adding class conditions on outer joins.
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/strats/InValueDiscriminatorStrategy.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/AbstractResult.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Joins.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/LogicalUnion.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Select.java
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/SelectImpl.java
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/JDBCStoreManager.java
Thu Sep 14 12:36:09 2006
@@ -367,7 +367,7 @@
throws SQLException {
Select sel = _sql.newSelect();
if (!select(sel, mapping, subs, sm, null, fetch,
- JDBCFetchConfiguration.EAGER_JOIN, true))
+ JDBCFetchConfiguration.EAGER_JOIN, true, false))
return null;
sel.wherePrimaryKey(sm.getObjectId(), mapping, this);
@@ -463,8 +463,8 @@
//### object that only creates a real select when actually used?
Select sel = _sql.newSelect();
- if (select(sel, mapping, sel.SUBS_EXACT, sm, fields, jfetch,
- EagerFetchModes.EAGER_JOIN, true)) {
+ if (select(sel, mapping, Select.SUBS_EXACT, sm, fields, jfetch,
+ EagerFetchModes.EAGER_JOIN, true, false)) {
sel.wherePrimaryKey(sm.getObjectId(), mapping, this);
res = sel.execute(this, jfetch, lockLevel);
try {
@@ -854,18 +854,20 @@
* @param eager eager fetch mode to use
* @param ident whether to select primary key columns as distinct
* identifiers
+ * @param outer whether we're outer-joining to this type
* @return true if the select is required, false otherwise
*/
public boolean select(Select sel, ClassMapping mapping, int subs,
OpenJPAStateManager sm, BitSet fields, JDBCFetchConfiguration fetch,
- int eager, boolean ident) {
+ int eager, boolean ident, boolean outer) {
// add class conditions so that they're cloned for any batched selects
boolean joinedSupers = false;
if ((sm == null || sm.getPCState() == PCState.TRANSIENT)
- && (subs == sel.SUBS_JOINABLE || subs == sel.SUBS_NONE)) {
+ && (subs == Select.SUBS_JOINABLE || subs == Select.SUBS_NONE)) {
loadSubclasses(mapping);
+ Joins joins = (outer) ? sel.newOuterJoins() : null;
joinedSupers = mapping.getDiscriminator().addClassConditions(sel,
- subs == sel.SUBS_JOINABLE, null);
+ subs == Select.SUBS_JOINABLE, joins);
}
// create all our eager selects so that those fields are reserved
@@ -889,7 +891,7 @@
fetch.traverseJDBC(eagerToMany), eager);
// optionally select subclass mappings
- if (subs == sel.SUBS_JOINABLE || subs == sel.SUBS_ANY_JOINABLE)
+ if (subs == Select.SUBS_JOINABLE || subs == Select.SUBS_ANY_JOINABLE)
selectSubclassMappings(sel, mapping, sm, fetch);
if (sm != null)
sel.setDistinct(false);
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/strats/InValueDiscriminatorStrategy.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/strats/InValueDiscriminatorStrategy.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/strats/InValueDiscriminatorStrategy.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/strats/InValueDiscriminatorStrategy.java
Thu Sep 14 12:36:09 2006
@@ -126,20 +126,29 @@
if (subs.length == 0 && base.getJoinablePCSuperclassMapping() == null)
return null;
- // if not selecting subclasses, limit to just the given class
Column col = disc.getColumns()[0];
SQLBuffer sql = new SQLBuffer(sel.getConfiguration().
getDBDictionaryInstance());
- sql.append(sel.getColumnAlias(col, joins));
- if (!subclasses || subs.length == 0)
+ boolean outer = joins != null && joins.isOuter();
+ if (outer)
+ sql.append("(");
+ String alias = sel.getColumnAlias(col, joins);
+ sql.append(alias);
+
+ // if not selecting subclasses, limit to just the given class
+ if (!outer && (!subclasses || subs.length == 0))
return sql.append(" = ").appendValue(getDiscriminatorValue(base),
col);
+ if (outer)
+ sql.append(" IS ").appendValue(null).append(" OR ").append(alias);
sql.append(" IN (");
sql.appendValue(getDiscriminatorValue(base), col);
for (int i = 0; i < subs.length; i++)
sql.append(", ").appendValue(getDiscriminatorValue(subs[i]), col);
sql.append(")");
+ if (outer)
+ sql.append(")");
return sql;
}
}
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/AbstractResult.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/AbstractResult.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/AbstractResult.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/AbstractResult.java
Thu Sep 14 12:36:09 2006
@@ -810,6 +810,10 @@
return true;
}
+ public boolean isOuter() {
+ return false;
+ }
+
public Joins crossJoin(Table localTable, Table foreignTable) {
return this;
}
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Joins.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Joins.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Joins.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Joins.java
Thu Sep 14 12:36:09 2006
@@ -32,6 +32,11 @@
public boolean isEmpty();
/**
+ * Whether this joins path results in outer joins.
+ */
+ public boolean isOuter();
+
+ /**
* Perform a cross join on the given tables.
*/
public Joins crossJoin(Table localTable, Table foreignTable);
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/LogicalUnion.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/LogicalUnion.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/LogicalUnion.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/LogicalUnion.java
Thu Sep 14 12:36:09 2006
@@ -810,6 +810,10 @@
return sel.newJoins();
}
+ public Joins newOuterJoins() {
+ return sel.newOuterJoins();
+ }
+
public void append(SQLBuffer buf, Joins joins) {
sel.append(buf, joins);
}
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Select.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Select.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Select.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/Select.java
Thu Sep 14 12:36:09 2006
@@ -653,6 +653,11 @@
public Joins newJoins();
/**
+ * Return a new instance to use for outer joining.
+ */
+ public Joins newOuterJoins();
+
+ /**
* Append the given joins to the given buffer.
*/
public void append(SQLBuffer buf, Joins joins);
Modified:
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/SelectImpl.java
URL:
http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/SelectImpl.java?view=diff&rev=443447&r1=443446&r2=443447
==============================================================================
---
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/SelectImpl.java
(original)
+++
incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/SelectImpl.java
Thu Sep 14 12:36:09 2006
@@ -759,7 +759,7 @@
// delegate to store manager to select in same order it loads result
((JDBCStoreManager) store).select(wrapper, mapping, subclasses, null,
- null, fetch, eager, ident);
+ null, fetch, eager, ident, (_flags & OUTER) != 0);
// reset
if (hasJoins)
@@ -1626,6 +1626,10 @@
return this;
}
+ public Joins newOuterJoins() {
+ return ((PathJoins) newJoins()).setOuter(true);
+ }
+
public void append(SQLBuffer buf, Joins joins) {
if (joins == null || joins.isEmpty())
return;
@@ -1744,10 +1748,9 @@
return joins;
// record that this is an outer join set, even if it's empty
- PathJoins pj = (PathJoins) joins;
- pj.setOuter(true);
- if (joins.isEmpty())
- return joins;
+ PathJoins pj = ((PathJoins) joins).setOuter(true);
+ if (pj.isEmpty())
+ return pj;
Join join;
Join rec;
@@ -1928,7 +1931,8 @@
return false;
}
- public void setOuter(boolean outer) {
+ public PathJoins setOuter(boolean outer) {
+ return new SelectJoins(this).setOuter(true);
}
public boolean isDirty() {
@@ -1994,14 +1998,12 @@
* Represents a SQL string selected with null id.
*/
private static class NullId {
-
}
/**
* Represents a placeholder SQL string.
*/
private static class Placeholder {
-
}
/**
@@ -2269,7 +2271,8 @@
return false;
}
- public void setOuter(boolean outer) {
+ public PathJoins setOuter(boolean outer) {
+ return this;
}
public boolean isDirty() {
@@ -2345,7 +2348,8 @@
return false;
}
- public void setOuter(boolean outer) {
+ public PathJoins setOuter(boolean outer) {
+ return this;
}
public boolean isDirty() {
@@ -2452,8 +2456,9 @@
return _outer;
}
- public void setOuter(boolean outer) {
+ public PathJoins setOuter(boolean outer) {
_outer = outer;
+ return this;
}
public boolean isDirty() {
@@ -2797,14 +2802,9 @@
extends Joins {
/**
- * Return whether this join set ended with an outer join.
- */
- public boolean isOuter();
-
- /**
* Mark this as an outer joins set.
*/
- public void setOuter(boolean outer);
+ public PathJoins setOuter(boolean outer);
/**
* Return true if this instance has a path, any joins, or a variable.