You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cayenne.apache.org by aa...@apache.org on 2006/05/28 00:48:25 UTC

svn commit: r409893 - in /incubator/cayenne/main/trunk/cayenne/cayenne-java/src: cayenne/java/org/objectstyle/cayenne/wocompat/ tests/java/org/objectstyle/cayenne/wocompat/ tests/resources/wotests/fetchspec.eomodeld/

Author: aadamchik
Date: Sat May 27 15:48:24 2006
New Revision: 409893

URL: http://svn.apache.org/viewvc?rev=409893&view=rev
Log:
CAY-336 - fixing EOQualifier import for DB attributes that have no ObjAttributes

Added:
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/java/org/objectstyle/cayenne/wocompat/EOQueryTst.java
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/DiagramLayout
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.fspec
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.plist
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity2.plist
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/index.eomodeld
Modified:
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOModelProcessor.java
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOObjEntity.java
    incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOQuery.java

Modified: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOModelProcessor.java
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOModelProcessor.java?rev=409893&r1=409892&r2=409893&view=diff
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOModelProcessor.java (original)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOModelProcessor.java Sat May 27 15:48:24 2006
@@ -102,7 +102,6 @@
                 }
 
                 String entityName = object.toString();
-
                 return entityName.startsWith("EO") && entityName.endsWith("Prototypes");
             }
         };
@@ -227,7 +226,6 @@
             Iterator queries = helper.queryNames(name);
             while (queries.hasNext()) {
                 String queryName = (String) queries.next();
-                System.out.println("Processing FetchSpecification: " + queryName);
                 EOObjEntity entity = (EOObjEntity) dataMap.getObjEntity(name);
                 makeQuery(helper, entity, queryName);
             }
@@ -294,6 +292,7 @@
 
         // create ObjEntity
         EOObjEntity objEntity = new EOObjEntity(name);
+        objEntity.setEoMap(entityPlist);
         objEntity.setIsClientEntity(generateClientClass);
         String parent = (String) entityPlist.get("parent");
         objEntity.setClassName(helper.entityClass(name, generateClientClass));

Modified: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOObjEntity.java
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOObjEntity.java?rev=409893&r1=409892&r2=409893&view=diff
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOObjEntity.java (original)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOObjEntity.java Sat May 27 15:48:24 2006
@@ -58,9 +58,16 @@
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
 import java.util.Map;
+import java.util.StringTokenizer;
 
+import org.apache.commons.collections.Transformer;
+import org.objectstyle.cayenne.CayenneRuntimeException;
 import org.objectstyle.cayenne.exp.Expression;
+import org.objectstyle.cayenne.exp.ExpressionFactory;
+import org.objectstyle.cayenne.map.Entity;
 import org.objectstyle.cayenne.map.ObjEntity;
 import org.objectstyle.cayenne.query.Query;
 
@@ -81,16 +88,16 @@
     protected boolean isAbstractEntity;
 
     private Collection filteredQueries;
+    private Map eoMap;
 
     public EOObjEntity() {
         super();
     }
 
