KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > objectstyle > cayenne > service > ObjectDataContext


1 /* ====================================================================
2  *
3  * The ObjectStyle Group Software License, version 1.1
4  * ObjectStyle Group - http://objectstyle.org/
5  *
6  * Copyright (c) 2002-2005, Andrei (Andrus) Adamchik and individual authors
7  * of the software. All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * 1. Redistributions of source code must retain the above copyright
14  * notice, this list of conditions and the following disclaimer.
15  *
16  * 2. Redistributions in binary form must reproduce the above copyright
17  * notice, this list of conditions and the following disclaimer in
18  * the documentation and/or other materials provided with the
19  * distribution.
20  *
21  * 3. The end-user documentation included with the redistribution, if any,
22  * must include the following acknowlegement:
23  * "This product includes software developed by independent contributors
24  * and hosted on ObjectStyle Group web site (http://objectstyle.org/)."
25  * Alternately, this acknowlegement may appear in the software itself,
26  * if and wherever such third-party acknowlegements normally appear.
27  *
28  * 4. The names "ObjectStyle Group" and "Cayenne" must not be used to endorse
29  * or promote products derived from this software without prior written
30  * permission. For written permission, email
31  * "andrus at objectstyle dot org".
32  *
33  * 5. Products derived from this software may not be called "ObjectStyle"
34  * or "Cayenne", nor may "ObjectStyle" or "Cayenne" appear in their
35  * names without prior written permission.
36  *
37  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
38  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
39  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
40  * DISCLAIMED. IN NO EVENT SHALL THE OBJECTSTYLE GROUP OR
41  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
42  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
43  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
44  * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
45  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
46  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
47  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
48  * SUCH DAMAGE.
49  * ====================================================================
50  *
51  * This software consists of voluntary contributions made by many
52  * individuals and hosted on ObjectStyle Group web site. For more
53  * information on the ObjectStyle Group, please see
54  * <http://objectstyle.org/>.
55  */

56
57 package org.objectstyle.cayenne.service;
58
59 import java.util.ArrayList JavaDoc;
60 import java.util.Collection JavaDoc;
61 import java.util.Collections JavaDoc;
62 import java.util.Iterator JavaDoc;
63 import java.util.List JavaDoc;
64 import java.util.Map JavaDoc;
65
66 import org.objectstyle.cayenne.CayenneRuntimeException;
67 import org.objectstyle.cayenne.DataObject;
68 import org.objectstyle.cayenne.ObjectId;
69 import org.objectstyle.cayenne.PersistenceState;
70 import org.objectstyle.cayenne.Persistent;
71 import org.objectstyle.cayenne.QueryResponse;
72 import org.objectstyle.cayenne.access.DataContext;
73 import org.objectstyle.cayenne.access.DataDomain;
74 import org.objectstyle.cayenne.access.DataRowStore;
75 import org.objectstyle.cayenne.access.HierarchicalObjectContext;
76 import org.objectstyle.cayenne.access.ObjectStore;
77 import org.objectstyle.cayenne.access.OperationObserver;
78 import org.objectstyle.cayenne.access.PersistenceContext;
79 import org.objectstyle.cayenne.access.Transaction;
80 import org.objectstyle.cayenne.graph.GraphDiff;
81 import org.objectstyle.cayenne.map.EntityResolver;
82 import org.objectstyle.cayenne.map.ObjEntity;
83 import org.objectstyle.cayenne.query.GenericSelectQuery;
84 import org.objectstyle.cayenne.query.NamedQuery;
85 import org.objectstyle.cayenne.query.Query;
86 import org.objectstyle.cayenne.query.QueryChain;
87 import org.objectstyle.cayenne.query.QueryExecutionPlan;
88
89 /**
90  * A temporary subclass of DataContext that implements ObjectContext interface. Used to
91  * test ObjectContext support without disturbing current DataContext.
92  *
93  * @since 1.2
94  * @author Andrus Adamchik
95  */

