/tests/com/google/appengine/datanucleus/jpa/JPASubclassTest.java
Java | 700 lines | 586 code | 87 blank | 27 comment | 10 complexity | c8362be0eee4d423b49feb8f4da6f0f0 MD5 | raw file
1/********************************************************************** 2Copyright (c) 2009 Google Inc. 3 4Licensed under the Apache License, Version 2.0 (the "License"); 5you may not use this file except in compliance with the License. 6You may obtain a copy of the License at 7 8http://www.apache.org/licenses/LICENSE-2.0 9 10Unless required by applicable law or agreed to in writing, software 11distributed under the License is distributed on an "AS IS" BASIS, 12WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13See the License for the specific language governing permissions and 14limitations under the License. 15**********************************************************************/ 16package com.google.appengine.datanucleus.jpa; 17 18import com.google.appengine.api.datastore.Entity; 19import com.google.appengine.api.datastore.EntityNotFoundException; 20import com.google.appengine.api.datastore.Key; 21import com.google.appengine.api.datastore.KeyFactory; 22import com.google.appengine.datanucleus.DatastoreManager; 23import com.google.appengine.datanucleus.test.jpa.IsEmbeddedWithEmbeddedSuperclass; 24import com.google.appengine.datanucleus.test.jpa.IsEmbeddedWithEmbeddedSuperclass2; 25import com.google.appengine.datanucleus.test.jpa.SubclassesJPA; 26import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.Child; 27import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.ChildEmbeddedInTablePerClass; 28import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.DurableChild; 29import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.Grandchild; 30import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.Joined; 31import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.JoinedChild; 32import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.MappedSuperclassChild; 33import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.MappedSuperclassParent; 34import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.Parent; 35import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.SingleTable; 36import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.SingleTableChild; 37import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.TablePerClass; 38import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.TablePerClassChild; 39import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.TablePerClassGrandchild; 40import com.google.appengine.datanucleus.test.jpa.SubclassesJPA.TablePerClassParentWithEmbedded; 41 42import org.datanucleus.exceptions.NoPersistenceInformationException; 43 44import java.util.List; 45 46import javax.persistence.PersistenceException; 47import javax.persistence.Query; 48 49/** 50 * @author Max Ross <maxr@google.com> 51 */ 52public class JPASubclassTest extends JPATestCase { 53 54 public void testUnsupportedStrategies_GAE() { 55 assertUnsupportedByGAE(new JoinedChild()); 56 } 57 58 public void testGrandchildren() throws Exception { 59 testGrandchild(new TablePerClassGrandchild()); 60 } 61 62 public void testChildren() throws Exception { 63 testChild(new TablePerClassChild(), null); 64 testChild(new MappedSuperclassChild(), null); 65 testChild(new SingleTableChild(), SingleTableChild.class.getName()); 66 } 67 68 public void testParents() throws Exception { 69 testParent(new TablePerClass(), null); 70 testParent(new Joined(), null); 71 testParent(new SingleTable(), SingleTable.class.getName()); 72 } 73 74 public void testInsertParent_MappedSuperclass() throws EntityNotFoundException { 75 MappedSuperclassParent parent = new MappedSuperclassParent(); 76 parent.setAString("a"); 77 beginTxn(); 78 try { 79 em.persist(parent); 80 commitTxn(); 81 fail("expected pe"); 82 } catch (PersistenceException pe) { 83 assertTrue(pe.getCause() instanceof NoPersistenceInformationException); 84 } 85 } 86 87 public void testAttributeOverride() throws EntityNotFoundException { 88 MappedSuperclassChild child = new MappedSuperclassChild(); 89 child.setOverriddenString("overridden"); 90 beginTxn(); 91 em.persist(child); 92 commitTxn(); 93 Entity e = ds.get(KeyFactory.createKey(kindForClass(child.getClass()), child.getId())); 94 assertEquals("overridden", e.getProperty("overridden_string")); 95 assertFalse(e.hasProperty("overriddenString")); 96 } 97 98 public void testEmbedded_Child() throws Exception { 99 ChildEmbeddedInTablePerClass child = new ChildEmbeddedInTablePerClass(); 100 child.setAString("aString"); 101 child.setBString("bString"); 102 IsEmbeddedWithEmbeddedSuperclass embedded = new IsEmbeddedWithEmbeddedSuperclass(); 103 embedded.setVal0("embedded val 0"); 104 embedded.setVal1("embedded val 1"); 105 child.setEmbedded(embedded); 106 SubclassesJPA.IsEmbeddedBase embeddedBase = new SubclassesJPA.IsEmbeddedBase(); 107 embeddedBase.setVal0("embedded base val 0"); 108 child.setEmbeddedBase(embeddedBase); 109 IsEmbeddedWithEmbeddedSuperclass2 embedded2 = new IsEmbeddedWithEmbeddedSuperclass2(); 110 embedded2.setVal2("embedded val 2"); 111 embedded2.setVal3("embedded val 3"); 112 child.setEmbedded2(embedded2); 113 SubclassesJPA.IsEmbeddedBase2 114 embeddedBase2 = new SubclassesJPA.IsEmbeddedBase2(); 115 embeddedBase2.setVal2("embedded base val 2"); 116 child.setEmbeddedBase2(embeddedBase2); 117 beginTxn(); 118 em.persist(child); 119 commitTxn(); 120 Key key = KeyFactory.createKey(kindForClass(child.getClass()), child.getId()); 121 Entity e = ds.get(key); 122 assertEquals("aString", e.getProperty("aString")); 123 assertEquals("bString", e.getProperty("bString")); 124 assertEquals("embedded val 0", e.getProperty("val0")); 125 assertEquals("embedded val 1", e.getProperty("val1")); 126 assertEquals("embedded base val 0", e.getProperty("VAL0")); 127 assertEquals("embedded val 2", e.getProperty("val2")); 128 assertEquals("embedded val 3", e.getProperty("val3")); 129 assertEquals("embedded base val 2", e.getProperty("VAL2")); 130 em.close(); 131 em = emf.createEntityManager(); 132 beginTxn(); 133 child = em.find(child.getClass(), child.getId()); 134 assertEmbeddedChildContents(child); 135 commitTxn(); 136 em.close(); 137 em = emf.createEntityManager(); 138 beginTxn(); 139 Query q = em.createQuery("select from " + child.getClass().getName() + " b where embedded.val1 = :p " 140 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 141 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 142 q.setParameter("p", "embedded val 1"); 143 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 144 assertEmbeddedChildContents(child); 145 146 q = em.createQuery("select from " + child.getClass().getName() + " b where embedded.val0 = :p " 147 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 148 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 149 q.setParameter("p", "embedded val 0"); 150 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 151 assertEmbeddedChildContents(child); 152 153 q = em.createQuery("select from " + child.getClass().getName() + " b where embeddedBase.val0 = :p " 154 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 155 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 156 q.setParameter("p", "embedded base val 0"); 157 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 158 assertEmbeddedChildContents(child); 159 160 q = em.createQuery("select from " + child.getClass().getName() + " b where embedded2.val2 = :p " 161 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 162 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 163 q.setParameter("p", "embedded val 2"); 164 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 165 assertEmbeddedChildContents(child); 166 167 q = em.createQuery("select from " + child.getClass().getName() + " b where embedded2.val3 = :p " 168 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 169 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 170 q.setParameter("p", "embedded val 3"); 171 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 172 assertEmbeddedChildContents(child); 173 174 q = em.createQuery("select from " + child.getClass().getName() + " b where embeddedBase2.val2 = :p " 175 + "order by embedded.val1 desc, embedded.val0 desc, embeddedBase.val0 desc, " 176 + "embedded2.val2 desc, embedded2.val3 desc, embeddedBase2.val2"); 177 q.setParameter("p", "embedded base val 2"); 178 child = (ChildEmbeddedInTablePerClass) q.getSingleResult(); 179 assertEmbeddedChildContents(child); 180 181 q = em.createQuery("select embedded.val1, embedded.val0, embeddedBase.val0, embedded2.val2, embedded2.val3, embeddedBase2.val2 from " + 182 child.getClass().getName() + " b where embeddedBase2.val2 = :p"); 183 q.setParameter("p", "embedded base val 2"); 184 185 Object[] result = (Object[]) q.getSingleResult(); 186 assertEquals("embedded val 1", result[0]); 187 assertEquals("embedded val 0", result[1]); 188 assertEquals("embedded base val 0", result[2]); 189 assertEquals("embedded val 2", result[3]); 190 assertEquals("embedded val 3", result[4]); 191 assertEquals("embedded base val 2", result[5]); 192 193 em.remove(child); 194 commitTxn(); 195 try { 196 ds.get(key); 197 fail("expected enfe"); 198 } catch (EntityNotFoundException enfe) { 199 // good 200 } 201 } 202 203 public void testEmbedded_Parent() throws Exception { 204 TablePerClassParentWithEmbedded parent = new TablePerClassParentWithEmbedded(); 205 parent.setAString("aString"); 206 IsEmbeddedWithEmbeddedSuperclass embedded = new IsEmbeddedWithEmbeddedSuperclass(); 207 embedded.setVal0("embedded val 0"); 208 embedded.setVal1("embedded val 1"); 209 parent.setEmbedded(embedded); 210 SubclassesJPA.IsEmbeddedBase 211 embeddedBase = new SubclassesJPA.IsEmbeddedBase(); 212 embeddedBase.setVal0("embedded base val 0"); 213 parent.setEmbeddedBase(embeddedBase); 214 beginTxn(); 215 em.persist(parent); 216 commitTxn(); 217 Key key = KeyFactory.createKey(kindForClass(parent.getClass()), parent.getId()); 218 Entity e = ds.get(key); 219 assertEquals("aString", e.getProperty("aString")); 220 assertEquals("embedded val 0", e.getProperty("val0")); 221 assertEquals("embedded val 1", e.getProperty("val1")); 222 assertEquals("embedded base val 0", e.getProperty("VAL0")); 223 em.close(); 224 em = emf.createEntityManager(); 225 beginTxn(); 226 parent = em.find(parent.getClass(), parent.getId()); 227 assertEmbeddedParentContents(parent); 228 commitTxn(); 229 em.close(); 230 em = emf.createEntityManager(); 231 beginTxn(); 232 Query q = em.createQuery("select from " + parent.getClass().getName() + " b where embedded.val1 = :p " 233 + "order by embedded.val1 desc, embedded.val0 asc, embeddedBase.val0 desc"); 234 q.setParameter("p", "embedded val 1"); 235 parent = (TablePerClassParentWithEmbedded) q.getSingleResult(); 236 assertEmbeddedParentContents(parent); 237 238 q = em.createQuery("select from " + parent.getClass().getName() + " b where embedded.val0 = :p " 239 + "order by embedded.val1 desc, embedded.val0 asc, embeddedBase.val0 desc"); 240 q.setParameter("p", "embedded val 0"); 241 parent = (TablePerClassParentWithEmbedded) q.getSingleResult(); 242 assertEmbeddedParentContents(parent); 243 244 q = em.createQuery("select from " + parent.getClass().getName() + " b where embeddedBase.val0 = :p " 245 + "order by embedded.val1 desc, embedded.val0 asc, embeddedBase.val0 desc"); 246 q.setParameter("p", "embedded base val 0"); 247 parent = (TablePerClassParentWithEmbedded) q.getSingleResult(); 248 assertEmbeddedParentContents(parent); 249 250 q = em.createQuery("select embedded.val1, embedded.val0, embeddedBase.val0 from " + 251 parent.getClass().getName() + " b where embeddedBase.val0 = :p " 252 + "order by embedded.val1 desc, embedded.val0 asc, embeddedBase.val0 desc"); 253 q.setParameter("p", "embedded base val 0"); 254 255 Object[] result = (Object[]) q.getSingleResult(); 256 assertEquals("embedded val 1", result[0]); 257 assertEquals("embedded val 0", result[1]); 258 assertEquals("embedded base val 0", result[2]); 259 260 em.remove(parent); 261 commitTxn(); 262 try { 263 ds.get(key); 264 fail("expected enfe"); 265 } catch (EntityNotFoundException enfe) { 266 // good 267 } 268 } 269 270 public void testNondurableParent() { 271 DurableChild dc = new DurableChild(); 272 dc.setStr("yar"); 273 beginTxn(); 274 em.persist(dc); 275 commitTxn(); 276 beginTxn(); 277 dc = em.find(DurableChild.class, dc.getId()); 278 assertEquals("yar", dc.getStr()); 279 } 280 281 // This is absurd, but if the signature of this method and the one below 282 // refers to the actual type we want the runtime enhancer gets totally 283 // confused. 284 private void assertEmbeddedParentContents(Object obj) { 285 TablePerClassParentWithEmbedded parentWithEmbedded = (TablePerClassParentWithEmbedded) obj; 286 assertEquals("aString", parentWithEmbedded.getAString()); 287 assertEquals("embedded val 0", parentWithEmbedded.getEmbedded().getVal0()); 288 assertEquals("embedded val 1", parentWithEmbedded.getEmbedded().getVal1()); 289 assertEquals("embedded base val 0", parentWithEmbedded.getEmbeddedBase().getVal0()); 290 } 291 292 private void assertEmbeddedChildContents(Object obj) { 293 ChildEmbeddedInTablePerClass child = (ChildEmbeddedInTablePerClass) obj; 294 assertEquals("bString", child.getBString()); 295 assertEquals("embedded val 2", child.getEmbedded2().getVal2()); 296 assertEquals("embedded val 3", child.getEmbedded2().getVal3()); 297 assertEquals("embedded base val 2", child.getEmbeddedBase2().getVal2()); 298 assertEmbeddedParentContents(child); 299 } 300 301 private void assertUnsupportedByGAE(Object obj) { 302 switchDatasource(EntityManagerFactoryName.transactional_ds_non_transactional_ops_not_allowed); 303 beginTxn(); 304 em.persist(obj); 305 try { 306 commitTxn(); 307 fail("expected exception"); 308 } catch (PersistenceException e) { 309 // good 310 assertTrue(e.getCause() instanceof DatastoreManager.UnsupportedInheritanceStrategyException); 311 } 312 rollbackTxn(); 313 } 314 315 private void testInsertParent(Parent parent) throws Exception { 316 parent.setAString("a"); 317 beginTxn(); 318 em.persist(parent); 319 commitTxn(); 320 321 Entity e = ds.get(KeyFactory.createKey(kindForClass(parent.getClass()), parent.getId())); 322 assertEquals("a", e.getProperty("aString")); 323 } 324 325 private void testInsertChild(Child child) throws Exception { 326 child.setAString("a"); 327 child.setBString("b"); 328 beginTxn(); 329 em.persist(child); 330 commitTxn(); 331 332 Entity e = ds.get(KeyFactory.createKey(kindForClass(child.getClass()), child.getId())); 333 assertEquals("a", e.getProperty("aString")); 334 assertEquals("b", e.getProperty("bString")); 335 } 336 337 private void testInsertGrandchild(Grandchild grandchild) throws Exception { 338 grandchild.setAString("a"); 339 grandchild.setBString("b"); 340 grandchild.setCString("c"); 341 beginTxn(); 342 em.persist(grandchild); 343 commitTxn(); 344 345 Entity e = ds.get(KeyFactory.createKey(kindForClass(grandchild.getClass()), grandchild.getId())); 346 assertEquals("a", e.getProperty("aString")); 347 assertEquals("b", e.getProperty("bString")); 348 assertEquals("c", e.getProperty("cString")); 349 } 350 351 private void testFetchParent(Class<? extends Parent> parentClass) { 352 Entity e = new Entity(kindForClass(parentClass)); 353 e.setProperty("aString", "a"); 354 ds.put(e); 355 356 beginTxn(); 357 Parent parent = em.find(parentClass, e.getKey()); 358 assertEquals(parentClass, parent.getClass()); 359 assertEquals("a", parent.getAString()); 360 commitTxn(); 361 } 362 363 private void testFetchChild(Class<? extends Child> childClass) { 364 Entity e = new Entity(kindForClass(childClass)); 365 e.setProperty("aString", "a"); 366 e.setProperty("bString", "b"); 367 ds.put(e); 368 369 beginTxn(); 370 Child child = em.find(childClass, e.getKey()); 371 assertEquals(childClass, child.getClass()); 372 assertEquals("a", child.getAString()); 373 assertEquals("b", child.getBString()); 374 commitTxn(); 375 } 376 377 private void testFetchGrandchild(Class<? extends Grandchild> grandchildClass) { 378 Entity e = new Entity(kindForClass(grandchildClass)); 379 e.setProperty("aString", "a"); 380 e.setProperty("bString", "b"); 381 e.setProperty("cString", "c"); 382 ds.put(e); 383 384 beginTxn(); 385 Grandchild grandchild = em.find(grandchildClass, e.getKey()); 386 assertEquals(grandchildClass, grandchild.getClass()); 387 assertEquals("a", grandchild.getAString()); 388 assertEquals("b", grandchild.getBString()); 389 assertEquals("c", grandchild.getCString()); 390 commitTxn(); 391 } 392 393 private void testQueryParent(Class<? extends Parent> parentClass, String discriminator) { 394 Entity e = new Entity(kindForClass(parentClass)); 395 if (discriminator != null) { 396 e.setProperty("TYPE", discriminator); 397 } 398 e.setProperty("aString", "z8"); 399 ds.put(e); 400 401 e = new Entity(kindForClass(parentClass)); 402 if (discriminator != null) { 403 e.setProperty("TYPE", discriminator); 404 } 405 e.setProperty("aString", "z9"); 406 ds.put(e); 407 408 beginTxn(); 409 Query q = em.createQuery("select from " + parentClass.getName() + " b where aString = :p"); 410 q.setParameter("p", "z8"); 411 Parent parent = (Parent) q.getSingleResult(); 412 assertEquals(parentClass, parent.getClass()); 413 assertEquals("z8", parent.getAString()); 414 415 q = em.createQuery("select from " + parentClass.getName() + " b where aString >= :p order by aString desc"); 416 q.setParameter("p", "z8"); 417 List<Parent> parents = q.getResultList(); 418 assertEquals("z9", parents.get(0).getAString()); 419 assertEquals("z8", parents.get(1).getAString()); 420 421 q = em.createQuery("select aString from " + parentClass.getName() + " b where aString = :p"); 422 q.setParameter("p", "z8"); 423 String result = (String) q.getSingleResult(); 424 assertEquals("z8", result); 425 426 commitTxn(); 427 428 } 429 430 private void testQueryChild(Class<? extends Child> childClass, String discriminator) { 431 Entity e1 = new Entity(kindForClass(childClass)); 432 if (discriminator != null) { 433 e1.setProperty("TYPE", discriminator); 434 } 435 e1.setProperty("aString", "a2"); 436 e1.setProperty("bString", "b2"); 437 ds.put(e1); 438 439 Entity e2 = new Entity(kindForClass(childClass)); 440 if (discriminator != null) { 441 e2.setProperty("TYPE", discriminator); 442 } 443 e2.setProperty("aString", "a2"); 444 e2.setProperty("bString", "b3"); 445 ds.put(e2); 446 447 Entity e3 = new Entity(kindForClass(childClass)); 448 if (discriminator != null) { 449 e3.setProperty("TYPE", discriminator); 450 } 451 e3.setProperty("aString", "a2"); 452 e3.setProperty("bString", "b3"); 453 ds.put(e3); 454 455 beginTxn(); 456 Query q = em.createQuery("select from " + childClass.getName() + " b where aString = :p"); 457 q.setParameter("p", "a2"); 458 Child child = (Child) q.getResultList().get(0); 459 assertEquals(childClass, child.getClass()); 460 assertEquals("a2", child.getAString()); 461 assertEquals("b2", child.getBString()); 462 463 q = em.createQuery("select from " + childClass.getName() + " b where bString = :p"); 464 q.setParameter("p", "b2"); 465 child = (Child) q.getSingleResult(); 466 assertEquals(childClass, child.getClass()); 467 assertEquals("a2", child.getAString()); 468 assertEquals("b2", child.getBString()); 469 470 List<Child> kids = ((List<Child>) em.createQuery( 471 "select from " + childClass.getName() + " b where aString = 'a2' order by bString desc").getResultList()); 472 assertEquals(3, kids.size()); 473 assertEquals(e2.getKey().getId(), kids.get(0).getId().longValue()); 474 assertEquals(e3.getKey().getId(), kids.get(1).getId().longValue()); 475 assertEquals(e1.getKey().getId(), kids.get(2).getId().longValue()); 476 477 kids = ((List<Child>) em.createQuery( 478 "select from " + childClass.getName() + " b where aString = 'a2' order by aString desc").getResultList()); 479 assertEquals(3, kids.size()); 480 assertEquals(e1.getKey().getId(), kids.get(0).getId().longValue()); 481 assertEquals(e2.getKey().getId(), kids.get(1).getId().longValue()); 482 assertEquals(e3.getKey().getId(), kids.get(2).getId().longValue()); 483 484 q = em.createQuery("select bString, aString from " + childClass.getName() + " b where bString = :p"); 485 q.setParameter("p", "b2"); 486 Object[] result = (Object[]) q.getSingleResult(); 487 assertEquals(2, result.length); 488 assertEquals("b2", result[0]); 489 assertEquals("a2", result[1]); 490 491 commitTxn(); 492 } 493 494 private void testQueryGrandchild(Class<? extends Grandchild> grandchildClass) { 495 Entity e1 = new Entity(kindForClass(grandchildClass)); 496 e1.setProperty("aString", "a2"); 497 e1.setProperty("bString", "b1"); 498 e1.setProperty("cString", "c2"); 499 ds.put(e1); 500 501 Entity e2 = new Entity(kindForClass(grandchildClass)); 502 e2.setProperty("aString", "a2"); 503 e2.setProperty("bString", "b3"); 504 e2.setProperty("cString", "c3"); 505 ds.put(e2); 506 507 Entity e3 = new Entity(kindForClass(grandchildClass)); 508 e3.setProperty("aString", "a2"); 509 e3.setProperty("bString", "b2"); 510 e3.setProperty("cString", "c3"); 511 ds.put(e3); 512 513 beginTxn(); 514 Query q = em.createQuery( 515 "select from " + grandchildClass.getName() + " b where aString = :p"); 516 q.setParameter("p", "a2"); 517 Grandchild grandchild = (Grandchild) q.getResultList().get(0); 518 519 assertEquals(grandchildClass, grandchild.getClass()); 520 assertEquals("a2", grandchild.getAString()); 521 assertEquals("b1", grandchild.getBString()); 522 assertEquals("c2", grandchild.getCString()); 523 524 q = em.createQuery( 525 "select from " + grandchildClass.getName() + " b where bString = :p"); 526 q.setParameter("p", "b2"); 527 grandchild = (Grandchild) q.getSingleResult(); 528 529 assertEquals(grandchildClass, grandchild.getClass()); 530 assertEquals("a2", grandchild.getAString()); 531 assertEquals("b2", grandchild.getBString()); 532 assertEquals("c3", grandchild.getCString()); 533 534 q = em.createQuery( 535 "select from " + grandchildClass.getName() + " b where cString = :p"); 536 q.setParameter("p", "c2"); 537 grandchild = (Grandchild) q.getSingleResult(); 538 539 assertEquals(grandchildClass, grandchild.getClass()); 540 assertEquals("a2", grandchild.getAString()); 541 assertEquals("b1", grandchild.getBString()); 542 assertEquals("c2", grandchild.getCString()); 543 544 List<Grandchild> grandkids = ((List<Grandchild>) em.createQuery( 545 "select from " + grandchildClass.getName() + " b where aString = 'a2' order by bString desc").getResultList()); 546 assertEquals(3, grandkids.size()); 547 assertEquals(e2.getKey().getId(), grandkids.get(0).getId().longValue()); 548 assertEquals(e3.getKey().getId(), grandkids.get(1).getId().longValue()); 549 assertEquals(e1.getKey().getId(), grandkids.get(2).getId().longValue()); 550 551 grandkids = ((List<Grandchild>) em.createQuery( 552 "select from " + grandchildClass.getName() + " b where aString = 'a2' order by aString desc").getResultList()); 553 assertEquals(3, grandkids.size()); 554 assertEquals(e1.getKey().getId(), grandkids.get(0).getId().longValue()); 555 assertEquals(e2.getKey().getId(), grandkids.get(1).getId().longValue()); 556 assertEquals(e3.getKey().getId(), grandkids.get(2).getId().longValue()); 557 558 grandkids = ((List<Grandchild>) em.createQuery( 559 "select from " + grandchildClass.getName() + " b where aString = 'a2' order by cString desc").getResultList()); 560 assertEquals(3, grandkids.size()); 561 assertEquals(e2.getKey().getId(), grandkids.get(0).getId().longValue()); 562 assertEquals(e3.getKey().getId(), grandkids.get(1).getId().longValue()); 563 assertEquals(e1.getKey().getId(), grandkids.get(2).getId().longValue()); 564 565 q = em.createQuery("select bString, aString, cString from " + grandchildClass.getName() + " b where cString = :p"); 566 q.setParameter("p", "c2"); 567 Object[] result = (Object[]) q.getSingleResult(); 568 assertEquals(3, result.length); 569 assertEquals("b1", result[0]); 570 assertEquals("a2", result[1]); 571 assertEquals("c2", result[2]); 572 573 commitTxn(); 574 } 575 576 private void testDeleteParent(Class<? extends Parent> parentClass) { 577 Entity e = new Entity(kindForClass(parentClass)); 578 e.setProperty("aString", "a"); 579 ds.put(e); 580 581 beginTxn(); 582 Parent parent = em.find(parentClass, e.getKey()); 583 em.remove(parent); 584 commitTxn(); 585 try { 586 ds.get(e.getKey()); 587 fail("expected exception"); 588 } catch (EntityNotFoundException e1) { 589 // good 590 } 591 } 592 593 private void testDeleteChild(Class<? extends Child> childClass) { 594 Entity e = new Entity(kindForClass(childClass)); 595 e.setProperty("aString", "a"); 596 e.setProperty("bString", "b"); 597 ds.put(e); 598 599 beginTxn(); 600 Child child = em.find(childClass, e.getKey()); 601 em.remove(child); 602 commitTxn(); 603 try { 604 ds.get(e.getKey()); 605 fail("expected exception"); 606 } catch (EntityNotFoundException e1) { 607 // good 608 } 609 } 610 611 private void testDeleteGrandchild(Class<? extends Grandchild> grandchildClass) { 612 Entity e = new Entity(kindForClass(grandchildClass)); 613 e.setProperty("aString", "a"); 614 e.setProperty("bString", "b"); 615 e.setProperty("cString", "c"); 616 ds.put(e); 617 618 beginTxn(); 619 Child child = em.find(grandchildClass, e.getKey()); 620 em.remove(child); 621 commitTxn(); 622 try { 623 ds.get(e.getKey()); 624 fail("expected exception"); 625 } catch (EntityNotFoundException e1) { 626 // good 627 } 628 } 629 630 private void testUpdateParent(Class<? extends Parent> parentClass) throws Exception { 631 Entity e = new Entity(kindForClass(parentClass)); 632 e.setProperty("aString", "a"); 633 ds.put(e); 634 635 beginTxn(); 636 Parent parent = em.find(parentClass, e.getKey()); 637 parent.setAString("not a"); 638 commitTxn(); 639 e = ds.get(e.getKey()); 640 assertEquals("not a", e.getProperty("aString")); 641 } 642 643 private void testUpdateChild(Class<? extends Child> childClass) throws Exception { 644 Entity e = new Entity(kindForClass(childClass)); 645 e.setProperty("aString", "a"); 646 e.setProperty("bString", "b"); 647 ds.put(e); 648 649 beginTxn(); 650 Child child = em.find(childClass, e.getKey()); 651 child.setAString("not a"); 652 child.setBString("not b"); 653 commitTxn(); 654 e = ds.get(e.getKey()); 655 assertEquals("not a", e.getProperty("aString")); 656 assertEquals("not b", e.getProperty("bString")); 657 } 658 659 private void testUpdateGrandchild(Class<? extends Grandchild> grandchildClass) throws Exception { 660 Entity e = new Entity(kindForClass(grandchildClass)); 661 e.setProperty("aString", "a"); 662 e.setProperty("bString", "b"); 663 ds.put(e); 664 665 beginTxn(); 666 Grandchild grandchild = em.find(grandchildClass, e.getKey()); 667 grandchild.setAString("not a"); 668 grandchild.setBString("not b"); 669 grandchild.setCString("not c"); 670 commitTxn(); 671 e = ds.get(e.getKey()); 672 assertEquals("not a", e.getProperty("aString")); 673 assertEquals("not b", e.getProperty("bString")); 674 assertEquals("not c", e.getProperty("cString")); 675 } 676 677 private void testGrandchild(Grandchild grandchild) throws Exception { 678 testInsertGrandchild(grandchild); 679 testUpdateGrandchild(grandchild.getClass()); 680 testDeleteGrandchild(grandchild.getClass()); 681 testFetchGrandchild(grandchild.getClass()); 682 testQueryGrandchild(grandchild.getClass()); 683 } 684 685 private void testChild(Child child, String discriminator) throws Exception { 686 testInsertChild(child); 687 testUpdateChild(child.getClass()); 688 testDeleteChild(child.getClass()); 689 testFetchChild(child.getClass()); 690 testQueryChild(child.getClass(), discriminator); 691 } 692 693 private void testParent(Parent parent, String discriminator) throws Exception { 694 testInsertParent(parent); 695 testUpdateParent(parent.getClass()); 696 testDeleteParent(parent.getClass()); 697 testFetchParent(parent.getClass()); 698 testQueryParent(parent.getClass(), discriminator); 699 } 700}