-   
     public EOObjEntity(String s) {
         super(s);
-    } 
-    
+    }
+
     /**
      * Sets the the superclass state.
      * 
@@ -190,7 +197,8 @@
             Collection queries = getDataMap().getQueries();
             if (queries.isEmpty()) {
                 filteredQueries = Collections.EMPTY_LIST;
-            } else {
+            }
+            else {
                 Map params = Collections.singletonMap("root", EOObjEntity.this);
                 Expression filter = Expression
                         .fromString("root = $root")
@@ -202,5 +210,105 @@
 
         return filteredQueries;
     }
-    
+
+    /**
+     * Overrides super to support translation of EO attributes that have no ObjAttributes.
+     * 
+     * @since 1.2
+     */
+    public Expression translateToDbPath(Expression expression) {
+
+        if (expression == null) {
+            return null;
+        }
+
+        if (getDbEntity() == null) {
+            throw new CayenneRuntimeException(
+                    "Can't translate expression to DB_PATH, no DbEntity for '"
+                            + getName()
+                            + "'.");
+        }
+
+        // converts all OBJ_PATH expressions to DB_PATH expressions
+        // and pass control to the DB entity
+        return expression.transform(new DBPathConverter());
+    }
+
+    /**
+     * @since 1.2
+     */
+    // TODO: andrus, 5/27/2006 - make public after 1.2. Also maybe move entity
+    // initialization code from EOModelProcessor to this class, kind of like EOQuery does.
+    Map getEoMap() {
+        return eoMap;
+    }
+
+    /**
+     * @since 1.2
+     */
+    // TODO: andrus, 5/27/2006 - make public after 1.2. Also maybe move entity
+    // initialization code from EOModelProcessor to this class, kind of like EOQuery does.
+    void setEoMap(Map eoMap) {
+        this.eoMap = eoMap;
+    }
+
+    final class DBPathConverter implements Transformer {
+
+        public Object transform(Object input) {
+
+            if (!(input instanceof Expression)) {
+                return input;
+            }
+
+            Expression expression = (Expression) input;
+
+            if (expression.getType() != Expression.OBJ_PATH) {
+                return input;
+            }
+
+            // convert obj_path to db_path
+
+            StringBuffer buffer = new StringBuffer();
+            EOObjEntity entity = EOObjEntity.this;
+            StringTokenizer toks = new StringTokenizer(expression.toString(), ".");
+            while (toks.hasMoreTokens() && entity != null) {
+                String chunk = toks.nextToken();
+
+                if (toks.hasMoreTokens()) {
+                    // this is a relationship
+                    if (buffer.length() > 0) {
+                        buffer.append(Entity.PATH_SEPARATOR);
+                    }
+
+                    buffer.append(chunk);
+
+                    entity = (EOObjEntity) entity
+                            .getRelationship(chunk)
+                            .getTargetEntity();
+                }
+                // this is an attribute...
+                else {
+
+                    List attributes = (List) entity.getEoMap().get("attributes");
+                    Iterator it = attributes.iterator();
+                    while (it.hasNext()) {
+                        Map attribute = (Map) it.next();
+                        if (chunk.equals(attribute.get("name"))) {
+
+                            if (buffer.length() > 0) {
+                                buffer.append(Entity.PATH_SEPARATOR);
+                            }
+
+                            buffer.append(attribute.get("columnName"));
+                            break;
+                        }
+                    }
+                }
+            }
+
+            Expression exp = ExpressionFactory.expressionOfType(Expression.DB_PATH);
+            exp.setOperand(0, buffer.toString());
+            return exp;
+        }
+    }
 }

Modified: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOQuery.java
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOQuery.java?rev=409893&r1=409892&r2=409893&view=diff
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOQuery.java (original)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/cayenne/java/org/objectstyle/cayenne/wocompat/EOQuery.java Sat May 27 15:48:24 2006
@@ -55,17 +55,17 @@
  */
 package org.objectstyle.cayenne.wocompat;
 
+import java.util.ArrayList;
 import java.util.Collection;
 import java.util.HashMap;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
-import java.util.ArrayList;
 
 import org.objectstyle.cayenne.exp.Expression;
+import org.objectstyle.cayenne.exp.ExpressionException;
 import org.objectstyle.cayenne.exp.ExpressionFactory;
 import org.objectstyle.cayenne.exp.ExpressionParameter;
-import org.objectstyle.cayenne.exp.ExpressionException;
 import org.objectstyle.cayenne.exp.parser.ASTObjPath;
 import org.objectstyle.cayenne.map.Entity;
 import org.objectstyle.cayenne.map.ObjAttribute;
@@ -78,7 +78,7 @@
  * Cayenne SelectQuery to provide access to the extra information of WebObjects
  * EOFetchSpecification.
  * 
- * @author Andrei Adamchik
+ * @author Andrus Adamchik
  * @since 1.1
  */
 public class EOQuery extends SelectQuery {
@@ -129,7 +129,7 @@
             }
         }
 