96 // TODO: merge into DataContext
97
class ObjectDataContext extends DataContext implements HierarchicalObjectContext {
98
99     PersistenceContext parentContext;
100     EntityResolver entityResolver;
101
102     /**
103      * Initializes ObjectDataContext obtaining settings from parent DataDomain.
104      */

105     ObjectDataContext(DataDomain parentDomain) {
106         this.parentContext = parentDomain;
107         super.parent = parentDomain;
108         this.entityResolver = parentDomain.getEntityResolver();
109
110         DataRowStore cache = parentDomain.isSharedCacheEnabled() ? parentDomain
111                 .getSharedSnapshotCache() : new DataRowStore(
112                 parentDomain.getName(),
113                 parentDomain.getProperties());
114
115         super.objectStore = new ObjectStore(cache);
116     }
117
118     ObjectDataContext(PersistenceContext parentContext, EntityResolver entityResolver,
119             DataRowStore cache) {
120         this.parentContext = parentContext;
121         this.entityResolver = entityResolver;
122
123         // if parent is a DataDomain, init it as "old" parent for backwards
124
// compatibility...
125
if (parentContext instanceof DataDomain) {
126             super.parent = (DataDomain) parentContext;
127         }
128
129         super.objectStore = new ObjectStore(cache);
130     }
131
132     // ==== START: DataContext compatibility code... need to merge to DataContext
133
// --------------------------------------------------------------------------
134

135     public EntityResolver getEntityResolver() {
136         // TODO: ready to be moved to DataContext
137
return entityResolver;
138     }
139
140     public int[] performNonSelectingQuery(Query query) {
141         // channel to the right implementation
142
return performUpdateQuery((QueryExecutionPlan) query);
143     }
144
145     public List JavaDoc performQuery(GenericSelectQuery query) {
146         // channel through a new implementation...
147
return performSelectQuery((QueryExecutionPlan) query);
148     }
149
150     /**
151      * @deprecated since 1.2 as QueryChains are now possible.
152      */

153     public void performQueries(Collection JavaDoc queries, OperationObserver observer) {
154         QueryChain query = new QueryChain(queries);
155         getParentContext().performQuery(query.resolve(getEntityResolver()), observer);
156     }
157
158     /**
159      * @deprecated since 1.2 as QueryChains are now possible.
160      */

161     public void performQueries(
162             Collection JavaDoc queries,
163             OperationObserver observer,
164             Transaction transaction) {
165
166         QueryChain query = new QueryChain(queries);
167         getParentContext().performQuery(
168                 query.resolve(getEntityResolver()),
169                 observer,
170                 transaction);
171     }
172
173     public int[] performNonSelectingQuery(String JavaDoc queryName, Map JavaDoc parameters) {
174         return performUpdateQuery(new NamedQuery(queryName, parameters));
175     }
176
177     public int[] performNonSelectingQuery(String JavaDoc queryName) {
178         return performUpdateQuery(new NamedQuery(queryName));
179     }
180
181     public List JavaDoc performQuery(String JavaDoc queryName, boolean refresh) {
182         // TODO: refresh is not handled...
183
return performSelectQuery(new NamedQuery(queryName));
184     }
185
186     public void commitChanges() throws CayenneRuntimeException {
187         commit();
188     }
189
190     // ==== END: DataContext compatibility code... need to merge to DataContext
191
// --------------------------------------------------------------------------
192

193     DataObject createAndRegisterNewObject(ObjectId id) {
194         if (id.getObjectClass() == null) {
195             throw new NullPointerException JavaDoc("DataObject class can't be null.");
196         }
197
198         ObjEntity entity = getEntityResolver().lookupObjEntity(id.getObjectClass());
199         if (entity == null) {
200             throw new IllegalArgumentException JavaDoc("Class is not mapped with Cayenne: "
201                     + id.getObjectClass().getName());
202         }
203
204         DataObject dataObject = null;
205         try {
206             dataObject = (DataObject) id.getObjectClass().newInstance();
207         }
208         catch (Exception JavaDoc ex) {
209             throw new CayenneRuntimeException("Error instantiating object.", ex);
210         }
211
212         dataObject.setObjectId(id);
213         registerNewObject(dataObject);
214         return dataObject;
215     }
216
217     public GraphDiff commit() throws CayenneRuntimeException {
218         return new ObjectDataContextCommitAction().commit(this);
219     }
220
221     public PersistenceContext getParentContext() {
222         return parentContext;
223     }
224
225     public void deleteObject(Persistent object) {
226
227         // TODO: only supports DataObject subclasses
228
if (object != null && !(object instanceof DataObject)) {
229             throw new IllegalArgumentException JavaDoc(
230                     this
231                             + ": this implementation of ObjectContext only supports full DataObjects. Object "
232                             + object
233                             + " is not supported.");
234         }
235
236         super.deleteObject((DataObject) object);
237     }
238
239     /**
240      * Creates and registers new persistent object.
241      */

242     public Persistent newObject(Class JavaDoc persistentClass) {
243         if (persistentClass == null) {
244             throw new NullPointerException JavaDoc("Null 'persistentClass'");
245         }
246
247         // TODO: only supports DataObject subclasses
248
if (!DataObject.class.isAssignableFrom(persistentClass)) {
249             throw new IllegalArgumentException JavaDoc(
250                     this
251                             + ": this implementation of ObjectContext only supports full DataObjects. Class "
252                             + persistentClass
253                             + " is invalid.");
254         }
255
256         return super.createAndRegisterNewObject(persistentClass);
257     }
258
259     /**
260      * Returns a collection of all uncommitted registered objects.
261      */

262     public Collection JavaDoc uncommittedObjects() {
263
264         int len = getObjectStore().registeredObjectsCount();
265         if (len == 0) {
266             return Collections.EMPTY_LIST;
267         }
268
269         // guess target collection size
270
Collection JavaDoc objects = new ArrayList JavaDoc(len > 100 ? len / 2 : len);
271
272         Iterator JavaDoc it = getObjectStore().getObjectIterator();
273         while (it.hasNext()) {
274             Persistent object = (Persistent) it.next();
275             int state = object.getPersistenceState();
276             if (state == PersistenceState.MODIFIED
277                     || state == PersistenceState.NEW
278                     || state == PersistenceState.DELETED) {
279
280                 objects.add(object);
281             }
282         }
283
284         return objects;
285     }
286
287     public QueryResponse performGenericQuery(QueryExecutionPlan query) {
288         if (this.getParentContext() == null) {
289             throw new CayenneRuntimeException(
290                     "Can't run query - parent PersistenceContext is not set.");
291         }
292
293         return new PersistenceContextQueryAction(getEntityResolver()).performMixed(
294                 getParentContext(),
295                 query);
296     }
297
298     public int[] performUpdateQuery(QueryExecutionPlan query) {
299         if (this.getParentContext() == null) {
300             throw new CayenneRuntimeException(
301                     "Can't run query - parent PersistenceContext is not set.");
302         }
303
304         return new PersistenceContextQueryAction(getEntityResolver())
305                 .performNonSelectingQuery(getParentContext(), query);
306     }
307
308     public List JavaDoc performSelectQuery(QueryExecutionPlan query) {
309         if (this.getParentContext() == null) {
310             throw new CayenneRuntimeException(
311                     "Can't run query - parent PersistenceContext is not set.");
312         }
313
314         return new ObjectDataContextSelectAction(this).performQuery(query);
315     }
316
317     // *** Unfinished stuff
318

319     public void objectWillRead(Persistent object, String JavaDoc property) {
320         // TODO: implement me
321
throw new CayenneRuntimeException(
322                 "Persistent interface methods are not yet handled.");
323     }
324
325     public void objectWillWrite(
326             Persistent object,
327             String JavaDoc property,
328             Object JavaDoc oldValue,
329             Object JavaDoc newValue) {
330         // TODO: implement me
331
throw new CayenneRuntimeException(
332                 "Persistent interface methods are not yet handled.");
333     }
334 }
335
Popular Tags