use of org.apache.cayenne.Fault in project cayenne by apache.
the class DataContextPrefetchMultistepIT method testToManyToManyFirstStepUnresolved.
@Test
public void testToManyToManyFirstStepUnresolved() throws Exception {
createTwoArtistsWithExhibitsDataSet();
// since objects for the phantom prefetches are not retained explicitly, they may
// get garbage collected, and we won't be able to detect them
// so ensure ObjectStore uses a regular map just for this test
context.getObjectStore().objectMap = new HashMap<Object, Persistent>();
// Check the target ArtistExhibit objects do not exist yet
Map<String, Object> id1 = new HashMap<>();
id1.put("ARTIST_ID", 11);
id1.put("EXHIBIT_ID", 2);
ObjectId oid1 = new ObjectId("ArtistExhibit", id1);
Map<String, Object> id2 = new HashMap<>();
id2.put("ARTIST_ID", 101);
id2.put("EXHIBIT_ID", 2);
ObjectId oid2 = new ObjectId("ArtistExhibit", id2);
assertNull(context.getGraphManager().getNode(oid1));
assertNull(context.getGraphManager().getNode(oid2));
Expression e = ExpressionFactory.exp("galleryName = $name");
SelectQuery<Gallery> q = SelectQuery.query(Gallery.class, e.params(Collections.singletonMap("name", "gallery2")));
q.addPrefetch("exhibitArray.artistExhibitArray");
List<Gallery> galleries = context.select(q);
assertEquals(1, galleries.size());
Gallery g2 = galleries.get(0);
// this relationship wasn't explicitly prefetched....
Object list = g2.readPropertyDirectly("exhibitArray");
assertTrue(list instanceof Fault);
// however the target objects must be resolved
ArtistExhibit ae1 = (ArtistExhibit) context.getGraphManager().getNode(oid1);
ArtistExhibit ae2 = (ArtistExhibit) context.getGraphManager().getNode(oid2);
assertNotNull(ae1);
assertNotNull(ae2);
assertEquals(PersistenceState.COMMITTED, ae1.getPersistenceState());
assertEquals(PersistenceState.COMMITTED, ae2.getPersistenceState());
}
use of org.apache.cayenne.Fault in project cayenne by apache.
the class ColumnSelectIT method testObjectWithDisjointPrefetch.
@Test
public void testObjectWithDisjointPrefetch() {
List<Artist> result = ObjectSelect.query(Artist.class).column(Property.createSelf(Artist.class)).prefetch(Artist.PAINTING_ARRAY.disjoint()).select(context);
assertEquals(20, result.size());
for (Artist artist : result) {
assertEquals(PersistenceState.COMMITTED, artist.getPersistenceState());
Object paintingsArr = artist.readPropertyDirectly(Artist.PAINTING_ARRAY.getName());
assertFalse(paintingsArr instanceof Fault);
}
}
use of org.apache.cayenne.Fault in project cayenne by apache.
the class ColumnSelectIT method testObjectSelectWithJointPrefetch.
@Test
public void testObjectSelectWithJointPrefetch() {
List<Artist> result = ObjectSelect.query(Artist.class).column(Property.createSelf(Artist.class)).prefetch(Artist.PAINTING_ARRAY.joint()).select(context);
assertEquals(20, result.size());
for (Artist artist : result) {
assertEquals(PersistenceState.COMMITTED, artist.getPersistenceState());
Object paintingsArr = artist.readPropertyDirectly(Artist.PAINTING_ARRAY.getName());
assertFalse(paintingsArr instanceof Fault);
}
}
use of org.apache.cayenne.Fault in project cayenne by apache.
the class DataContext method currentSnapshot.
/**
* Returns a DataRow reflecting current, possibly uncommitted, object state.
* <p>
* <strong>Warning:</strong> This method will return a partial snapshot if
* an object or one of its related objects that propagate their keys to this
* object have temporary ids. DO NOT USE this method if you expect a DataRow
* to represent a complete object state.
* </p>
*
* @since 1.1
*/
public DataRow currentSnapshot(final Persistent object) {
// for a HOLLOW object return snapshot from cache
if (object.getPersistenceState() == PersistenceState.HOLLOW && object.getObjectContext() != null) {
return getObjectStore().getSnapshot(object.getObjectId());
}
ObjEntity entity = getEntityResolver().getObjEntity(object);
final ClassDescriptor descriptor = getEntityResolver().getClassDescriptor(entity.getName());
final DataRow snapshot = new DataRow(10);
snapshot.setEntityName(entity.getName());
descriptor.visitProperties(new PropertyVisitor() {
public boolean visitAttribute(AttributeProperty property) {
ObjAttribute objAttr = property.getAttribute();
// processing compound attributes correctly
snapshot.put(objAttr.getDbAttributePath(), property.readPropertyDirectly(object));
return true;
}
public boolean visitToMany(ToManyProperty property) {
// do nothing
return true;
}
public boolean visitToOne(ToOneProperty property) {
ObjRelationship rel = property.getRelationship();
// if target doesn't propagates its key value, skip it
if (rel.isSourceIndependentFromTargetChange()) {
return true;
}
Object targetObject = property.readPropertyDirectly(object);
if (targetObject == null) {
return true;
}
// to avoid unneeded fault triggering
if (targetObject instanceof Fault) {
DataRow storedSnapshot = getObjectStore().getSnapshot(object.getObjectId());
if (storedSnapshot == null) {
throw new CayenneRuntimeException("No matching objects found for ObjectId %s" + ". Object may have been deleted externally.", object.getObjectId());
}
DbRelationship dbRel = rel.getDbRelationships().get(0);
for (DbJoin join : dbRel.getJoins()) {
String key = join.getSourceName();
snapshot.put(key, storedSnapshot.get(key));
}
return true;
}
// target is resolved and we have an FK->PK to it,
// so extract it from target...
Persistent target = (Persistent) targetObject;
Map<String, Object> idParts = target.getObjectId().getIdSnapshot();
// this method.
if (idParts.isEmpty()) {
return true;
}
DbRelationship dbRel = rel.getDbRelationships().get(0);
Map<String, Object> fk = dbRel.srcFkSnapshotWithTargetSnapshot(idParts);
snapshot.putAll(fk);
return true;
}
});
// process object id map
// we should ignore any object id values if a corresponding attribute
// is a part of relationship "toMasterPK", since those values have been
// set above when db relationships where processed.
Map<String, Object> thisIdParts = object.getObjectId().getIdSnapshot();
if (thisIdParts != null) {
// put only those that do not exist in the map
for (Map.Entry<String, Object> entry : thisIdParts.entrySet()) {
String nextKey = entry.getKey();
if (!snapshot.containsKey(nextKey)) {
snapshot.put(nextKey, entry.getValue());
}
}
}
return snapshot;
}
use of org.apache.cayenne.Fault in project cayenne by apache.
the class ObjectDiff method isNoop.
/**
* Checks whether at least a single property is modified.
*/
@Override
public boolean isNoop() {
// if we have no baseline to compare with, assume that there are changes
if (snapshot == null) {
return false;
}
if (flatIds != null && !flatIds.isEmpty()) {
return false;
}
if (phantomFks != null && !phantomFks.isEmpty()) {
return false;
}
int state = object.getPersistenceState();
if (state == PersistenceState.NEW || state == PersistenceState.DELETED) {
return false;
}
// check phantom mods
final boolean[] modFound = new boolean[1];
getClassDescriptor().visitProperties(new PropertyVisitor() {
@Override
public boolean visitAttribute(AttributeProperty property) {
Object oldValue = snapshot.get(property.getName());
Object newValue = property.readProperty(object);
if (!Util.nullSafeEquals(oldValue, newValue)) {
modFound[0] = true;
}
return !modFound[0];
}
@Override
public boolean visitToMany(ToManyProperty property) {
// flattened changes
return true;
}
@Override
public boolean visitToOne(ToOneProperty property) {
if (arcSnapshot == null) {
return true;
}
Object newValue = property.readPropertyDirectly(object);
if (newValue instanceof Fault) {
return true;
}
Object oldValue = arcSnapshot.get(property.getName());
if (!Util.nullSafeEquals(oldValue, newValue != null ? ((Persistent) newValue).getObjectId() : null)) {
modFound[0] = true;
}
return !modFound[0];
}
});
return !modFound[0];
}
Aggregations