-        //qualifiers
+        // qualifiers
         Map qualifierMap = (Map) plistMap.get("qualifier");
         if (qualifierMap != null && !qualifierMap.isEmpty()) {
             this.setQualifier(makeQualifier(qualifierMap));
@@ -253,7 +253,9 @@
             return null;
         }
 
-        return EOFetchSpecificationParser.makeQualifier(qualifierMap);
+        return EOFetchSpecificationParser.makeQualifier(
+                (EOObjEntity) getRoot(),
+                qualifierMap);
     }
 
     /**
@@ -266,14 +268,14 @@
     static class EOFetchSpecificationParser {
 
         // selector strings
-        public static final String IS_EQUAL_TO = "isEqualTo:";
-        public static final String IS_NOT_EQUAL_TO = "isNotEqualTo:";
-        public static final String IS_LIKE = "isLike:";
-        public static final String CASE_INSENSITIVE_LIKE = "isCaseInsensitiveLike:";
-        public static final String IS_LESS_THAN = "isLessThan:";
-        public static final String IS_LESS_THAN_OR_EQUAL_TO = "isLessThanOrEqualTo:";
-        public static final String IS_GREATER_THAN = "isGreaterThan:";
-        public static final String IS_GREATER_THAN_OR_EQUAL_TO = "isGreaterThanOrEqualTo:";
+        static final String IS_EQUAL_TO = "isEqualTo:";
+        static final String IS_NOT_EQUAL_TO = "isNotEqualTo:";
+        static final String IS_LIKE = "isLike:";
+        static final String CASE_INSENSITIVE_LIKE = "isCaseInsensitiveLike:";
+        static final String IS_LESS_THAN = "isLessThan:";
+        static final String IS_LESS_THAN_OR_EQUAL_TO = "isLessThanOrEqualTo:";
+        static final String IS_GREATER_THAN = "isGreaterThan:";
+        static final String IS_GREATER_THAN_OR_EQUAL_TO = "isGreaterThanOrEqualTo:";
 
         private static HashMap selectorToExpressionBridge;
 
@@ -283,7 +285,7 @@
          * 
          * @return HashMap of Expression types, keyed by the corresponding selector name
          */
