blob: 2aa6f1e1a55d6a186d38a67df007033d46ac9771 [file] [log] [blame]
/*
* 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.openjpa.persistence.detach;
import java.util.Collection;
import java.util.HashSet;
import org.apache.openjpa.conf.Compatibility;
import org.apache.openjpa.meta.ClassMetaData;
import org.apache.openjpa.meta.MetaDataRepository;
import org.apache.openjpa.meta.ValueMetaData;
import org.apache.openjpa.persistence.OpenJPAEntityManager;
import org.apache.openjpa.persistence.test.SingleEMFTestCase;
public class TestDetachNoCascade extends SingleEMFTestCase {
OpenJPAEntityManager em;
int id = 0;
Compatibility compat;
Entity1 e1;
Entity7 e7;
Entity14 e14;
Collection<Object> allEntities = new HashSet<>();
@Override
public void setUp() throws Exception {
setUp(Entity1.class, // references Entity14
Entity7.class,
Entity14.class,
CLEAR_TABLES);
assertNotNull(emf);
em = emf.createEntityManager();
assertNotNull(em);
compat = emf.getConfiguration().getCompatibilityInstance();
compat.setFlushBeforeDetach(true);
compat.setCopyOnDetach(false);
compat.setCascadeWithDetach(false);
}
private void create(int id) {
allEntities.clear();
e1 = new Entity1(id,"entity1");
allEntities.add(e1);
e7 = new Entity7(id, "entity7");
allEntities.add(e7);
e14 = new Entity14(id, "entity14");
allEntities.add(e14);
e1.setE14(e14);
}
// Make sure the default values are the same
public void testDefaults() {
assertTrue(compat.getFlushBeforeDetach());
assertFalse(compat.getCopyOnDetach());
assertFalse(compat.getCascadeWithDetach());
}
// Make sure all the fields in Entity1 are CASCADE_NONE
public void testCascadeValues() {
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
em.getTransaction().commit();
MetaDataRepository repos = emf.getConfiguration()
.getMetaDataRepositoryInstance();
ClassMetaData meta = repos.getCachedMetaData(Entity1.class);
assertNotNull(meta);
assertEquals(ValueMetaData.CASCADE_NONE,
meta.getField("id").getCascadeDetach());
assertEquals(ValueMetaData.CASCADE_NONE,
meta.getField("name").getCascadeDetach());
assertEquals(ValueMetaData.CASCADE_NONE,
meta.getField("e14").getCascadeDetach());
}
// Test clear() to clear all entities.
public void testClearAll() {
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
assertEquals(allEntities.size(),em.getManagedObjects().size());
em.clear();
assertEquals(0,em.getManagedObjects().size());
assertFalse(em.contains(e1));
em.getTransaction().commit();
}
// Test clear(Object entity) to clear 1 entity. Do not
// cascade and make sure contained entities and other entities
// are still managed.
public void testClearOne() {
id++;
boolean cwd = compat.getCascadeWithDetach();
boolean cod = compat.getCopyOnDetach();
compat.setCascadeWithDetach(false);
compat.setCopyOnDetach(false);
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
assertTrue(em.contains(e1));
em.detach(e1);
assertFalse(em.contains(e1));
assertTrue(em.contains(e14));
assertTrue(em.contains(e7));
em.getTransaction().commit();
compat.setCascadeWithDetach(cwd);
compat.setCopyOnDetach(cod);
}
// Test clear on a new, unmanaged object. Nothing should happen. After
// persist it should still become a managed entity.
public void testClearNew() {
id++;
em.getTransaction().begin();
create(id);
assertFalse(em.contains(e1));
em.detach(e1);
em.persistAll(allEntities);
assertTrue(em.contains(e1));
em.getTransaction().commit();
}
// Test clear on dirty object. Make sure the change is not flushed.
public void testClearDirty() {
boolean cod = compat.getCopyOnDetach();
boolean fbd = compat.getFlushBeforeDetach();
compat.setCopyOnDetach(false);
compat.setFlushBeforeDetach(false);
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
em.getTransaction().commit();
em.getTransaction().begin();
e1 = em.find(Entity1.class, id);
assertEquals("entity1",e1.getName());
e1.setName("new name");
em.detach(e1);
em.getTransaction().commit();
em.getTransaction().begin();
em.clear();
e1 = em.find(Entity1.class, id);
assertNotEquals("new name", e1.getName());
assertEquals("entity1", e1.getName());
em.getTransaction().commit();
compat.setCopyOnDetach(cod);
compat.setFlushBeforeDetach(fbd);
}
// Remove an Entity before clearing it. Make sure it is still in the
// DB after the commit.
public void testClearRemove() {
boolean cwd = compat.getCascadeWithDetach();
boolean cod = compat.getCopyOnDetach();
compat.setCascadeWithDetach(false);
compat.setCopyOnDetach(false);
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
em.getTransaction().commit();
em.getTransaction().begin();
e1 = em.find(Entity1.class, id);
em.remove(e1);
em.detach(e1);
em.getTransaction().commit();
em.getTransaction().begin();
em.clear();
e1 = em.find(Entity1.class, id);
assertNotNull(e1);
em.getTransaction().commit();
compat.setCascadeWithDetach(cwd);
compat.setCopyOnDetach(cod);
}
// Try to clear an entity that has already been cleared. There should be
// no exception and the entity should still not be there.
public void testClearOnClearedEntity() {
boolean cwd = compat.getCascadeWithDetach();
boolean cod = compat.getCopyOnDetach();
compat.setCascadeWithDetach(false);
compat.setCopyOnDetach(false);
id++;
em.getTransaction().begin();
create(id);
em.persist(e1);
em.detach(e1);
em.detach(e1);
assertFalse(em.contains(e1));
em.getTransaction().commit();
compat.setCascadeWithDetach(cwd);
compat.setCopyOnDetach(cod);
}
// Test that no copy is done by default
public void testNoCopy() {
boolean cwd = compat.getCascadeWithDetach();
boolean cod = compat.getCopyOnDetach();
compat.setCascadeWithDetach(false);
compat.setCopyOnDetach(false);
id++;
em.getTransaction().begin();
create(id);
em.persist(e1);
Entity14 e14PreDetach = e1.getE14();
// Flip on cascade to detach e14
compat.setCascadeWithDetach(true);
em.detach(e1);
// Assert that e14 was not copied on detachment
assertEquals(e14, e14PreDetach);
assertFalse(em.contains(e1));
assertFalse(em.contains(e14));
em.getTransaction().commit();
compat.setCascadeWithDetach(false);
compat.setCascadeWithDetach(cwd);
compat.setCopyOnDetach(cod);
}
// Change copy option and validate
public void testCopy() {
id++;
em.getTransaction().begin();
create(id);
em.persist(e1);
Entity1 e1Det = em.detachCopy(e1);
assertNotEquals(e1, e1Det);
assertTrue(em.contains(e1));
em.getTransaction().commit();
compat.setCopyOnDetach(false);
}
// Change flush option and validate
public void testFlush() {
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
em.getTransaction().commit();
compat.setFlushBeforeDetach(true);
em.getTransaction().begin();
e1 = em.find(Entity1.class, id);
assertEquals("entity1",e1.getName());
e1.setName("new name");
em.detach(e1);
em.getTransaction().commit();
em.getTransaction().begin();
em.clear();
e1 = em.find(Entity1.class, id);
assertEquals("new name", e1.getName());
em.getTransaction().commit();
compat.setFlushBeforeDetach(false);
}
// Clear an entity, then recreate it in the same transaction.
public void testClearRecreate() {
id++;
em.getTransaction().begin();
create(id);
em.persistAll(allEntities);
em.detach(e1);
em.merge(e1);
em.getTransaction().commit();
em.getTransaction().begin();
em.clear();
Entity1 newE1 = em.find(Entity1.class, id);
assertNotNull(newE1);
em.getTransaction().commit();
}
}