-        public static HashMap selectorToExpressionBridge() {
+        static HashMap selectorToExpressionBridge() {
             if (null == selectorToExpressionBridge) {
                 // initialize selectorToExpressionBridge
                 selectorToExpressionBridge = new HashMap(8);
@@ -313,7 +315,7 @@
          * @param qualifier - a Map containing the qualifier settings
          * @return boolean indicating whether the qualifier is "aggregate" qualifier
          */
-        public static boolean isAggregate(Map qualifier) {
+        static boolean isAggregate(Map qualifier) {
             boolean result = true;
 
             String theClass = (String) qualifier.get("class");
@@ -336,7 +338,7 @@
          * @param qualifierMap - a Map containing the qualifier settings to examine.
          * @return int Expression type
          */
-        public static int expressionTypeForQualifier(Map qualifierMap) {
+        static int expressionTypeForQualifier(Map qualifierMap) {
             // get selector
             String selector = (String) qualifierMap.get("selectorName");
             return expressionTypeForSelector(selector);
@@ -349,7 +351,7 @@
          * @param selector - a String containing the selector name.
          * @return int Expression type
          */
-        public static int expressionTypeForSelector(String selector) {
+        static int expressionTypeForSelector(String selector) {
             Integer expType = (Integer) selectorToExpressionBridge().get(selector);
             return (expType != null ? expType.intValue() : -1);
         }
@@ -361,7 +363,7 @@
          * @param qualifierMap - containing the qualifier to examine
          * @return int aggregate Expression type
          */
-        public static int aggregateExpressionClassForQualifier(Map qualifierMap) {
+        static int aggregateExpressionClassForQualifier(Map qualifierMap) {
             String qualifierClass = (String) qualifierMap.get("class");
             if (qualifierClass != null) {
                 if (qualifierClass.equalsIgnoreCase("EOAndQualifier")) {
@@ -386,22 +388,21 @@
          * @param qualifierMap - Map representation of EOFetchSpecification
          * @return Expression translation of the EOFetchSpecification
          */
-        public static Expression makeQualifier(Map qualifierMap) {
+        static Expression makeQualifier(EOObjEntity entity, Map qualifierMap) {
             if (isAggregate(qualifierMap)) {
                 // the fetch specification has more than one qualifier
                 int aggregateClass = aggregateExpressionClassForQualifier(qualifierMap); // AND,
-                                                                                         // OR,
-                                                                                         // NOT
+                // OR,
+                // NOT
 
                 if (aggregateClass == Expression.NOT) {
                     // NOT qualifiers only have one child, keyed with "qualifier"
                     Map child = (Map) qualifierMap.get("qualifier");
                     // build the child expression
-                    Expression childExp = makeQualifier(child);
+                    Expression childExp = makeQualifier(entity, child);
 
                     return childExp.notExp(); // add the "not" clause and return the
-                                              // result
-
+                    // result
                 }
                 else {
                     // AND, OR qualifiers can have multiple children, keyed with
@@ -413,7 +414,7 @@
                         // build an Expression for each child
                         Iterator it = children.iterator();
                         while (it.hasNext()) {
-                            Expression childExp = makeQualifier((Map) it.next());
+                            Expression childExp = makeQualifier(entity, (Map) it.next());
                             childExpressions.add(childExp);
                         }
                         // join the child expressions and return the result
@@ -425,8 +426,7 @@
             } // end if isAggregate(qualifierMap)...
 
             // the query has a single qualifier
-            //  get expression selector type
-            int expType = expressionTypeForQualifier(qualifierMap); // =, like, >. <. etc.
+            // get expression selector type
             String qualifierClass = (String) qualifierMap.get("class");
 
             // the key or key path we're comparing
@@ -452,8 +452,8 @@
                 if (value instanceof Map) {
                     Map valueMap = (Map) value;
                     String objClass = (String) valueMap.get("class"); // can be a
-                                                                      // qualifier class
-                                                                      // or java type
+                    // qualifier class
+                    // or java type
 
                     if ("EOQualifierVariable".equals(objClass)
                             && valueMap.containsKey("_key")) {
@@ -484,27 +484,27 @@
                 } // end if (value instanceof Map) else...
             }
 
-            // Now create the correct Expression type for the comparison class
-            // and return it.
-            switch (expType) {
-                case Expression.EQUAL_TO:
-                    return ExpressionFactory.matchExp(key, comparisonValue);
-                case Expression.NOT_EQUAL_TO:
-                    return ExpressionFactory.noMatchExp(key, comparisonValue);
-                case Expression.LIKE:
-                    return ExpressionFactory.likeExp(key, comparisonValue);
-                case Expression.LIKE_IGNORE_CASE:
-                    return ExpressionFactory.likeIgnoreCaseExp(key, comparisonValue);
-                case Expression.LESS_THAN:
-                    return ExpressionFactory.lessExp(key, comparisonValue);
-                case Expression.LESS_THAN_EQUAL_TO:
-                    return ExpressionFactory.lessOrEqualExp(key, comparisonValue);
-                case Expression.GREATER_THAN:
-                    return ExpressionFactory.greaterExp(key, comparisonValue);
-                case Expression.GREATER_THAN_EQUAL_TO:
-                    return ExpressionFactory.greaterOrEqualExp(key, comparisonValue);
-                default:
-                    return null;
+            // check whether the key is an object path; if at least one component is not,
+            // switch to db path..
+
+            Expression keyExp = Expression.fromString(key);
+            try {
+                entity.lastPathComponent(keyExp);
+            }
+            catch (ExpressionException e) {
+                keyExp = entity.translateToDbPath(keyExp);
+            }
+
+            try {
+                Expression exp = ExpressionFactory
+                        .expressionOfType(expressionTypeForQualifier(qualifierMap));
+
+                exp.setOperand(0, keyExp);
+                exp.setOperand(1, comparisonValue);
+                return exp;
+            }
+            catch (ExpressionException e) {
+                return null;
             }
         }
     }

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/java/org/objectstyle/cayenne/wocompat/EOQueryTst.java
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/java/org/objectstyle/cayenne/wocompat/EOQueryTst.java?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/java/org/objectstyle/cayenne/wocompat/EOQueryTst.java (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/java/org/objectstyle/cayenne/wocompat/EOQueryTst.java Sat May 27 15:48:24 2006
@@ -0,0 +1,86 @@
+/* ====================================================================
+ * 
+ * The ObjectStyle Group Software License, version 1.1
+ * ObjectStyle Group - http://objectstyle.org/
+ * 
+ * Copyright (c) 2002-2005, Andrei (Andrus) Adamchik and individual authors
+ * of the software. 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 independent contributors
+ *    and hosted on ObjectStyle Group web site (http://objectstyle.org/)."
+ *    Alternately, this acknowlegement may appear in the software itself,
+ *    if and wherever such third-party acknowlegements normally appear.
+ * 
+ * 4. The names "ObjectStyle Group" and "Cayenne" must not be used to endorse
+ *    or promote products derived from this software without prior written
+ *    permission. For written permission, email
+ *    "andrus at objectstyle dot org".
+ * 
+ * 5. Products derived from this software may not be called "ObjectStyle"
+ *    or "Cayenne", nor may "ObjectStyle" or "Cayenne" appear in their
+ *    names without prior written permission.
+ * 
+ * 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 THE OBJECTSTYLE GROUP 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 and hosted on ObjectStyle Group web site.  For more
+ * information on the ObjectStyle Group, please see
+ * <http://objectstyle.org/>.
+ */
+package org.objectstyle.cayenne.wocompat;
+
+import java.util.Map;
+
+import junit.framework.TestCase;
+
+import org.objectstyle.cayenne.map.DataMap;
+
+public class EOQueryTst extends TestCase {
+
+    public void testConstructor() throws Exception {
+
+        EOModelProcessor processor = new EOModelProcessor();
+        DataMap map = processor.loadEOModel("wotests/fetchspec.eomodeld");
+
+        Map fspecMap = (Map) PropertyListSerialization.propertyListFromStream(getClass()
+                .getClassLoader()
+                .getResourceAsStream("wotests/fetchspec.eomodeld/Entity1.fspec"));
+        assertNotNull(fspecMap);
+        assertNotNull(fspecMap.get("E1FS1"));
+
+        EOQuery query = new EOQuery(map.getObjEntity("Entity1"), (Map) fspecMap
+                .get("E1FS1"));
+        assertNull(query.getName());
+
+        assertNotNull(query.getQualifier());
+        assertEquals(
+                "(name = \"aa\") and (db:ID >= 7) and ((e2.name = \"bb\") or (db:e2.ID != 5))",
+                query.getQualifier().toString());
+    }
+}

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/DiagramLayout
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/DiagramLayout?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/DiagramLayout (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/DiagramLayout Sat May 27 15:48:24 2006
@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict/>
+</plist>

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.fspec
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.fspec?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.fspec (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.fspec Sat May 27 15:48:24 2006
@@ -0,0 +1,49 @@
+{
+    E1FS1 = {
+        class = EOFetchSpecification; 
+        entityName = Entity1; 
+        fetchLimit = 500; 
+        isDeep = YES; 
+        locksObjects = YES; 
+        prefetchingRelationshipKeyPaths = (e2); 
+        qualifier = {
+            class = EOAndQualifier; 
+            qualifiers = (
+                {
+                    class = EOKeyValueQualifier; 
+                    key = name; 
+                    selectorName = "isEqualTo:"; 
+                    value = aa; 
+                }, 
+                {
+                    class = EOKeyValueQualifier; 
+                    key = id; 
+                    selectorName = "isGreaterThanOrEqualTo:"; 
+                    value = {class = NSNumber; value = 7; }; 
+                }, 
+                {
+                    class = EOOrQualifier; 
+                    qualifiers = (
+                        {
+                            class = EOKeyValueQualifier; 
+                            key = "e2.name"; 
+                            selectorName = "isEqualTo:"; 
+                            value = bb; 
+                        }, 
+                        {
+                            class = EOKeyValueQualifier; 
+                            key = "e2.id"; 
+                            selectorName = "isNotEqualTo:"; 
+                            value = {class = NSNumber; value = 5; }; 
+                        }
+                    ); 
+                }
+            ); 
+        }; 
+        rawRowKeyPaths = (); 
+        refreshesRefetchedObjects = YES; 
+        requiresAllQualifierBindingVariables = YES; 
+        sortOrderings = ({class = EOSortOrdering; key = name; selectorName = "compareDescending:"; }); 
+        usesDistinct = YES; 
+    }; 
+}

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.plist
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.plist?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.plist (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity1.plist Sat May 27 15:48:24 2006
@@ -0,0 +1,42 @@
+{
+    attributes = (
+        {
+            allowsNull = Y; 
+            columnName = "E2_ID"; 
+            externalType = int; 
+            name = "e2_id"; 
+            valueClassName = NSNumber; 
+            valueType = i; 
+        }, 
+        {
+            columnName = ID; 
+            externalType = int; 
+            name = id; 
+            valueClassName = NSNumber; 
+            valueType = i; 
+        }, 
+        {
+            allowsNull = Y; 
+            columnName = NAME; 
+            externalType = varchar; 
+            name = name; 
+            valueClassName = NSString; 
+            width = 255; 
+        }
+    ); 
+    attributesUsedForLocking = (id, "e2_id"); 
+    className = "org.example.Entity1"; 
+    classProperties = (name, "e2_id", e2); 
+    externalName = ENTITY1; 
+    name = Entity1; 
+    primaryKeyAttributes = (id); 
+    relationships = (
+        {
+            destination = Entity2; 
+            isToMany = N; 
+            joinSemantic = EOInnerJoin; 
+            joins = ({destinationAttribute = id; sourceAttribute = "e2_id"; }); 
+            name = e2; 
+        }
+    ); 
+}

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity2.plist
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity2.plist?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity2.plist (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/Entity2.plist Sat May 27 15:48:24 2006
@@ -0,0 +1,36 @@
+{
+    attributes = (
+        {
+            columnName = ID; 
+            externalType = int; 
+            name = id; 
+            valueClassName = NSNumber; 
+            valueType = i; 
+        }, 
+        {
+            allowsNull = Y; 
+            columnName = NAME; 
+            externalType = varchar; 
+            name = name; 
+            valueClassName = NSString; 
+            width = 255; 
+        }
+    ); 
+    attributesUsedForLocking = (id, name); 
+    className = "org.example.Entity2"; 
+    classProperties = (name, e1s); 
+    externalName = ENTITY2; 
+    fetchSpecificationDictionary = {}; 
+    name = Entity2; 
+    primaryKeyAttributes = (id); 
+    relationships = (
+        {
+            deleteRule = EODeleteRuleCascade; 
+            destination = Entity1; 
+            isToMany = Y; 
+            joinSemantic = EOInnerJoin; 
+            joins = ({destinationAttribute = "e2_id"; sourceAttribute = id; }); 
+            name = e1s; 
+        }
+    ); 
+}

Added: incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/index.eomodeld
URL: http://svn.apache.org/viewvc/incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/index.eomodeld?rev=409893&view=auto
==============================================================================
--- incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/index.eomodeld (added)
+++ incubator/cayenne/main/trunk/cayenne/cayenne-java/src/tests/resources/wotests/fetchspec.eomodeld/index.eomodeld Sat May 27 15:48:24 2006
@@ -0,0 +1,8 @@
+{
+    EOModelVersion = "2.1"; 
+    adaptorName = None; 
+    entities = (
+        {className = "org.example.Entity1"; name = Entity1; }, 
+        {className = "org.example.Entity2"; name = Entity2; }
+    ); 
+}