1 2 12 package com.versant.core.jdo; 13 14 import com.versant.core.common.Debug; 15 import com.versant.core.common.*; 16 import com.versant.core.jdo.sco.VersantSCOCollection; 17 import com.versant.core.metadata.*; 18 import com.versant.core.jdo.query.mem.MemQueryCompiler; 19 20 import javax.jdo.*; 21 import javax.jdo.spi.JDOImplHelper; 22 import javax.jdo.spi.PersistenceCapable; 23 import javax.jdo.spi.StateManager; 24 25 import javax.transaction.Status ; 26 import javax.transaction.Synchronization ; 27 import javax.transaction.xa.XAException ; 28 import javax.transaction.xa.XAResource ; 29 import javax.transaction.xa.Xid ; 30 31 import java.lang.reflect.Modifier ; 32 import java.lang.ref.Reference ; 33 import java.sql.Connection ; 34 import java.util.*; 35 36 import com.versant.core.common.BindingSupportImpl; 37 import com.versant.core.storagemanager.StorageManager; 39 import com.versant.core.storagemanager.ApplicationContext; 40 41 45 public final class VersantPersistenceManagerImp 46 implements VersantPersistenceManager, ApplicationContext, Transaction, PersistenceContext 47 , XAResource , Synchronization { 48 49 55 private PCStateMan txDirtyListHead; 56 private PCStateMan txDirtyListTail; 57 58 public VersantPersistenceManagerImp prev; 59 public VersantPersistenceManagerImp next; 60 public boolean idle; 61 62 65 private final DeletePacket toBeDeleted; 66 69 public final StatesToStore storeOidStateContainer; 70 73 private boolean retrieveing; 74 77 private final Set retrieveSet = new HashSet(); 78 79 82 private Object userObject; 83 84 90 91 private Synchronization synchronizationInstance; 92 93 94 98 public PCStateMan requestedPCState; 99 public final ModelMetaData modelMetaData; 100 private LocalPMCache cache; 101 public final JDOImplHelper jdoImplHelper = JDOImplHelper.getInstance(); 102 103 106 private boolean transactionActive; 107 private boolean busyWithRollback; 108 109 112 private int counter = 0; 113 114 private boolean retainValues; 115 private boolean restoreValues; 116 private boolean optimistic; 117 private boolean nontransactionalRead; 118 private boolean nontransactionalWrite; 119 private boolean ignoreCache; 120 private boolean multithreaded; 121 122 125 private boolean closed; 126 127 130 private final VersantPMFInternal pmf; 131 132 private final MemQueryCompiler memQueryCompiler; 133 134 137 private boolean mustNotPool; 138 private boolean inPool; 139 140 146 private PMProxy proxy; 147 148 151 private final CmdBitSet dirtyCmdBits; 152 private final StorageManager sm; 153 154 159 private boolean strict; 160 private boolean interceptDfgFieldAccess = true; 161 162 private boolean checkModelConsistencyOnCommit; 163 164 public static final String LANGUAGE_SQL = "SQL"; 165 public static final String LANGUAGE_EJBQL = "EJBQL"; 166 167 168 private Object [] epcObjects; 172 private int epcObjectCount; 173 private int[] epcClasses; 174 private int epcClassCount; 175 private boolean[] epcClassPresent; 176 private boolean epcAll; 177 178 private LifecycleListenerManager listeners; 179 180 private Reference activeReference; 181 182 public VersantPersistenceManagerImp(VersantPMFInternal pmf, 183 ModelMetaData modelMetaData, StorageManager sm, 184 LocalPMCache jdoManagedCache, 185 MemQueryCompiler memQueryCompiler) { 186 this.pmf = pmf; 187 this.modelMetaData = modelMetaData; 188 this.sm = sm; 189 this.storeOidStateContainer = new StatesToStore(modelMetaData); 190 this.toBeDeleted = new DeletePacket(modelMetaData); 191 dirtyCmdBits = new CmdBitSet(modelMetaData); 192 this.cache = jdoManagedCache; 193 this.cache.setPm(this); 194 this.memQueryCompiler = memQueryCompiler; 195 } 196 197 private void createProxy() { 198 if (multithreaded) { 199 proxy = new SynchronizedPMProxy(this); 200 } else { 201 proxy = new UnsynchronizedPMProxy(this); 202 } 203 } 204 205 public boolean isInterceptDfgFieldAccess() { 206 return interceptDfgFieldAccess; 207 } 208 209 public void setInterceptDfgFieldAccess(boolean on) { 210 if (interceptDfgFieldAccess == on) return; 211 cache.setInterceptDfgFieldAccess( 212 interceptDfgFieldAccess = on); 213 } 214 215 public boolean isStrict() { 216 return strict; 217 } 218 219 public void setStrict(boolean strict) { 220 this.strict = strict; 221 } 222 223 public PMProxy getProxy() { 224 return proxy; 225 } 226 227 public boolean isInPool() { 228 return inPool; 229 } 230 231 public void setMustNotPool(boolean mustNotPool) { 232 this.mustNotPool = mustNotPool; 233 } 234 235 public boolean isMustNotPool() { 236 return mustNotPool; 237 } 238 239 243 public void setInPool(boolean inPool) { 244 this.inPool = inPool; 245 if (inPool) { 246 proxy = null; 247 } else { 248 createProxy(); 249 if (managed) managedClosed = false; 250 } 251 } 252 253 257 protected void finalize() throws Throwable { 258 boolean txWasActive = transactionActive; 259 if (transactionActive) { 260 rollback(); 261 } 262 proxy.resetPM(); 263 pmf.pmClosedNotification(this, true, txWasActive); 264 } 265 266 271 public void setMasterOnDetail(PersistenceCapable detail, int managedFieldNo, 272 PersistenceCapable master, boolean removeFromCurrentMaster) { 273 getInternalSM(detail).setMaster(managedFieldNo, master, 274 removeFromCurrentMaster); 275 } 276 277 281 public VersantSCOCollection getCollectionField(PersistenceCapable pc, 282 int fieldNo) { 283 PCStateMan sm = getInternalSM(pc); 284 return (VersantSCOCollection)sm.getObjectField(null, fieldNo, null); 285 } 286 287 public Object getObjectField(PersistenceCapable pc, 288 int fieldNo) { 289 PCStateMan sm = getInternalSM(pc); 290 return sm.getObjectField(null, fieldNo, null); 291 } 292 293 public String getConnectionURL(String dataStore) { 294 try { 295 return pmf.getConnectionURL(); 296 } catch (Exception e) { 297 handleException(e); 298 return null; 299 } 300 } 301 302 public void cancelQueryExecution() { 303 } 305 306 public String getConnectionDriverName(String dataStore) { 307 try { 308 return pmf.getConnectionDriverName(); 309 } catch (Exception e) { 310 handleException(e); 311 return null; 312 } 313 } 314 315 public Connection getJdbcConnection(String datastore) { 316 if (!transactionActive) { 317 throw BindingSupportImpl.getInstance().invalidOperation( 318 "A JDBC Connection may only be obtained within a active JDO transaction."); 319 } 320 try { 321 return (Connection )sm.getDatastoreConnection(); 322 } catch (Exception e) { 323 handleException(e); 324 return null; 325 } 326 } 327 328 331 public void flushIfDepOn(int[] cmdBits) { 332 if (cmdBits != null && dirtyCmdBits.containsAny(cmdBits)) flushRetainState(); 333 } 334 335 public void loadFetchGroup(Object pc, String name) { 336 try { 337 if (!(pc instanceof PersistenceCapable)) { 338 String msg; 339 if (pc == null) { 340 msg = "Instance is null"; 341 } else { 342 msg = "Instance is not a persistence class: " + 343 pc.getClass().getName(); 344 } 345 throw BindingSupportImpl.getInstance().runtime(msg); 346 } 347 PCStateMan sm = getInternalSM((PersistenceCapable)pc); 348 if (sm == null) { 349 throw BindingSupportImpl.getInstance().invalidOperation("Instance is not managed by JDO (it is transient): " + 350 Utils.toString(pc)); 351 } 352 sm.loadFetchGroup(name); 353 } catch (RuntimeException e) { 354 handleException(e); 355 } 356 } 357 358 public boolean isRetainValues() { 359 return retainValues; 360 } 361 362 public boolean isRestoreValues() { 363 return restoreValues; 364 } 365 366 public boolean isOptimistic() { 367 return optimistic; 368 } 369 370 public boolean isNontransactionalRead() { 371 return nontransactionalRead; 372 } 373 374 public boolean isNontransactionalWrite() { 375 return nontransactionalWrite; 376 } 377 378 public boolean isIgnoreCache() { 379 return ignoreCache; 380 } 381 382 public void evict(Object pc) { 383 try { 384 if (pc == null) return; 385 PersistenceCapable persistenceCapable = checkPersCapable(pc); 386 PersistenceManager pm = persistenceCapable.jdoGetPersistenceManager(); 387 if (pm == null) return; 389 checkPM(pm, proxy); 390 getInternalSM(persistenceCapable).evict(); 391 } catch (Exception e) { 392 handleException(e); 393 } 394 } 395 396 public void evictAll() { 397 try { 398 cache.evict(); 399 } catch (Exception e) { 400 handleException(e); 401 } 402 } 403 404 public void evictAll(Object [] pcs) { 405 for (int i = pcs.length - 1; i >= 0; i--) { 406 evict(pcs[i]); 407 } 408 } 409 410 public void evictAll(Collection pcs) { 411 try { 412 Object [] persistenceCapables = new Object [pcs.size()]; 413 pcs.toArray(persistenceCapables); 414 for (int i = persistenceCapables.length - 1; i >= 0; i--) { 415 evict(persistenceCapables[i]); 416 } 417 } catch (Exception e) { 418 handleException(e); 419 } 420 } 421 422 public Object getObjectId(Object pc) { 423 try { 424 if (pc == null) { 425 throw BindingSupportImpl.getInstance().invalidOperation( 426 "The supplied Object param is null"); 427 } 428 429 if (!(pc instanceof PersistenceCapable)) 430 { 432 return null; 433 } 434 435 PCStateMan pcStateObject = pmPreCheck(pc); 436 if (pcStateObject != null) { 437 return pcStateObject.getObjectId(null); 438 } else { 439 return null; 440 } 441 } catch (RuntimeException e) { 442 handleException(e); 443 return null; 444 } 445 } 446 447 public Object getExternalOID(OID oid) { 448 PCStateMan sm = cache.getByOID(oid, false); 449 if (sm != null) { 450 return sm.getObjectId(null); 451 } else { 452 ClassMetaData classMetaData = oid.getAvailableClassMetaData(); 453 if (classMetaData.identityType == MDStatics.IDENTITY_TYPE_DATASTORE) { 454 return new VersantOid(oid, modelMetaData, oid.isResolved()); 455 } else if (classMetaData.identityType == MDStatics.IDENTITY_TYPE_APPLICATION) { 456 Object pcID = jdoImplHelper.newObjectIdInstance( 457 classMetaData.cls); 458 oid.populateObjectIdClassInstance(pcID); 459 return pcID; 460 } else { 461 throw BindingSupportImpl.getInstance().unsupported(); 462 } 463 } 464 } 465 466 public Object getObjectByIDString(String value, boolean toValidate) { 467 return getObjectByIDString(value, toValidate, true); 468 } 469 470 public Object getObjectByIDString(String value, boolean toValidate, 471 boolean resolved) { 472 try { 473 OID oid = modelMetaData.newOIDFromIDString(value, resolved); 474 return getObjectById(oid, toValidate); 475 } catch (Exception e) { 476 handleException(e); 477 return null; 478 } 479 } 480 481 public Object getTransactionalObjectId(Object pc) { 482 try { 483 return getObjectId(pc); 484 } catch (Exception e) { 485 handleException(e); 486 return null; 487 } 488 } 489 490 491 497 public boolean isClosed() { 498 checkInPool(); 499 if (!managed) { 500 return closed; 501 } else { 502 return managedClosed; 503 } 504 } 505 506 519 public synchronized void close() { 520 checkClosed(); 521 if (!managed) { 522 checkCloseWithActiveTx(); 523 boolean txWasActive = transactionActive; 524 if (transactionActive) { 525 rollback(); 526 } 527 proxy.resetPM(); 528 pmf.pmClosedNotification(this, false, txWasActive); 529 } else { 530 managedClosed = true; 531 } 532 } 533 534 private void checkCloseWithActiveTx() { 535 if (transactionActive && !pmf.isAllowPmCloseWithTxOpen()) { 536 throw BindingSupportImpl.getInstance().invalidOperation( 537 538 "May not close 'PersistenceManager' with active transaction"); 539 540 541 } 542 } 543 544 547 public void destroy() { 548 try { 549 sm.reset(); 550 resetEpcFields(); 551 reset(); 552 cache.clear(); 553 this.closed = true; 554 } catch (Exception e) { 555 handleException(e); 556 } 557 } 558 559 public boolean isActualClosed() { 560 return closed; 561 } 562 563 public Transaction currentTransaction() { 564 return this; 565 } 566 567 public void refresh(Object pc) { 568 try { 569 572 if (isTransient(pc)) return; 573 pmPreCheck(pc).refresh(); 574 } catch (Exception e) { 575 handleException(e); 576 } 577 } 578 579 public void setPmCacheRefType(Object pc, int type) { 580 pmPreCheck(pc).cacheEntry.changeToRefType(cache.queue, type); 581 } 582 583 public void setPmCacheRefType(Object [] pcs, int type) { 584 for (int i = 0; i < pcs.length; i++) { 585 if (pcs[i] != null) setPmCacheRefType(pcs[i], type); 586 } 587 } 588 589 public void setPmCacheRefType(Collection col, int type) { 590 for (Iterator iterator = col.iterator(); iterator.hasNext();) { 591 Object o = iterator.next(); 592 if (o != null) setPmCacheRefType(o, type); 593 } 594 } 595 596 public void setPmCacheRefType(int type) { 597 cache.setCurrentRefType(type); 598 } 599 600 public int getPmCacheRefType() { 601 return cache.getCurrentRefType(); 602 } 603 604 public void refreshAll(Object [] pcs) { 605 try { 606 for (int i = 0; i < pcs.length; i++) { 607 refresh(pcs[i]); 608 } 609 } catch (Exception e) { 610 handleException(e); 611 } 612 } 613 614 public void refreshAll(Collection pcs) { 615 if (pcs instanceof QueryResult) { 616 cache.setOverWriteMode(true); 617 try { 618 Iterator iter = ((QueryResult)pcs).createInternalIterNoFlush(); 619 while (iter.hasNext()) iter.next(); 620 } catch (Exception e) { 621 handleException(e); 622 } finally { 623 cache.setOverWriteMode(false); 624 } 625 } else { 626 try { 627 for (Iterator iterator = pcs.iterator(); iterator.hasNext();) { 628 refresh(iterator.next()); 629 } 630 } catch (Exception e) { 631 handleException(e); 632 } 633 } 634 } 635 636 public void refreshAll() { 637 try { 638 if (transactionActive) { 639 cache.doRefresh(strict); 640 } 641 } catch (Exception e) { 642 handleException(e); 643 } 644 } 645 646 public Query newQuery() { 647 try { 648 return new VersantQueryImp(proxy); 649 } catch (Exception e) { 650 handleException(e); 651 return null; 652 } 653 } 654 655 public Query newQuery(Object compiled) { 656 try { 660 VersantQueryImp other = null; 661 try { 662 other = (VersantQueryImp)compiled; 663 } catch (Exception e) { 664 throw BindingSupportImpl.getInstance().invalidOperation( 665 "The supplied instance is not supported to re-create a query from."); 666 } 667 return new VersantQueryImp(proxy, other); 668 } catch (RuntimeException e) { 669 handleException(e); 670 return null; 671 } 672 } 673 674 700 public Query newQuery(String language, Object query) { 701 try { 702 if (language != null) { 703 language = language.toUpperCase(); 704 } 705 if (LANGUAGE_SQL.equals(language)) { 706 VersantQueryImp clientQuery = new VersantQueryImp(proxy, 707 QueryDetails.LANGUAGE_SQL); 708 clientQuery.setFilter((String )query); 709 return clientQuery; 710 711 } else if (LANGUAGE_EJBQL.equals(language)) { 712 VersantQueryImp clientQuery = new VersantQueryImp(proxy, 713 QueryDetails.LANGUAGE_EJBQL); 714 clientQuery.setFilter((String )query); 715 return clientQuery; 716 } else { 717 return newQuery(query); 718 } 719 } catch (Exception e) { 720 handleException(e); 721 return null; 722 } 723 } 724 725 public Query newQuery(Class cls) { 726 try { 727 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 728 clientQuery.setClass(cls); 729 return clientQuery; 730 } catch (Exception e) { 731 handleException(e); 732 return null; 733 } 734 } 735 736 public Query newQuery(Extent extent) { 737 try { 738 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 739 clientQuery.setCandidates(extent); 740 return clientQuery; 741 } catch (Exception e) { 742 handleException(e); 743 return null; 744 } 745 } 746 747 public Query newQuery(Extent extent, String filter) { 748 try { 749 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 750 clientQuery.setCandidates(extent); 751 clientQuery.setFilter(filter); 752 return clientQuery; 753 } catch (Exception e) { 754 handleException(e); 755 return null; 756 } 757 } 758 759 public Query newQuery(Class cls, Collection cln) { 760 try { 761 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 762 clientQuery.setClass(cls); 763 clientQuery.setCandidates(cln); 764 return clientQuery; 765 } catch (Exception e) { 766 handleException(e); 767 return null; 768 } 769 } 770 771 public Query newQuery(Class cls, String filter) { 772 try { 773 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 774 clientQuery.setClass(cls); 775 clientQuery.setFilter(filter); 776 return clientQuery; 777 } catch (Exception e) { 778 handleException(e); 779 return null; 780 } 781 } 782 783 public Query newQuery(Class cls, Collection cln, String filter) { 784 try { 785 VersantQueryImp clientQuery = new VersantQueryImp(proxy); 786 clientQuery.setClass(cls); 787 clientQuery.setCandidates(cln); 788 clientQuery.setFilter(filter); 789 return clientQuery; 790 } catch (Exception e) { 791 handleException(e); 792 return null; 793 } 794 } 795 796 public Class getObjectIdClass(Class cls) { 797 try { 798 if (cls == null) { 799 return null; 800 } 802 if (!PersistenceCapable.class.isAssignableFrom(cls)) { 803 return null; 804 } 805 if (Modifier.isAbstract(cls.getModifiers())) { 806 return null; 807 } 808 ClassMetaData cmd = modelMetaData.getClassMetaData(cls); 809 if (cmd == null) { 810 throw BindingSupportImpl.getInstance().invalidOperation( 811 "The class is not specified as " + PersistenceCapable.class.getName() + " for the application"); 812 } 813 if (cmd.identityType == MDStatics.IDENTITY_TYPE_APPLICATION) { 814 return cmd.objectIdClass; 815 } else { 816 return VersantOid.class; 817 } 818 } catch (RuntimeException e) { 819 handleException(e); 820 return null; 821 } 822 } 823 824 public Object newObjectIdInstance(Class cls, String s) { 825 return newObjectIdInstance(cls, s, true); 826 } 827 828 public Object newObjectIdInstance(Class cls, String s, boolean resolved) { 829 try { 830 if (s == null || s.length() == 0) { 831 throw BindingSupportImpl.getInstance().invalidOperation( 832 "Please supply an non-null, non-empty String"); 833 } 834 if (cls == null) { return new VersantOid( 836 modelMetaData.newOIDFromIDString(s, resolved), 837 modelMetaData, resolved); 838 } 839 ClassMetaData cmd = modelMetaData.getClassMetaData(cls); 840 if (cmd == null) { 841 throw BindingSupportImpl.getInstance().invalidOperation("There is no metadata registered for class '" + 842 cls.getName() + "'"); 843 } 844 if (cmd.identityType == MDStatics.IDENTITY_TYPE_APPLICATION) { 845 return jdoImplHelper.newObjectIdInstance(cls, s); 846 } else if (cmd.identityType == MDStatics.IDENTITY_TYPE_DATASTORE) { 847 return new VersantOid( 848 modelMetaData.newOIDFromIDString(s, resolved), 849 modelMetaData, resolved); 850 } else { 851 throw BindingSupportImpl.getInstance().invalidOperation("Class '" + cls.getName() + 852 " uses non-durable identity"); 853 } 854 } catch (RuntimeException e) { 855 handleException(e); 856 return null; 857 } 858 } 859 860 public void retrieve(Object o) { 861 try { 862 PCStateMan pcStateObject = pmPreCheck(o); 863 if (pcStateObject != null) { 864 try { 865 if (Debug.DEBUG) { 866 if (retrieveing) { 867 throw BindingSupportImpl.getInstance().internal( 868 "Retrieveing is already set"); 869 } 870 } 871 retrieveing = true; 872 if (Debug.DEBUG) { 873 if (retrieveSet.contains(pcStateObject.pc)) { 874 throw BindingSupportImpl.getInstance().internal( 875 "RetrieveSet already contains pc"); 876 } 877 } 878 retrieveSet.add(pcStateObject.pc); 879 pcStateObject.retrieve(this); 880 } finally { 881 retrieveing = false; 882 retrieveSet.clear(); 883 } 884 } 885 } catch (RuntimeException e) { 886 if (BindingSupportImpl.getInstance().isOwnInternalException(e)) { 887 handleException(e); 888 } else { 889 throw e; 890 } 891 } 892 } 893 894 public void retrieveImp(Object o) { 895 if (o == null) return; 896 PCStateMan pcStateObject = pmPreCheck(o); 897 if (pcStateObject != null && 898 !retrieveSet.contains(pcStateObject.pc)) { 899 retrieveSet.add(pcStateObject.pc); 900 pcStateObject.retrieve(this); 901 } 902 } 903 904 public void retrieveAllImp(Object [] toRetrieve) { 905 for (int i = 0; i < toRetrieve.length; i++) { 906 retrieveImp(toRetrieve[i]); 907 } 908 } 909 910 public void retrieveAllImp(Collection toRetrieve) { 911 retrieveAllImp(toRetrieve.toArray()); 912 } 913 914 public void retrieveAll(Collection collection) { 915 try { 916 retrieveAll(collection.toArray()); 917 } catch (Exception e) { 918 handleException(e); 919 } 920 } 921 922 public void retrieveAll(Collection collection, boolean b) { 923 retrieveAll(collection); 924 } 925 926 public void retrieveAll(Object [] objects, boolean b) { 927 retrieveAll(objects); 928 } 929 930 public void retrieveAll(Object [] objects) { 931 try { 932 try { 933 if (Debug.DEBUG) { 934 if (retrieveing) { 935 throw BindingSupportImpl.getInstance().internal( 936 "Retrieveing is already set"); 937 } 938 } 939 retrieveing = true; 940 for (int i = 0; i < objects.length; i++) { 941 retrieveImp(objects[i]); 942 } 943 } finally { 944 retrieveing = false; 945 retrieveSet.clear(); 946 } 947 } catch (RuntimeException e) { 948 if (BindingSupportImpl.getInstance().isOwnInternalException(e)) { 949 handleException(e); 950 } else { 951 throw e; 952 } 953 } 954 } 955 956 963 public Extent getExtent(Class persistenceCapableClass, boolean subclasses) { 964 try { 965 return new ExtentImp(persistenceCapableClass, subclasses, proxy); 966 } catch (Exception e) { 967 handleException(e); 968 return null; 969 } 970 } 971 972 975 private int getFgIndex(OID nOID, String fetchGroupName) { 976 int fgIndex = 0; 977 FetchGroup fg = nOID.getAvailableClassMetaData().getFetchGroup( 978 fetchGroupName); 979 if (fg != null) { 980 fgIndex = fg.index; 981 } 982 return fgIndex; 983 } 984 985 public Object getObjectById(Object oid, boolean validate) { 986 if (oid == null) { 987 throw BindingSupportImpl.getInstance().invalidOperation( 988 "The supplied oid is null"); 989 } 990 991 PersistenceCapable pc = null; 992 try { 993 OID nOID = extractOID(oid); 994 PCStateMan stateMan = cache.getByOID(nOID, true); 995 if (stateMan == null) { 996 if (!nOID.isNew()) { 997 1021 if (validate 1022 || (nOID.getAvailableClassMetaData().useKeyGen && nOID.getAvailableClassMetaData( 1023 ).identityType == MDStatics.IDENTITY_TYPE_APPLICATION) 1024 || (!nOID.isResolved() && nOID.getAvailableClassMetaData( 1025 ).isInHeirachy())) { 1026 checkNonTxRead(); 1027 OID nOIDcopy = nOID.copy(); 1028 stateMan = getStateMan(nOIDcopy, 0, -1, -1, validate); 1029 1030 if (stateMan == null) { 1031 throw BindingSupportImpl.getInstance().objectNotFound( 1032 "No row for " + 1033 nOID.getAvailableClassMetaData().storeClass + " " + nOID.toSString()); 1034 } 1035 1036 pc = stateMan.pc; 1037 stateMan.loadDFGIntoPC(this); 1038 } else { 1039 PCStateMan sm = getStateObject(); 1041 sm.init(nOID, this); 1042 pc = sm.pc; 1043 cache.add(sm); 1044 } 1045 } else { 1046 throw BindingSupportImpl.getInstance().objectNotFound( 1047 "No row for " + nOID.toSString()); 1048 } 1049 } else { 1050 pc = stateMan.pc; 1051 if (validate && !stateMan.isTransactional(null)) { 1052 checkNonTxRead(); 1053 if (stateMan.isHollow()) { 1054 stateMan.loadDfgFromHollow(); 1055 } else { 1056 getState(stateMan.oid, null, 0, -1, -1, true); 1057 } 1058 } 1059 } 1060 return pc; 1061 } catch (Exception e) { 1062 handleException(e); 1063 return null; 1064 } 1065 } 1066 1067 public OID extractOID(Object oid) { 1068 OID nOID; 1069 if (oid instanceof VersantOid) { 1070 nOID = modelMetaData.convertJDOGenieOIDtoOID((VersantOid)oid); 1071 nOID = convertNewToActual(nOID); 1072 } else if (oid instanceof OID) { 1073 nOID = convertNewToActual((OID)oid); 1074 } else { 1075 nOID = modelMetaData.convertFromAppIdToOID(oid); 1076 } 1077 return nOID; 1078 } 1079 1080 1086 public Object getObjectByIdForState(OID oid, int stateFieldNo, 1087 int navClassIndex, OID fromOID) { 1088 try { 1089 PersistenceCapable pc; 1090 FieldMetaData fmd = fromOID.getAvailableClassMetaData().stateFields[stateFieldNo]; 1091 if (fmd.embedded) { 1092 PCStateMan owningSM = cache.getByOID(fromOID, false); 1094 if (fmd.nullIndicatorFmd != null) { 1095 if (owningSM.state.isFieldNullorZero(fmd.nullIndicatorFmd.stateFieldNo)) { 1096 return null; 1097 } 1098 } 1099 EmbeddedStateManager embeddedSm = owningSM.createEmbeddedSM(fmd); 1100 pc = embeddedSm.pc; 1101 } else { 1102 PCStateMan stateMan = cache.getByOID(oid, true); 1103 if (stateMan == null) { 1104 stateMan = getStateMan(oid, 0, stateFieldNo, navClassIndex, 1105 false); 1106 if (stateMan != null) { 1107 pc = stateMan.pc; 1108 stateMan.loadDFGIntoPC(this); 1109 } else { 1110 pc = null; 1111 } 1112 } else { 1113 pc = stateMan.pc; 1114 if (!stateMan.isTransactional(null)) { 1115 checkNonTxRead(); 1116 if (stateMan.isHollow()) stateMan.loadDfgFromHollow(); 1118 } 1119 } 1120 } 1121 return pc; 1122 } catch (Exception e) { 1123 handleException(e); 1124 return null; 1125 } 1126 } 1127 1128 public final void checkNonTxRead() { 1129 if (!(transactionActive || nontransactionalRead)) { 1130 throw BindingSupportImpl.getInstance().invalidOperation( 1131 "Must set nonTransactionalRead to true"); 1132 } 1133 } 1134 1135 public final void checkNonTxWrite() { 1136 if (!(transactionActive || nontransactionalWrite)) { 1137 throw BindingSupportImpl.getInstance().invalidOperation( 1138 "Must set nonTransactionalWrite to true"); 1139 } 1140 } 1141 1142 public boolean doBeforeState(boolean isTransient, boolean isTransactional) { 1143 return ((restoreValues || isTransient || isTransactional) && transactionActive); 1144 } 1145 1146 private OID convertNewToActual(OID oid) { 1147 if (!oid.isNew()) { 1148 oid.getAvailableClassMetaData(); 1149 return oid; 1150 } 1151 return oid.getAvailableOID(); 1152 } 1153 1154 public void makePersistent(final Object o) { 1155 try { 1156 if (o == null) { 1157 throw BindingSupportImpl.getInstance().invalidOperation( 1158 "makePersistent called with null object"); 1159 } 1160 checkActiveTx(); 1161 PCStateMan root = txDirtyListHead; 1162 makeReachablePersistent(o); 1163 if (root == null) { 1164 root = txDirtyListTail; 1165 } else { 1166 root = root.next; 1167 } 1168 1169 for (; root != null; root = root.next) root.addRefs(); 1170 } catch (Exception e) { 1171 handleException(e); 1172 } 1173 } 1174 1175 1180 public void makeReachablePersistent(final Object o) { 1181 if (o == null) return; 1182 PersistenceCapable pc = checkPersCapable(o); 1183 PersistenceManager pm = pc.jdoGetPersistenceManager(); 1184 if (pm == null) { 1185 reManage(pc, assignOID(pc), false); 1186 } else { 1187 PMProxy pmProxy = (PMProxy)pm; 1188 if (pmProxy.getRealPM() != this) { 1189 throw BindingSupportImpl.getInstance().invalidOperation("Object is managed by " + pm + " (this is " + proxy + "): " + 1190 pc.getClass() + ": " + Utils.toString(pc)); 1191 } 1192 } 1193 } 1194 1195 public void makePersistentAll(final Object [] pcs) { 1196 try { 1197 ArrayList failed = null; 1198 for (int i = 0; i < pcs.length; i++) { 1199 Object pc = pcs[i]; 1200 try { 1201 makePersistent(pc); 1202 } catch (RuntimeException e) { 1203 if (BindingSupportImpl.getInstance().isOwnException(e)) { 1204 if (BindingSupportImpl.getInstance().getFailedObject(e) == null) { 1205 e = BindingSupportImpl.getInstance().exception( 1206 e.getMessage(), e, pc); 1207 } 1208 if (failed == null) failed = new ArrayList(); 1209 failed.add(e); 1210 } else { 1211 throw e; 1212 } 1213 } 1214 } 1215 if (failed != null) { 1216 int n = failed.size(); 1217 if (n == 1) { 1218 throw (Exception )failed.get(0); 1219 } else { 1220 Throwable [] a = new Throwable [n]; 1221 failed.toArray(a); 1222 throw BindingSupportImpl.getInstance().exception( 1223 n + " instances failed to persist", 1224 a); 1225 } 1226 } 1227 } catch (Exception e) { 1228 handleException(e); 1229 } 1230 } 1231 1232 public void makePersistentAll(final Collection pcs) { 1233 try { 1234 ArrayList failed = null; 1235 for (Iterator i = pcs.iterator(); i.hasNext();) { 1236 Object pc = i.next(); 1237 try { 1238 makePersistent(pc); 1239 } catch (RuntimeException e) { 1240 if (BindingSupportImpl.getInstance().isOwnException(e)) { 1241 if (BindingSupportImpl.getInstance().getFailedObject(e) == null) { 1242 e = BindingSupportImpl.getInstance().exception( 1243 e.getMessage(), e, pc); 1244 } 1245 if (failed == null) failed = new ArrayList(); 1246 failed.add(e); 1247 } else { 1248 throw e; 1249 } 1250 } 1251 } 1252 if (failed != null) { 1253 int n = failed.size(); 1254 if (n == 1) { 1255 throw (Exception )failed.get(0); 1256 } else { 1257 Throwable [] a = new Throwable [n]; 1258 failed.toArray(a); 1259 throw BindingSupportImpl.getInstance().exception( 1260 n + " instances failed to persist", 1261 a); 1262 } 1263 } 1264 } catch (Exception e) { 1265 handleException(e); 1266 } 1267 } 1268 1269 1272 public void deletePersistentAll(Object [] pcs) { 1273 try { 1274 for (int i = 0; i < pcs.length; i++) { 1275 deletePersistent(pcs[i]); 1276 } 1277 } catch (Exception e) { 1278 handleException(e); 1279 } 1280 } 1281 1282 1285 public void deletePersistent(Object pc) { 1286 checkActiveTx(); 1287 if (isTransient(pc)) { 1288 throw BindingSupportImpl.getInstance().invalidOperation( 1289 "The instance is transient"); 1290 } 1291 try { 1292 pmPreCheck(pc).deletePersistent(); 1293 } catch (Exception e) { 1294 handleException(e); 1295 } 1296 } 1297 1298 1301 public void deletePersistentAll(Collection pcs) { 1302 try { 1303 for (Iterator iterator = pcs.iterator(); iterator.hasNext();) { 1304 deletePersistent(iterator.next()); 1305 } 1306 } catch (Exception e) { 1307 handleException(e); 1308 } 1309 } 1310 1311 1316 public void makeTransient(Object pc) { 1317 checkPersCapable(pc); 1318 try { 1319 if (isTransient(pc)) { 1320 return; 1322 } 1323 pmPreCheck(pc).makeTransient(); 1324 } catch (Exception e) { 1325 handleException(e); 1326 } 1327 } 1328 1329 public void makeTransientRecursive(Object pc) { 1330 checkPersCapable(pc); 1331 try { 1332 if (isTransient(pc)) { 1333 return; 1335 } 1336 pmPreCheck(pc).makeTransientRecursive(); 1337 } catch (Exception e) { 1338 handleException(e); 1339 } 1340 } 1341 1342 1347 public void makeTransientAll(Object [] pcs) { 1348 try { 1349 Map failed = new HashMap(); 1350 for (int i = 0; i < pcs.length; i++) { 1351 Object pc = pcs[i]; 1352 try { 1353 makeTransient(pc); 1354 } catch (Exception e) { 1355 failed.put(pc, e); 1356 } 1357 } 1358 if (failed.size() > 0) { 1359 throw BindingSupportImpl.getInstance().invalidOperation( 1360 "Errors occured with makeTransientAll: " + failed); 1361 } 1362 } catch (RuntimeException e) { 1363 handleException(e); 1364 } 1365 } 1366 1367 1372 public void makeTransientAll(Collection pcs) { 1373 try { 1374 if (pcs == null) return; 1375 makeTransientAll(pcs.toArray()); 1376 } catch (Exception e) { 1377 handleException(e); 1378 } 1379 } 1380 1381 private final boolean isTransient(Object pc) { 1382 if (JDOHelper.getPersistenceManager(pc) == null) { 1383 return true; 1384 } 1385 return false; 1386 } 1387 1388 public void makeTransactional(Object pc) { 1389 try { 1390 if (JDOHelper.getPersistenceManager(pc) == null) { 1391 reManage((PersistenceCapable)pc, 1393 assignOID((PersistenceCapable)pc), true); 1394 } 1395 PCStateMan pcStateObject = pmPreCheck(pc); 1396 pcStateObject.makeTransactional(); 1397 } catch (Exception e) { 1398 handleException(e); 1399 } 1400 } 1401 1402 public void makeTransactionalAll(Object [] pcs) { 1403 if (pcs == null) return; 1404 try { 1405 Map failed = new HashMap(pcs.length); 1406 for (int i = 0; i < pcs.length; i++) { 1407 Object pc = pcs[i]; 1408 try { 1409 makeTransactional(pc); 1410 } catch (Exception e) { 1411 failed.put(pc, e); 1412 } 1413 } 1414 if (failed.size() > 0) { 1415 throw BindingSupportImpl.getInstance().invalidOperation( 1416 "Errors occured with makePersistentAll:" + failed); 1417 } 1418 } catch (RuntimeException e) { 1419 handleException(e); 1420 } 1421 } 1422 1423 public void makeTransactionalAll(Collection pcs) { 1424 if (pcs == null) return; 1425 try { 1426 makeTransactionalAll(pcs.toArray()); 1427 } catch (Exception e) { 1428 handleException(e); 1429 } 1430 } 1431 1432 private final void makeNonTransactionalImp(Object pc) { 1433 PCStateMan pcStateObject = pmPreCheck(pc); 1434 pcStateObject.makeNonTransactional(); 1435 } 1436 1437 public void makeNontransactional(Object pc) { 1438 try { 1439 makeNonTransactionalImp(pc); 1440 } catch (Exception e) { 1441 handleException(e); 1442 } 1443 } 1444 1445 public void makeNontransactionalAll(Object [] pcs) { 1446 try { 1447 for (int i = 0; i < pcs.length; i++) { 1448 makeNonTransactionalImp(pcs[i]); 1449 } 1450 } catch (Exception e) { 1451 handleException(e); 1452 } 1453 } 1454 1455 public void makeNontransactionalAll(Collection pcs) { 1456 for (Iterator iterator = pcs.iterator(); iterator.hasNext();) { 1457 makeNonTransactionalImp(iterator.next()); 1458 } 1459 } 1460 1461 public void setUserObject(Object o) { 1462 try { 1463 sm.setUserObject(userObject = o); 1464 } catch (Exception e) { 1465 handleException(e); 1466 } 1467 } 1468 1469 public Object getUserObject() { 1470 return userObject; 1471 } 1472 1473 public PersistenceManagerFactory getPersistenceManagerFactory() { 1474 return pmf; 1475 } 1476 1477 public void setMultithreaded(boolean flag) { 1478 if (flag && !multithreaded) { 1481 throw BindingSupportImpl.getInstance().invalidOperation("PM.setMultithreaded(true) is not allowed if the PM " + 1482 "was created from a PMF with multithreaded false"); 1483 } 1484 } 1487 1488 public boolean getMultithreaded() { 1489 return multithreaded; 1490 } 1491 1492 public void setMultithreadedImp(boolean flag) { 1493 multithreaded = flag; 1494 createProxy(); 1495 } 1496 1497 public void setIgnoreCache(boolean flag) { 1498 this.ignoreCache = flag; 1499 } 1500 1501 public boolean getIgnoreCache() { 1502 return this.ignoreCache; 1503 } 1504 1505 1509 private final PCStateMan pmPreCheck(final Object pc) { 1510 return pmPreCheck(checkPersCapable(pc)); 1511 1512 } 1513 1514 private PCStateMan pmPreCheck(PersistenceCapable pc) { 1515 if (!checkManagedBy(pc)) { 1516 return null; 1517 } 1518 PCStateMan pcState = getInternalSM(pc); 1519 if (Debug.DEBUG) { 1520 if (pcState == null && JDOHelper.getPersistenceManager(pc) != null) { 1521 throw BindingSupportImpl.getInstance().internal( 1522 "The pm is set on instance but is not in weak list"); 1523 } 1524 } 1525 return pcState; 1526 } 1527 1528 private final boolean checkManagedBy(PersistenceCapable pc) { 1529 PMProxy pm = (PMProxy)pc.jdoGetPersistenceManager(); 1530 if (pm != null) { 1531 if (pm == proxy) return true; 1532 throw BindingSupportImpl.getInstance().invalidOperation("Object is managed by " + pm + " (this is " + proxy + "): " + 1533 pc.getClass() + ": " + Utils.toString(pc)); 1534 } 1535 return false; 1536 } 1537 1538 private final void checkActiveTx() { 1539 if (!isActive()) { 1540 throw BindingSupportImpl.getInstance().invalidOperation( 1541 "No active transaction."); 1542 } 1543 } 1544 1545 public void begin() { 1546 if (managed) { 1547 throw BindingSupportImpl.getInstance().invalidOperation( 1548 "May not call begin in managed transaction environment"); 1549 } 1550 beginImp(); 1551 } 1552 1553 private void beginImp() { 1554 if (transactionActive) { 1555 throw BindingSupportImpl.getInstance().invalidOperation( 1556 "The transaction is already active"); 1557 } 1558 try { 1559 transactionActive = true; 1560 sm.begin(optimistic); 1561 if (!optimistic && !interceptDfgFieldAccess) { 1562 cache.setInterceptDfgFieldAccess(true); 1563 } 1564 } catch (Exception e) { 1565 handleException(e); 1566 } 1567 } 1568 1569 1579 public void rollback() { 1580 if (Debug.DEBUG) { 1581 System.out.println( 1582 ">>>>>>>>>>> JdoGeniePersistenceManagerImp.rollback <<<<<<<<<<<<<<<"); 1583 } 1584 if (managed) { 1585 throw BindingSupportImpl.getInstance().invalidOperation( 1586 "May not call rollback in managed transaction environment"); 1587 } 1588 rollbackImp(); 1589 } 1590 1591 1595 private void fatalReset() { 1596 mustNotPool = true; 1597 } 1598 1599 1603 public void rollbackForFatalExceptionInJDOConnectionProxy() { 1604 if (managed || !transactionActive) return; 1605 rollbackImp(); 1606 } 1607 1608 1611 private void rollbackImp() { 1612 if (busyWithRollback) return; 1613 checkActiveTx(); 1614 resetEpcFields(); 1615 try { 1616 busyWithRollback = true; 1617 1618 if (synchronizationInstance != null) { 1619 synchronizationInstance.afterCompletion( 1620 Status.STATUS_ROLLING_BACK); 1621 } 1622 1623 try { 1624 cache.doRollback(retainValues); 1625 sm.rollback(); 1626 } finally { 1627 reset(); 1628 } 1629 1630 if (synchronizationInstance != null) { 1631 synchronizationInstance.afterCompletion( 1632 Status.STATUS_ROLLEDBACK); 1633 } 1634 1635 } catch (Exception e) { 1636 fatalReset(); 1637 if (BindingSupportImpl.getInstance().isOwnException(e)) { 1638 throw (RuntimeException )e; 1639 } else { 1640 throw BindingSupportImpl.getInstance().internal(e.getMessage(), 1641 e); 1642 } 1643 } finally { 1644 transactionActive = false; 1645 busyWithRollback = false; 1646 } 1647 } 1648 1649 public void setRestoreValues(boolean b) { 1650 checkPropChange(); 1651 this.restoreValues = b; 1652 } 1653 1654 public boolean getRestoreValues() { 1655 return restoreValues; 1656 } 1657 1658 1667 public void checkModelConsistency() { 1668 cache.checkModelConsistency(); 1669 } 1670 1671 1674 public void addForDelete(OID oid, State state) { 1675 if (Debug.DEBUG) { 1676 if (oid.getAvailableClassMetaData() == null) { 1678 BindingSupportImpl.getInstance().internal("oid is untyped: " + 1679 oid); 1680 } 1681 } 1682 toBeDeleted.add(oid, state); 1683 } 1684 1685 1689 public void commit() { 1690 if (managed) { 1691 throw BindingSupportImpl.getInstance().invalidOperation( 1692 "May not call commit in managed transaction environment"); 1693 } 1694 if (!transactionActive) { 1695 throw BindingSupportImpl.getInstance().invalidOperation( 1696 "Transaction is not active"); 1697 } 1698 internalCommit(false); 1699 } 1700 1701 private void dumpTxDirtyList(String msg) { 1702 System.out.println("--- txDirtyListHead: " + msg); 1703 for (PCStateMan o = txDirtyListTail; o != null; o = o.next) { 1704 System.out.println(o.pc.getClass().getName() + "@" + 1705 Integer.toHexString(System.identityHashCode(o.pc)) + 1706 ": " + o.pc); 1707 } 1708 System.out.println("---"); 1709 } 1710 1711 private void internalCommit(boolean phase) { 1712 StatesReturned sc = null; 1713 1714 if (synchronizationInstance != null) { 1715 synchronizationInstance.beforeCompletion(); 1716 synchronizationInstance.afterCompletion(Status.STATUS_COMMITTING); 1717 } 1718 1719 try { 1720 prepareForStore(true); 1721 1722 sc = sm.store(storeOidStateContainer, toBeDeleted, retainValues, 1723 phase 1724 ? StorageManager.STORE_OPTION_PREPARE 1725 : StorageManager.STORE_OPTION_COMMIT, 1726 false); 1727 1728 resetEpcFields(); 1729 updateOIDsAndDoAutoS(sc); 1730 cache.doCommit(retainValues); 1731 1732 invokePostStore(); 1733 1734 if (!phase) { 1735 1736 if (synchronizationInstance != null) { 1737 synchronizationInstance.afterCompletion( 1738 Status.STATUS_COMMITTED); 1739 } 1740 1741 } 1742 1743 reset(); 1744 transactionActive = false; 1745 } catch (Exception e) { 1746 handleException(e); 1747 } finally { 1748 if (sc != null) { 1749 sc.clear(); 1750 } 1751 } 1752 } 1753 1754 1759 private void prepareForStore(boolean commit) { 1760 boolean preStoreCalled = false; 1761 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1762 1763 i.addRefs(); 1764 preStoreCalled |= i.doJDOPreStore(listeners); 1765 } 1766 for (; preStoreCalled;) { 1767 PCStateMan root = txDirtyListHead; 1768 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1769 1770 i.addRefs(); 1771 } 1772 if (root == txDirtyListHead) break; 1773 preStoreCalled = false; 1774 for (PCStateMan i = root; i != null; i = i.next) { 1775 preStoreCalled |= i.doJDOPreStore(listeners); 1776 } 1777 } 1778 1779 storeOidStateContainer.clear(); 1780 toBeDeleted.clear(); 1781 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1782 i.prepareCommitOrFlush(commit); 1783 } 1784 if (checkModelConsistencyOnCommit) { 1785 checkModelConsistency(); 1786 } 1787 1788 if (commit) { storeOidStateContainer.epcAll = epcAll; 1790 storeOidStateContainer.epcOids = epcObjectCount > 0 1791 ? modelMetaData.convertToOID(epcObjects, epcObjectCount) 1792 : null; 1793 storeOidStateContainer.epcClasses = epcClasses; 1794 storeOidStateContainer.epcClassCount = epcClassCount; 1795 } 1796 } 1797 1798 private void invokePostStore() { 1799 if (listeners != null && listeners.hasPostStoreListeners()) { 1800 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1801 i.firePostStore(listeners); 1802 } 1803 } 1804 } 1805 1806 1811 public void flush() { 1812 StatesReturned sc = null; 1813 try { 1814 prepareForStore(true); 1815 1816 sc = sm.store(storeOidStateContainer, toBeDeleted, 1817 false, StorageManager.STORE_OPTION_FLUSH, true); 1818 1819 updateOIDsAndDoAutoS(sc); 1820 1821 cache.doCommit(retainValues); 1822 1823 invokePostStore(); 1824 1825 resetEpcFields(); 1826 reset(); 1827 } catch (Exception x) { 1828 handleException(x); 1829 } finally { 1830 if (sc != null) { 1831 sc.clear(); 1832 } 1833 } 1834 } 1835 1836 public void flush(boolean retainValues) { 1837 if (retainValues) { 1838 flushRetainState(); 1839 } else { 1840 flush(); 1841 } 1842 } 1843 1844 public List versantAllDirtyInstances() { 1845 if (txDirtyListTail == null) return Collections.EMPTY_LIST; 1846 List l = new ArrayList(); 1847 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1848 l.add(i.pc); 1849 } 1850 return l; 1851 } 1852 1853 1863 public void flushRetainState() { 1864 if (!transactionActive) return; 1865 StatesReturned sc = null; 1866 1867 storeOidStateContainer.clear(); 1868 toBeDeleted.clear(); 1869 try { 1870 prepareForStore(false); 1871 1872 if (storeOidStateContainer.isEmpty() && toBeDeleted.size() == 0) { 1873 return; 1874 } 1875 1876 sc = sm.store(storeOidStateContainer, toBeDeleted, true, 1877 StorageManager.STORE_OPTION_FLUSH, false); 1878 1879 updateOIDsAndDoAutoS(sc); 1880 for (PCStateMan i = txDirtyListTail; i != null; i = i.next) { 1881 i.flushCommit(); 1882 } 1883 1884 invokePostStore(); 1885 1886 storeOidStateContainer.clear(); 1887 toBeDeleted.clear(); 1888 } catch (Exception x) { 1889 handleException(x); 1890 } finally { 1891 try { 1892 sc.clear(); 1893 } catch (Exception e) { 1894 } 1896 } 1897 } 1898 1899 1902 public void phaseCommit1() { 1903 internalCommit(true); 1904 } 1905 1906 1909 public void phaseCommit2() { 1910 sm.commit(); 1911 1912 if (synchronizationInstance != null) { 1913 synchronizationInstance.afterCompletion(Status.STATUS_COMMITTED); 1914 } 1915 1916 } 1917 1918 public boolean isActive() { 1919 return transactionActive; 1920 } 1921 1922 public final boolean isActiveDS() { 1923 return transactionActive && !optimistic; 1924 } 1925 1926 public void setNontransactionalRead(boolean nontransactionalRead) { 1927 checkPropChange(); 1928 this.nontransactionalRead = nontransactionalRead; 1929 } 1930 1931 public boolean getNontransactionalRead() { 1932 return nontransactionalRead; 1933 } 1934 1935 public void setNontransactionalWrite(boolean nontransactionalWrite) { 1936 checkPropChange(); 1937 this.nontransactionalWrite = nontransactionalWrite; 1938 } 1939 1940 public boolean getNontransactionalWrite() { 1941 return nontransactionalWrite; 1942 } 1943 1944 public void setRetainValues(boolean retainValues) { 1945 this.retainValues = retainValues; 1947 } 1948 1949 1952 private final void checkPropChange() { 1953 if (transactionActive) { 1954 throw BindingSupportImpl.getInstance().invalidOperation( 1955 "May not be changed in active transaction"); 1956 } 1957 } 1958 1959 public boolean getRetainValues() { 1960 return retainValues; 1961 } 1962 1963 public void setOptimistic(boolean optimistic) { 1964 checkPropChange(); 1965 this.optimistic = optimistic; 1966 } 1967 1968 public boolean getOptimistic() { 1969 return optimistic; 1970 } 1971 1972 1973 public void setSynchronization(Synchronization sync) { 1974 this.synchronizationInstance = sync; 1975 } 1976 1977 public Synchronization getSynchronization() { 1978 return synchronizationInstance; 1979 } 1980 1981 1982 public PersistenceManager getPersistenceManager() { 1983 return VersantPersistenceManagerImp.this; 1984 } 1985 1986 1988 1989 1992 private NewObjectOID assignOID(PersistenceCapable pc) { 1993 ClassMetaData cmd = modelMetaData.getClassMetaData(pc.getClass()); 1994 if (cmd == null) { 1995 throw BindingSupportImpl.getInstance().invalidOperation( 1996 "There is no metadata registered for " + pc.getClass()); 1997 } 1998 if (cmd.instancesNotAllowed) { 1999 throw BindingSupportImpl.getInstance().invalidOperation( 2000 "Instances of " + cmd.qname + " may not be persistent or managed"); 2001 } 2002 NewObjectOID oid = cmd.createNewObjectOID(); 2003 oid.init(++counter); 2004 return oid; 2005 } 2006 2007 2011 public PCStateMan reManage(OID oid, State state) { 2012 if (oid.getAvailableClassMetaData() == null) { 2013 OID tmp = state.getClassMetaData(modelMetaData).createOID(true); 2015 tmp.setLongPrimaryKey(oid.getLongPrimaryKey()); 2016 oid = tmp; 2017 } 2018 PCStateMan stateObject = getStateObject(); 2019 stateObject.init(oid, state.getClassMetaData(modelMetaData), state, this); 2020 return stateObject; 2021 } 2022 2023 private final void reManage(PersistenceCapable pc, OID oid, 2024 boolean isTransactional) { 2025 PCStateMan sm = getStateObject(); 2026 pc.jdoReplaceStateManager(createStateManagerProxy(sm)); 2027 sm.init(pc, oid, isTransactional); 2028 sm.getRealOIDIfAppId(); 2029 2030 if (!isTransactional 2033 && sm.getClassMetaData().identityType == MDStatics.IDENTITY_TYPE_APPLICATION) { 2034 OID realOID = ((NewObjectOID)sm.oid).realOID; 2035 if (realOID != null && cache.contains(realOID)) { 2036 2037 throw BindingSupportImpl.getInstance(). 2040 runtime("Instance of " + sm.getClassMetaData().qname + 2041 " with identity '" + realOID + "' already exists in" + 2042 " the local PM cache"); 2043 2044 2045 2046 } 2047 } 2048 2049 cache.add(sm); 2051 if (Debug.DEBUG) { 2052 if (sm.cacheEntry == null) { 2053 throw BindingSupportImpl.getInstance().internal( 2054 "cacheEntry must be initialized"); 2055 } 2056 } 2057 } 2058 2059 2064 public StateManager createStateManagerProxy(PCStateMan sm) { 2065 if (multithreaded) { 2066 return new SynchronizedStateManagerProxy(proxy, sm); 2067 } else { 2068 return sm; 2069 } 2070 } 2071 2072 2077 public void addTxStateObject(PCStateMan stateObject) { 2078 if (Debug.DEBUG) { 2079 if (!stateObject.isTx()) { 2080 throw BindingSupportImpl.getInstance().internal( 2081 "The instance is not Transactional"); 2082 } 2083 } 2084 2085 if (stateObject.isDirty()) { 2086 if (!stateObject.isInDirtyList(txDirtyListHead)) { 2087 addTxDirty(stateObject); 2088 } 2089 } else { 2090 if (stateObject.isInDirtyList(txDirtyListHead)) { 2091 removeTxDirty(stateObject); 2092 } 2093 } 2094 } 2095 2096 2099 private void addTxDirty(PCStateMan pc) { 2100 if (txDirtyListHead == null) { 2101 txDirtyListHead = txDirtyListTail = pc; 2102 pc.next = null; 2103 pc.prev = null; 2104 } else { 2105 pc.prev = txDirtyListHead; 2106 txDirtyListHead.next = pc; 2107 pc.next = null; 2108 txDirtyListHead = pc; 2109 } 2110 dirtyCmdBits.add(pc.getClassMetaData()); 2111 pc.inDirtyList = true; 2112 } 2113 2114 2117 private void removeTxDirty(PCStateMan pc) { 2118 if (Debug.DEBUG) { 2119 if (!pc.isInDirtyList(txDirtyListHead)) { 2120 throw BindingSupportImpl.getInstance().internal( 2121 "not in dirty list: " + pc); 2122 } 2123 } 2124 if (txDirtyListTail == pc) { 2125 txDirtyListTail = pc.next; 2126 } else { 2127 pc.prev.next = pc.next; 2128 } 2129 if (txDirtyListHead == pc) { 2130 txDirtyListHead = pc.prev; 2131 } else { 2132 pc.next.prev = pc.prev; 2133 } 2134 dirtyCmdBits.remove(pc.getClassMetaData()); 2135 } 2136 2137 2140 public void clearTxDirtyList() { 2141 for (PCStateMan i = txDirtyListTail; i != null;) { 2142 PCStateMan next = i.next; 2143 i.prev = null; 2144 i.next = null; 2145 i = next; 2146 dirtyCmdBits.clear(); 2147 } 2148 txDirtyListHead = txDirtyListTail = null; 2149 } 2150 2151 public void removeTxStateObject(PCStateMan stateObject) { 2152 if (stateObject.isInDirtyList(txDirtyListHead)) { 2153 removeTxDirty(stateObject); 2154 } 2155 } 2156 2157 private final void reset() { 2158 storeOidStateContainer.clear(); 2159 clearTxDirtyList(); 2160 } 2161 2162 2165 public void resetForPooling() { 2166 if (Debug.DEBUG) { 2167 if (transactionActive) { 2168 throw BindingSupportImpl.getInstance().fatal( 2169 "The tx must be inactive"); 2170 } 2171 } 2172 managed = false; 2173 cache.clear(); 2174 sm.reset(); 2175 sm.setUserObject(userObject = null); 2176 2177 synchronizationInstance = null; 2178 2179 resetEpcFields(); 2180 reset(); 2181 } 2182 2183 2186 private void checkClosed() { 2187 checkInPool(); 2188 if (closed) { 2189 throw BindingSupportImpl.getInstance().invalidOperation( 2190 2191 "The 'PersistenceManager' is already closed"); 2192 2193 2194 } 2195 } 2196 2197 public PersistenceManager getPersistenceManager(PersistenceCapable pc) { 2198 return this; 2199 } 2200 2201 private PCStateMan getStateObject() { 2202 return new PCStateMan(cache, modelMetaData, proxy); 2203 } 2204 2205 2221 2223 public boolean isPNonTx(Object pc) { 2224 return pmPreCheck(pc).isPNonTx(); 2225 } 2226 2227 public boolean isPClean(Object pc) { 2228 return pmPreCheck(pc).isPClean(); 2229 } 2230 2231 public boolean isPNew(Object pc) { 2232 return pmPreCheck(pc).isPNew(); 2233 } 2234 2235 public boolean isPNewDeleted(Object pc) { 2236 return pmPreCheck(pc).isPNewDeleted(); 2237 } 2238 2239 public boolean isPDeleted(Object pc) { 2240 return pmPreCheck(pc).isPDeleted(); 2241 } 2242 2243 public boolean isTClean(Object pc) { 2244 return pmPreCheck(pc).isTClean(); 2245 } 2246 2247 public boolean isTDirty(Object pc) { 2248 return pmPreCheck(pc).isTDirty(); 2249 } 2250 2251 public boolean isPDirty(Object pc) { 2252 return pmPreCheck(pc).isPDirty(); 2253 } 2254 2255 2260 public OID getInternalOID(final PersistenceCapable pc) { 2261 if (pc == null) return null; 2262 return getInternalSM(pc).oid; 2263 } 2264 2265 2269 public PCStateMan getInternalSM(final PersistenceCapable pc) { 2270 if (pc == null) return null; 2271 requestedPCState = null; 2272 pc.jdoGetPersistenceManager(); 2273 if (requestedPCState == null) { 2274 throw BindingSupportImpl.getInstance().internal("Instance not managed: " + 2275 pc.getClass().getName() + "@" + 2276 Integer.toHexString(System.identityHashCode(pc)) + ": " + 2277 pc.toString()); 2278 } 2279 return requestedPCState; 2280 } 2281 2282 public PCStateMan getSMIfManaged(PersistenceCapable pc) { 2283 if (pc == null) return null; 2284 requestedPCState = null; 2285 pc.jdoGetPersistenceManager(); 2286 return requestedPCState; 2287 } 2288 2289 2293 public PCStateMan getInternalSM(OID oid) { 2294 if (oid == null) return null; 2295 return getInternalSM((PersistenceCapable)getObjectById(oid, false)); 2296 } 2297 2298 2301 public State getInternaleState(PersistenceCapable pc) { 2302 PCStateMan pcState = getInternalSM(pc); 2303 if (pcState == null) return null; 2304 return pcState.state; 2305 } 2306 2307 public void dump(OID oid) { 2308 if (Debug.DEBUG) { 2309 PCStateMan pcStateObject = cache.getByOID(oid, true); 2310 if (pcStateObject != null) { 2311 pcStateObject.dump(); 2312 } else { 2313 if (Debug.DEBUG) { 2314 Debug.OUT.println("######## null for dump#######"); 2315 } 2316 } 2317 } 2318 } 2319 2320 2323 public boolean isDirty() { 2324 return txDirtyListHead != null; 2325 } 2326 2327 2335 private PCStateMan getStateMan(OID aOID, int fgIndex, int fieldNo, 2336 int navClassIndex, boolean ignoreLocalPmCache) { 2337 StatesReturned container = null; 2338 try { 2339 container = getStateJdoConnection(aOID, null, fgIndex, 2340 aOID.getAvailableClassId(), 2341 ignoreLocalPmCache, fieldNo, navClassIndex); 2342 2343 if (Debug.DEBUG) { 2344 if (container.get(container.getDirectOID()) == NULLState.NULL_STATE) { 2345 if (container.size() != 1) { 2347 throw BindingSupportImpl.getInstance().internal("Then directOid of the container is null " + 2348 "so there should not be any other instances"); 2349 } 2350 } 2351 } 2352 2353 return addAndReturnFirstDirect(container); 2354 } finally { 2355 if (container != null) container.clear(); 2356 } 2357 } 2358 2359 2363 private StatesReturned getStateJdoConnection(OID oid, State current, 2364 int fetchGroup, int classId, boolean ignoreLocalPmCache, 2365 int fieldNo, int navClassIndex) { 2366 2368 if (classId < 0) classId = oid.getAvailableClassId(); 2369 ClassMetaData cmd = oid.getAvailableClassMetaData(); 2370 FetchGroup fg = cmd == null ? null : cmd.getFetchGroup(fetchGroup, classId); 2371 2372 FieldMetaData triggerField; 2373 if (navClassIndex >= 0) { ClassMetaData navCmd = modelMetaData.classes[navClassIndex]; 2375 triggerField = navCmd.stateFields[fieldNo]; 2376 } else if (fieldNo >= 0 && cmd != null) { triggerField = cmd.stateFields[cmd.absToRel[fieldNo]]; 2378 } else { 2379 triggerField = null; 2380 } 2381 2382 return sm.fetch(this, oid, current, fg, triggerField); 2383 } 2384 2385 2394 public StatesReturned getState(OID oid, State current, int fgi, int fieldNo, 2395 int navClassIndex, boolean ignoreLocalPmCache) { 2396 StatesReturned container = getStateJdoConnection(oid, 2397 current == null || current.isEmpty() ? null : current, 2398 fgi, oid.getAvailableClassId(), 2399 ignoreLocalPmCache, fieldNo, navClassIndex); 2400 2401 if (Debug.DEBUG) { 2402 if (container.get(container.getDirectOID()) == NULLState.NULL_STATE) { 2403 if (container.size() != 1) { 2405 throw BindingSupportImpl.getInstance().internal("Then directOid of the container is null " + 2406 "so there should not be any other instances"); 2407 } 2408 } 2409 } 2410 addToCache(container); 2411 return container; 2412 } 2413 2414 2418 public void getStateForRefresh(OID oid, State current, int fgi) { 2419 StatesReturned container = null; 2420 try { 2421 container = getStateJdoConnection(oid, 2422 current == null || current.isEmpty() ? null : current, 2423 fgi, oid.getAvailableClassId(), true, 2424 -1, -1); 2425 addToCache(container); 2426 } finally { 2427 if (container != null) container.clear(); 2428 } 2429 } 2430 2431 private void fillCacheWith(OIDArray oids, int fgi, int stateFieldNo, 2432 int navClassIndex) { 2433 StatesReturned container = null; 2434 try { 2435 FieldMetaData triggerField; 2436 if (navClassIndex >= 0) { ClassMetaData navCmd = modelMetaData.classes[navClassIndex]; 2438 triggerField = navCmd.stateFields[stateFieldNo]; 2439 } else { 2440 triggerField = null; 2441 } 2442 container = sm.fetch(this, oids, triggerField); 2443 addToCache(container); 2444 } finally { 2445 if (container != null) container.clear(); 2446 } 2447 } 2448 2449 2452 private static final void checkPM(PersistenceManager otherPM, 2453 PersistenceManager currentPM) { 2454 if (otherPM != null && otherPM != currentPM) { 2455 throw BindingSupportImpl.getInstance().invalidOperation( 2456 "The instance is not managed by this PersistenceManager"); 2457 } 2458 } 2459 2460 private static final PersistenceCapable checkPersCapable(Object o) { 2461 try { 2462 return (PersistenceCapable)o; 2463 } catch (ClassCastException e) { 2464 throw BindingSupportImpl.getInstance().invalidOperation("The supplied instance is not of type " + 2465 PersistenceCapable.class.getName() + 2466 " (" + o.getClass().getName() + ")"); 2467 } 2468 } 2469 2470 2481 public void checkToPreFetch(Object [] oids, int stateFieldNo, 2482 int navClassIndex) { 2483 if (oids != null && oids.length > 0 && oids[0] != null 2484 && cache.getByOID((OID)oids[0], true) == null) { 2485 OIDArray oidArray = new OIDArray(); 2486 for (int i = 0; i < oids.length && oids[i] != null; i++) { 2487 oidArray.add((OID)oids[i]); 2488 } 2489 fillCacheWith(oidArray, 0, stateFieldNo, navClassIndex); 2490 } 2491 } 2492 2493 2500 private final void handleException(Exception x) { 2501 if (BindingSupportImpl.getInstance().isOwnFatalException(x) && isActive()) { 2502 try { 2503 rollbackImp(); 2504 } catch (Exception e) { 2505 } 2508 } 2509 if (BindingSupportImpl.getInstance().isOwnInternalException(x)) { 2510 fatalReset(); 2511 throw (RuntimeException )x; 2512 } else if (BindingSupportImpl.getInstance().isOwnException(x)) { 2513 throw (RuntimeException )x; 2514 } else { 2515 fatalReset(); 2516 throw BindingSupportImpl.getInstance().internal(x.getMessage(), x); 2517 } 2518 } 2519 2520 2525 public void convertPcParamsToOID(Object [] params) { 2526 if (params == null) return; 2527 int n = params.length; 2528 for (int i = 0; i < n; i++) { 2529 Object param = params[i]; 2530 if (param == null) continue; 2531 if (param instanceof Collection) { 2532 List l = new ArrayList((Collection)param); 2533 for (int j = 0; j < l.size(); j++) { 2534 Object o = (Object )l.get(j); 2535 o = convertPcParamsToOIDImp(o, i); 2536 if (o instanceof OID) { 2537 l.set(j, o); 2538 } 2539 } 2540 params[i] = l; 2541 } else { 2542 params[i] = convertPcParamsToOIDImp(param, i); 2543 } 2544 } 2545 } 2546 2547 private Object convertPcParamsToOIDImp(Object param, int paramIndex) { 2548 if (param == null) return param; 2549 if (param instanceof PersistenceCapable) { 2550 PersistenceCapable pc = (PersistenceCapable)param; 2551 if (pc.jdoGetPersistenceManager() != proxy) { 2552 if (pc.jdoGetPersistenceManager() != null) { 2553 throw BindingSupportImpl.getInstance().invalidOperation("PC parameter " + paramIndex + " is managed by " + pc.jdoGetPersistenceManager() + 2554 " (this is " + proxy + "): " + 2555 pc.getClass() + ": " + Utils.toString(pc)); 2556 } else { 2557 throw BindingSupportImpl.getInstance().invalidOperation("PC parameter " + paramIndex + " is transient: " + 2558 pc.getClass() + ": " + Utils.toString(pc)); 2559 } 2560 } 2561 param = getInternalOID((PersistenceCapable)param); 2562 } else if (param instanceof VersantOid) { 2563 OID oid = modelMetaData.convertJDOGenieOIDtoOID((VersantOid)param); 2565 param = convertNewToActual(oid); 2566 } else { 2567 ClassMetaData cmd = 2568 modelMetaData.getClassMetaDataForObjectIdClass( 2569 param.getClass()); 2570 if (cmd != null) { OID oid = cmd.createOID(false); 2572 oid.fillFromPK(param); 2573 param = oid; 2574 } 2575 } 2576 return param; 2577 } 2578 2579 2580 2582 2583 2584 private int txTimeout = 3000; 2585 private Xid xid = null; 2586 2587 2588 private int txState; 2589 public static final int TX_INACTIVE = 0; 2590 public static final int TX_STARTED = 1; 2591 public static final int TX_FAIL = 2; 2592 public static final int TX_PREPARED = 4; 2593 public static final int TX_SUSPENDED = 8; 2594 2595 2598 private boolean managed; 2599 2602 private boolean managedClosed = false; 2603 2604 2609 public boolean isManaged() { 2610 return managed; 2611 } 2612 2613 2618 public void setManaged(boolean managed) { 2619 this.managed = managed; 2620 this.managedClosed = false; 2621 } 2622 2623 2643 2644 public void start(Xid xid, int flags) throws XAException { 2645 if (Debug.DEBUG) { 2646 Debug.OUT.println("***** JdoGeniePersistenceManagerImp.start ***** flag = " 2647 + getFlagString(flags) + " for \n" + this); 2648 System.out.println("xid = " + xid); 2649 } 2650 checkInPool(); 2651 switch (flags) { 2652 case TMNOFLAGS: 2653 case TMJOIN: 2654 begin(xid); 2655 break; 2656 case TMRESUME: 2657 if (checkId(xid)) { 2658 resume(xid); 2659 } 2660 break; 2661 default: 2662 throw new XAException ( 2663 "Unsupported state for method start state = " + flags); 2664 } 2665 } 2666 2667 2668 2669 private boolean checkId(Xid xid) { 2670 if (!this.xid.equals(xid)) { 2671 return false; 2673 } 2674 return true; 2675 } 2676 2677 2678 2679 private void resume(Xid xid) throws XAException { 2680 checkInPool(); 2681 if (this.txState != TX_SUSPENDED) { 2682 throw new XAException ( 2683 "Could resume a transaction that was not suspended"); 2684 } 2685 this.txState = TX_STARTED; 2686 } 2687 2688 2689 2690 private void begin(Xid xid) throws XAException { 2691 checkInPool(); 2692 if (this.txState == TX_INACTIVE) { 2693 this.xid = xid; 2694 try { 2695 beginImp(); 2696 this.txState = TX_STARTED; 2697 } catch (Exception e) { 2698 throw new XAException ( 2699 "Could not begin a transaction : " + e.getMessage()); 2700 } 2701 } else if (this.txState == TX_STARTED 2702 || this.txState == TX_PREPARED 2703 || this.txState == TX_SUSPENDED) { 2704 return; 2707 } else { 2708 throw new XAException ( 2709 "Could not begin a transaction in state = " + txState); 2710 } 2711 } 2712 2713 2714 2728 2729 public int prepare(Xid xid) throws XAException { 2730 if (Debug.DEBUG) { 2731 Debug.OUT.println( 2732 "***** JdoGeniePersistenceManagerImp.prepare *****"); 2733 } 2734 checkInPool(); 2735 if (checkId(xid)) { 2736 if (txState == TX_STARTED) { 2737 try { 2738 internalCommit(true); 2739 this.txState = TX_PREPARED; 2740 return XA_OK; 2741 } catch (Exception ex) { 2742 ex.printStackTrace(); 2743 throw new XAException ( 2744 "Could not prepare commit : " + ex.getMessage()); 2745 } 2746 } else if (this.txState == TX_PREPARED || this.txState == TX_SUSPENDED) { 2747 return XA_OK; 2748 } else { 2749 throw new XAException ( 2750 "Wrong state to commit phase one on : state = " + this.txState); 2751 } 2752 } 2753 return XA_OK; 2754 } 2755 2756 2757 2771 2772 public void commit(Xid xid, boolean onePhase) throws XAException { 2773 if (Debug.DEBUG) { 2774 Debug.OUT.println("***** JdoGeniePersistenceManagerImp.commit ***** onePhase: " + onePhase 2775 + " for \n" + this); 2776 } 2777 checkInPool(); 2778 if (checkId(xid)) { 2779 try { 2780 if (onePhase && txState == TX_STARTED) { 2781 internalCommit(false); 2782 } else if (this.txState == TX_PREPARED) { 2783 phaseCommit2(); 2784 } else if (this.txState == TX_INACTIVE) { 2785 return; 2786 } else { 2787 throw new XAException ("Unable to commit unexpected state: state = " + 2788 txState + " for xid = " + xid); 2789 } 2790 2791 this.txState = TX_INACTIVE; 2792 this.xid = null; 2793 } catch (XAException ex) { 2794 ex.printStackTrace(); 2795 throw ex; 2796 } catch (Exception ex) { 2797 ex.printStackTrace(); 2798 throw new XAException ("Could not commit : " + ex.getMessage()); 2799 } 2800 } 2801 } 2802 2803 2804 private void checkInPool() { 2805 if (inPool) { 2806 throw BindingSupportImpl.getInstance().fatal( 2807 "The pm is in the pool"); 2808 } 2809 } 2810 2811 public boolean isInTx() { 2812 return this.txState != TX_INACTIVE; 2813 } 2814 2815 2822 2823 public void rollback(Xid xid) throws XAException { 2824 if (Debug.DEBUG) { 2825 Debug.OUT.println( 2826 "***** JdoGeniePersistenceManagerImp.rollback *****"); 2827 } 2828 checkInPool(); 2829 if (checkId(xid)) { 2830 try { 2831 if (this.txState != TX_INACTIVE) { 2832 rollbackImp(); 2833 this.txState = TX_INACTIVE; 2834 } 2835 this.xid = null; 2836 } catch (Exception e) { 2837 throw new XAException ("Could not rollback: " + e.getMessage()); 2838 } 2839 } 2840 } 2841 2842 2843 2864 2865 public void end(Xid xid, int flags) throws XAException { 2866 if (Debug.DEBUG) { 2867 Debug.OUT.println("***** JdoGeniePersistenceManagerImp.end ***** flag: " + getFlagString( 2868 flags) 2869 + " for \n" + this); 2870 System.out.println("xid = " + xid); 2871 } 2872 checkInPool(); 2873 if (checkId(xid)) { 2874 switch (flags) { 2875 case TMSUCCESS: 2876 this.txState = TX_STARTED; 2877 break; 2878 case TMFAIL: 2879 this.txState = TX_FAIL; 2880 break; 2881 case TMSUSPEND: 2882 this.txState = TX_SUSPENDED; 2883 break; 2884 default: 2885 throw new XAException ( 2886 "Unable to end transaction = " + xid + " unhandled flag = " + flags); 2887 } 2888 } 2889 } 2890 2891 2892 private String getFlagString(int flag) { 2893 switch (flag) { 2894 case 8388608: 2895 return "TMENDRSCAN"; 2896 case 536870912: 2897 return "TMFAIL"; 2898 case 2097152: 2899 return "TMJOIN"; 2900 case 0: 2901 return "TMNOFLAGS"; 2902 case 1073741824: 2903 return "TMONEPHASE"; 2904 case 134217728: 2905 return "TMRESUME"; 2906 case 16777216: 2907 return "TMSTARTRSCAN"; 2908 case 67108864: 2909 return "TMSUCCESS"; 2910 case 33554432: 2911 return "TMSUSPEND"; 2912 default: 2913 return "UNKNOWN"; 2914 } 2915 } 2916 2917 2925 2926 public void forget(Xid xid) throws XAException { 2927 if (Debug.DEBUG) { 2928 Debug.OUT.println( 2929 "***** JdoGeniePersistenceManagerImp.forget *****"); 2930 } 2931 checkInPool(); 2932 if (this.xid.equals(xid)) { 2933 this.txState = TX_STARTED; 2934 } 2935 } 2936 2937 2938 2945 2946 public int getTransactionTimeout() throws XAException { 2947 if (Debug.DEBUG) { 2948 Debug.OUT.println( 2949 "***** JdoGeniePersistenceManagerImp.getTransactionTimeout *****"); 2950 } 2951 checkInPool(); 2952 return txTimeout; 2953 } 2954 2955 2956 2971 2972 public boolean isSameRM(XAResource xaResource) throws XAException { 2973 if (Debug.DEBUG) { 2974 Debug.OUT.println( 2975 "***** JdoGeniePersistenceManagerImp.isSameRM *****"); 2976 Debug.OUT.println("***** isSame: this = " + this); 2977 Debug.OUT.println("***** isSame: other = " + this); 2978 } 2979 return xaResource == this; 2980 } 2981 2982 2983 3006 3007 public Xid [] recover(int flag) throws XAException { 3008 if (Debug.DEBUG) { 3009 Debug.OUT.println("***** JdoGeniePersistenceManagerImp.recover ***** flag = " + getFlagString( 3010 flag)); 3011 } 3012 checkInPool(); 3013 Xid [] xids = txState == TX_PREPARED ? new Xid []{xid} : null; 3014 return xids; 3015 } 3016 3017 3018 3034 3035 public boolean setTransactionTimeout(int seconds) throws XAException { 3036 if (Debug.DEBUG) { 3037 Debug.OUT.println( 3038 "***** JdoGeniePersistenceManagerImp.setTransactionTimeout *****"); 3039 } 3040 checkInPool(); 3041 if (seconds < -1) { 3042 return false; 3043 } else { 3044 this.txTimeout = seconds; 3045 } 3046 return true; 3047 } 3048 3049 3050 3051 3053 3054 3055 public void afterCompletion(int status) { 3056 if (Debug.DEBUG) { 3057 Debug.OUT.println( 3058 "***** JdoGeniePersistenceManagerImp.afterCompletion *****"); 3059 } 3060 proxy.resetPM(); 3061 pmf.pmClosedNotification(this, false, false); 3062 } 3063 3064 3065 3066 public void beforeCompletion() { 3067 if (Debug.DEBUG) { 3068 Debug.OUT.println( 3069 "***** JdoGeniePersistenceManagerImp.beforeCompletion *****"); 3070 } 3071 } 3072 3073 3074 3084 public void setDatastoreTxLocking(int mode) { 3085 int policy; 3086 switch (mode) { 3087 case VersantPersistenceManager.LOCKING_NONE: 3088 policy = StorageManager.LOCK_POLICY_NONE; 3089 break; 3090 case VersantPersistenceManager.LOCKING_FIRST: 3091 policy = StorageManager.LOCK_POLICY_FIRST; 3092 break; 3093 case VersantPersistenceManager.LOCKING_ALL: 3094 policy = StorageManager.LOCK_POLICY_ALL; 3095 break; 3096 default: 3097 throw BindingSupportImpl.getInstance().invalidOperation( 3098 "Invalid datastoreTxLocking mode: " + mode); 3099 } 3100 sm.setLockingPolicy(policy); 3101 } 3102 3103 3106 public int getDatastoreTxLocking() { 3107 switch (sm.getLockingPolicy()) { 3108 case StorageManager.LOCK_POLICY_NONE: 3109 return VersantPersistenceManager.LOCKING_NONE; 3110 case StorageManager.LOCK_POLICY_FIRST: 3111 return VersantPersistenceManager.LOCKING_FIRST; 3112 case StorageManager.LOCK_POLICY_ALL: 3113 return VersantPersistenceManager.LOCKING_ALL; 3114 } 3115 return VersantPersistenceManager.LOCKING_NONE; 3116 } 3117 3118 public void logEvent(int level, String description, int ms) { 3119 sm.logEvent(level, description, ms); 3120 } 3121 3122 3130 public Object getObjectByIdFromCache(Object oid) { 3131 if (oid == null) { 3132 throw BindingSupportImpl.getInstance().invalidOperation( 3133 "The oid is null"); 3134 } 3135 try { 3136 PCStateMan stateMan = cache.getByOID(extractOID(oid), 3137 true); 3138 return stateMan == null ? null : stateMan.pc; 3139 } catch (Exception e) { 3140 handleException(e); 3141 return null; 3142 } 3143 } 3144 3145 3151 public boolean isHollow(Object pc) { 3152 PCStateMan pcStateObject = pmPreCheck(pc); 3153 return pcStateObject != null && pcStateObject.isHollow(); 3154 } 3155 3156 3161 public boolean hasIdentity(Object pc) { 3162 return !pmPreCheck(pc).oid.isNew(); 3163 } 3164 3165 3170 public void processLocalCacheReferenceQueue() { 3171 cache.processReferenceQueue(); 3172 } 3173 3174 3190 public Collection versantDetachCopy(Collection pcs, String fetchGroup) { 3191 if (pcs instanceof QueryResult) { 3192 pcs.size(); 3195 } 3196 3197 if (fetchGroup == null) fetchGroup = FetchGroup.DFG_NAME; 3198 for (Iterator pcIt = pcs.iterator(); pcIt.hasNext();) { 3199 Object o = pcIt.next(); 3200 if (o == null || !(o instanceof VersantDetachable)) continue; 3201 VersantDetachable pc = (VersantDetachable)o; 3202 requestedPCState = null; 3203 pc.jdoGetPersistenceManager(); 3204 if (requestedPCState == null) { 3205 makePersistent(pc); 3206 } 3207 } 3208 flushRetainState(); 3209 DetachStateContainer dsc = new DetachStateContainer(this); 3211 for (Iterator pcIt = pcs.iterator(); pcIt.hasNext();) { 3212 PersistenceCapable pc = (PersistenceCapable)pcIt.next(); 3213 if (pc == null) continue; 3214 PCStateMan sm = getInternalSM(pc); 3215 ClassMetaData cmd = sm.state.getClassMetaData(modelMetaData); 3216 FetchGroup fg = cmd.getFetchGroup(fetchGroup); 3217 if (fg == null) { 3218 fg = cmd.fetchGroups[0]; 3219 } 3220 dsc.add(sm.oid, sm.state, fg); 3221 } 3222 3223 for (; dsc.hasNextFetchGroup();) { 3225 State state = dsc.getNextFetchGroupState(); 3226 FetchGroup fg = dsc.getNextFetchGroup(); 3227 OID oid = dsc.getNextFetchGroupOID(); 3228 3229 if (!oid.isNew() && (state == null || !state.containsFetchGroup(fg))) { 3234 StatesReturned con = getStateForDetach(oid, fg.index); 3235 addToDetachStateContainer(con, dsc); 3236 state = con.get(oid); 3237 addToCache(con); 3238 dsc.add(oid, state, fg); 3239 } 3240 ClassMetaData cmd = state.getClassMetaData(modelMetaData); 3241 state.addFetchGroupStatesToDCS(fg, dsc, this, oid, cmd); 3242 } 3243 dsc.createPcClasses(modelMetaData); 3244 ArrayList copyList = new ArrayList(pcs.size()); 3245 for (Iterator pcIt = pcs.iterator(); pcIt.hasNext();) { 3246 Object o = pcIt.next(); 3247 if (o == null || !(o instanceof VersantDetachable)) { 3248 copyList.add(null); 3249 continue; 3250 } 3251 VersantDetachable pc = (VersantDetachable)o; 3252 requestedPCState = null; 3253 pc.jdoGetPersistenceManager(); 3254 if (requestedPCState == null) { 3255 copyList.add(pc); 3256 } 3257 copyList.add(dsc.getDetachCopy(pc)); 3258 } 3259 return copyList; 3260 } 3261 3262 public List versantCollectReachable(Collection roots, String fetchGroup) { 3263 if (fetchGroup == null) { 3264 fetchGroup = FetchGroup.REF_NAME; 3265 } 3266 checkActiveTx(); 3267 3268 Set result = new HashSet(); 3269 List todo = new ArrayList(roots); 3270 3271 while (todo.size() > 0) { 3273 Object o = todo.remove(0); 3274 String currentFetchGroup = fetchGroup; 3275 if (o instanceof Object []) { Object [] tmp = (Object [])o; 3277 currentFetchGroup = (String )tmp[1]; 3278 o = tmp[0]; 3279 } 3280 3281 if (o == null || !(o instanceof PersistenceCapable)) continue; 3282 PersistenceCapable pc = (PersistenceCapable)o; 3283 3284 requestedPCState = null; 3285 pc.jdoGetPersistenceManager(); 3286 if (requestedPCState == null) { 3287 makePersistent(pc); 3288 } 3289 PCStateMan sm = pmPreCheck(pc); 3290 if (!result.contains(sm) && !sm.isDeleted(pc)) { 3291 if (currentFetchGroup != null) 3292 { 3294 sm.collectReachable(currentFetchGroup, todo); 3295 } 3296 result.add(sm); 3297 } 3298 } 3299 List pcresult = new ArrayList(); 3300 for (Iterator it = result.iterator(); it.hasNext();) { 3301 pcresult.add(((PCStateMan)it.next()).pc); 3302 } 3303 return pcresult; 3304 } 3305 3306 3310 public StatesReturned getStateForDetach(OID oid, int fgi) { 3311 return getStateJdoConnection(oid, null, fgi, 3312 oid.getAvailableClassId(), false, 3313 -1, -1); 3314 } 3315 3316 public State getStateFromLocalCacheById(Object oid) { 3317 if (oid == null) { 3318 throw BindingSupportImpl.getInstance().invalidOperation( 3319 "The supplied oid is null"); 3320 } 3321 try { 3322 OID nOID = extractOID(oid); 3323 PCStateMan stateMan = cache.getByOID(nOID, true); 3324 if (stateMan == null) { 3325 return null; 3326 } 3327 return stateMan.state; 3328 } catch (Exception e) { 3329 handleException(e); 3330 return null; 3331 } 3332 } 3333 3334 3344 public int getObjectsById(Object [] oids, int length, Object [] data, 3345 int stateFieldNo, int classMetaDataIndex) { 3346 if (oids == null || oids.length <= 0) return 0; 3347 OIDArray oidArray = new OIDArray(); 3348 for (int i = 0; i < length; i++) { 3349 Object o = oids[i]; 3350 if (!(o instanceof OID)) { 3355 data[i] = o; 3356 continue; 3357 } 3358 OID oid = (OID)o; 3359 PCStateMan pcStateMan = cache.getByOID(oid, true); 3360 if (pcStateMan != null) { 3361 data[i] = pcStateMan.pc; 3362 } else { 3363 oidArray.add(oid); 3364 data[i] = null; 3365 } 3366 } 3367 if (!oidArray.isEmpty()) { 3368 FieldMetaData triggerField; 3369 if (classMetaDataIndex >= 0) { ClassMetaData navCmd = modelMetaData.classes[classMetaDataIndex]; 3371 triggerField = navCmd.stateFields[stateFieldNo]; 3372 } else { 3373 triggerField = null; 3374 } 3375 StatesReturned container = sm.fetch(this, oidArray, triggerField); 3376 PCStateMan[] nogc = addToCacheAndManage(container); 3379 for (int i = 0; i < length; i++) { 3380 if (data[i] == null) { 3381 data[i] = cache.getByOID((OID)oids[i], true).pc; 3382 } 3383 } 3384 if (nogc == null) { 3385 } 3388 } 3389 return length; 3390 } 3391 3392 3398 public Query versantNewNamedQuery(Class cls, String queryName) { 3399 try { 3400 ClassMetaData cmd = modelMetaData.getClassMetaData(cls); 3401 if (cmd == null) { 3402 throw BindingSupportImpl.getInstance().invalidOperation("Class " + cls.getName() + 3403 " is not persistent"); 3404 } 3405 QueryDetails qp = cmd.getNamedQuery(queryName); 3406 if (qp == null) { 3407 throw BindingSupportImpl.getInstance().invalidOperation("No query called '" + queryName + 3408 "' has been defined in the meta data for Class " + 3409 cmd.qname); 3410 } 3411 return new VersantQueryImp(proxy, qp); 3412 } catch (Exception e) { 3413 handleException(e); 3414 return null; 3415 } 3416 } 3417 3418 3422 public boolean isCheckModelConsistencyOnCommit() { 3423 return checkModelConsistencyOnCommit; 3424 } 3425 3426 public void setCheckModelConsistencyOnCommit(boolean on) { 3427 this.checkModelConsistencyOnCommit = on; 3428 } 3429 3430 3443 public Collection versantAttachCopy(Collection detached, 3444 boolean makeTransactional) { 3445 return versantAttachCopy(detached, makeTransactional, false); 3446 } 3447 3448 3466 public Collection versantAttachCopy(Collection detached, 3467 boolean makeTransactional, boolean shallow) { 3468 AttachStateContainer asc = new AttachStateContainer(this); 3469 for (Iterator pcIt = detached.iterator(); pcIt.hasNext();) { 3470 VersantDetachable detachable = (VersantDetachable)pcIt.next(); 3471 if (detachable == null) continue; 3472 asc.addVersantDetachable(detachable); 3473 } 3474 if (!shallow) { 3475 AttachNavStateManager ansm = new AttachNavStateManager(asc); 3476 for (int c = 0; c < asc.getDetachedSize(); c++) { 3477 VersantDetachable detachable = asc.getVersantDetachable(c); 3478 if (detachable.jdoGetPersistenceManager() != null) continue; 3479 detachable.jdoReplaceStateManager(ansm); 3480 ClassMetaData cmd = modelMetaData.getClassMetaData( 3481 detachable.getClass()); 3482 for (; cmd != null; cmd = cmd.pcSuperMetaData) { 3483 for (int i = 0; i < cmd.fields.length; i++) { 3484 FieldMetaData field = cmd.fields[i]; 3485 if (field.fake) continue; 3486 switch (field.category) { 3487 case FieldMetaData.CATEGORY_REF: 3488 case FieldMetaData.CATEGORY_POLYREF: 3489 case FieldMetaData.CATEGORY_COLLECTION: 3490 case FieldMetaData.CATEGORY_MAP: 3491 case FieldMetaData.CATEGORY_ARRAY: 3492 detachable.jdoProvideField( 3493 field.managedFieldNo); 3494 } 3495 } 3496 } 3497 } 3498 } 3499 3500 AttachCopyStateManager acsm = new AttachCopyStateManager(this); 3501 for (int c = 0; c < asc.getDetachedSize(); c++) { 3502 OID oid = asc.getOID(c); 3503 VersantDetachable detachable = asc.getVersantDetachable(c); 3504 if (detachable.jdoGetPersistenceManager() != null) continue; 3505 boolean notNew = !oid.isNew(); 3506 if (notNew && !detachable.versantIsDirty()) continue; 3507 detachable.jdoReplaceStateManager(acsm); 3508 PCStateMan sm = getInternalSM(oid); 3509 if (notNew && sm.state.isHollow()) { 3510 StatesReturned con = getStateForDetach(oid, 0); 3511 addToCache(con); 3512 } 3513 acsm.setState(sm.state); 3514 if (notNew) { 3515 Object dVersion = detachable.versantGetVersion(); 3516 Object aVersion = sm.getOptimisticLockingValue(); 3517 if (aVersion == null && sm.getClassMetaData().optimisticLockingField != null) { 3518 throw BindingSupportImpl.getInstance().internal("Optimistic locking value not available for " 3519 + sm.getClassMetaData().qname); 3520 } 3521 if (aVersion != null && !aVersion.equals(dVersion)) { 3522 throw BindingSupportImpl.getInstance().concurrentUpdate( 3523 "The object (" + oid.toStringImp() + 3524 ") has been updated since its been detached " + 3525 "(current='" + aVersion + "', detached='" + dVersion + "')", oid); 3526 } 3527 } 3528 ClassMetaData cmd = modelMetaData.getClassMetaData( 3529 detachable.getClass()); 3530 for (; cmd != null; cmd = cmd.pcSuperMetaData) { 3531 for (int i = 0; i < cmd.fields.length; i++) { 3532 FieldMetaData fmd = cmd.fields[i]; 3533 if (fmd.fake) continue; 3534 if (notNew && !detachable.versantIsDirty( 3535 fmd.getManagedFieldNo())) { 3536 continue; 3537 } 3538 switch (fmd.category) { 3539 case FieldMetaData.CATEGORY_SIMPLE: 3540 case FieldMetaData.CATEGORY_POLYREF: 3541 case FieldMetaData.CATEGORY_EXTERNALIZED: 3542 case FieldMetaData.CATEGORY_REF: 3543 case FieldMetaData.CATEGORY_COLLECTION: 3544 case FieldMetaData.CATEGORY_ARRAY: 3545 case FieldMetaData.CATEGORY_MAP: 3546 acsm.setFieldMetaData(fmd); 3547 int managedFieldNo = fmd.managedFieldNo; 3548 detachable.jdoProvideField(managedFieldNo); 3549 if (notNew) { 3550 sm.makeDirty(detachable, managedFieldNo); 3551 } 3552 } 3553 } 3554 } 3555 if (notNew) { 3556 sm.resetLoadedFields(); 3557 sm.setLoadRequired(); 3558 } 3559 } 3560 Collection deleted = asc.getDeleted(); 3561 for (Iterator it = deleted.iterator(); it.hasNext();) { 3562 try { 3563 Object o = getObjectById(it.next(), true); 3564 deletePersistent(o); 3565 } catch (JDOObjectNotFoundException e) { 3566 } 3568 } 3569 ArrayList attached = new ArrayList(); 3570 for (Iterator pcIt = detached.iterator(); pcIt.hasNext();) { 3571 VersantDetachable pc = (VersantDetachable)pcIt.next(); 3572 if (pc == null) { 3573 attached.add(pc); 3574 continue; 3575 } 3576 Object newPC = getObjectById(getOID(pc), false); 3577 attached.add(newPC); 3578 } 3579 return attached; 3580 } 3581 3582 OID getOID(VersantDetachable detachable) { 3583 Object oid = detachable.versantGetOID(); 3584 if (oid == null) { 3585 PersistenceManager pm = detachable.jdoGetPersistenceManager(); 3586 if (pm != null) { 3587 if (pm instanceof PMProxy) { 3588 pm = ((PMProxy)pm).getRealPM(); 3589 } 3590 if (pm instanceof VersantPersistenceManagerImp) { 3591 OID internalOID = ((VersantPersistenceManagerImp)pm).getInternalOID( 3592 detachable); 3593 detachable.versantSetOID(getExternalOID(internalOID)); 3594 return internalOID; 3595 } else { 3596 throw BindingSupportImpl.getInstance().runtime( 3597 "Can't attach a managed " + 3598 "instance that is not managed by Versant Open Access"); 3599 } 3600 } 3601 PCStateMan sm = getStateObject(); 3602 NewObjectOID nOID = assignOID(detachable); 3603 sm.init(detachable, nOID, this); 3604 cache.add(sm); 3605 detachable.versantSetOID(nOID); 3606 return sm.oid.getAvailableOID(); 3607 } else { 3608 return extractOID(oid); 3609 } 3610 } 3611 3612 3613 final PCStateMan getStateManager(Object o) { 3614 return cache.getByOID( 3615 extractOID(((PersistenceCapable)o).jdoGetObjectId()), false); 3616 } 3617 3618 final PCStateMan getStateManagerById(Object oid) { 3619 return cache.getByOID(extractOID(oid), false); 3620 } 3621 3622 public void setRetainConnectionInOptTx(boolean on) { 3623 sm.setConnectionPolicy(on 3624 ? StorageManager.CON_POLICY_PIN_FOR_TX 3625 : StorageManager.CON_POLICY_RELEASE); 3626 } 3627 3628 3631 private void resetEpcFields() { 3632 epcAll = false; 3633 epcObjects = null; 3634 epcObjectCount = 0; 3635 epcClasses = null; 3636 epcClassCount = 0; 3637 epcClassPresent = null; 3638 } 3639 3640 public void evictFromL2CacheAfterCommit(Object o) { 3641 checkActiveTx(); 3642 evictFromL2CacheAfterCommitImp(o); 3643 } 3644 3645 3649 public void evictFromL2CacheAfterCommitImp(Object o) { 3650 if (epcAll) return; 3651 if (o instanceof PersistenceCapable) { 3652 PCStateMan sm = pmPreCheck((PersistenceCapable)o); 3653 if (sm == null || sm.isNew(null)) { 3654 return; } 3656 o = sm.oid; 3657 } 3658 if (epcObjects == null) { 3659 epcObjects = new Object [4]; 3660 } else if (epcObjectCount == epcObjects.length) { 3661 Object [] a = new Object [epcObjects.length * 3 / 2 + 1]; 3662 System.arraycopy(epcObjects, 0, a, 0, epcObjects.length); 3663 epcObjects = a; 3664 } 3665 epcObjects[epcObjectCount++] = o; 3666 } 3667 3668 public void evictAllFromL2CacheAfterCommit(final Object [] data) { 3669 checkActiveTx(); 3670 int n = data.length; 3671 if (n == 0 || epcAll) return; 3672 ensureCapacityEpcObjects(n); 3673 for (int i = 0; i < n; i++) { 3674 Object o = data[i]; 3675 if (o instanceof PersistenceCapable) { 3676 PCStateMan sm = pmPreCheck((PersistenceCapable)o); 3677 if (sm == null || sm.isNew(null)) { 3678 continue; } 3680 o = sm.oid; 3681 } 3682 epcObjects[epcObjectCount++] = o; 3683 } 3684 } 3685 3686 public void evictAllFromL2CacheAfterCommit(final Collection data) { 3687 checkActiveTx(); 3688 int n = data.size(); 3689 if (n == 0 || epcAll) return; 3690 ensureCapacityEpcObjects(n); 3691 for (Iterator i = data.iterator(); i.hasNext();) { 3692 Object o = i.next(); 3693 if (o instanceof PersistenceCapable) { 3694 PCStateMan sm = pmPreCheck((PersistenceCapable)o); 3695 if (sm == null || sm.isNew(null)) { 3696 continue; } 3698 o = sm.oid; 3699 } 3700 epcObjects[epcObjectCount++] = o; 3701 } 3702 } 3703 3704 private void ensureCapacityEpcObjects(int delta) { 3705 if (epcObjects == null) { 3706 epcObjects = new Object [delta + 4]; 3707 } else if (epcObjectCount + delta >= epcObjects.length) { 3708 Object [] a = new Object [epcObjectCount + delta]; 3709 System.arraycopy(epcObjects, 0, a, 0, epcObjects.length); 3710 epcObjects = a; 3711 } 3712 } 3713 3714 public void evictAllFromL2CacheAfterCommit(final Class cls, 3715 final boolean includeSubclasses) { 3716 checkActiveTx(); 3717 ClassMetaData cmd = modelMetaData.getClassMetaData(cls); 3718 if (cmd == null) { 3719 BindingSupportImpl.getInstance().runtime( 3720 "Class is not persistent: " + cls); 3721 } 3722 evictAllFromL2CacheAfterCommitImp(cmd, includeSubclasses); 3723 } 3724 3725 private void evictAllFromL2CacheAfterCommitImp(ClassMetaData cmd, 3726 final boolean includeSubclasses) { 3727 if (epcAll) return; 3728 if (epcClasses == null) { 3729 epcClasses = new int[4]; 3730 epcClassPresent = new boolean[modelMetaData.classes.length]; 3731 } 3732 int ci = cmd.index; 3733 if (!epcClassPresent[ci]) { 3734 if (epcClassCount == epcClasses.length) { 3735 int[] a = new int[epcClasses.length * 2]; 3736 System.arraycopy(epcClasses, 0, a, 0, epcClasses.length); 3737 epcClasses = a; 3738 } 3739 epcClasses[epcClassCount++] = ci; 3740 epcClassPresent[ci] = true; 3741 } 3742 if (includeSubclasses) { 3743 ClassMetaData[] subs = cmd.pcSubclasses; 3744 if (subs != null) { 3745 for (int i = subs.length - 1; i >= 0; i--) { 3746 evictAllFromL2CacheAfterCommitImp(subs[i], 3747 includeSubclasses); 3748 } 3749 } 3750 } 3751 } 3752 3753 public void evictAllFromL2CacheAfterCommit() { 3754 checkActiveTx(); 3755 epcAll = true; 3756 epcObjects = null; 3757 epcObjectCount = 0; 3758 epcClasses = null; 3759 epcClassCount = 0; 3760 epcClassPresent = null; 3761 } 3762 3763 public Object getOptimisticLockingValue(Object o) { 3764 return getInternalSM((PersistenceCapable)o).getOptimisticLockingValue(); 3765 } 3766 3767 public void setListeners(LifecycleListenerManager listeners) { 3768 this.listeners = listeners; 3769 } 3770 3771 public void addLifecycleListener(LifecycleListener listener, 3772 Class [] classes) { 3773 if (classes != null) { 3774 BindingSupportImpl.getInstance().runtime("Support for non-null " + 3775 "classes parameter has not been implemented"); 3776 } 3777 if (listeners == null) { 3778 listeners = new LifecycleListenerManager(listener); 3779 } else { 3780 listeners = listeners.add(listener); 3781 } 3782 } 3783 3784 public void removeLifecycleListener(LifecycleListener listener) { 3785 if (listeners == null) { 3786 return; 3787 } 3788 listeners = listeners.remove(listener); 3789 } 3790 3791 3794 public void fireDelete(ClassMetaData cmd, Object o) { 3795 if (listeners != null) { 3796 listeners.fireDelete(o); 3797 } 3798 } 3799 3800 3803 public StorageManager getStorageManager() { 3804 return sm; 3805 } 3806 3807 public LocalPMCache getCache() { 3808 return cache; 3809 } 3810 3811 public void setCache(LocalPMCache cache) { 3812 this.cache = cache; 3813 } 3814 3815 public MemQueryCompiler getMemQueryCompiler() { 3816 return memQueryCompiler; 3817 } 3818 3819 public Reference getActiveReference() { 3820 return activeReference; 3821 } 3822 3823 public void setActiveReference(Reference activeReference) { 3824 this.activeReference = activeReference; 3825 } 3826 3827 3832 private void updateOIDsAndDoAutoS(StatesReturned container) { 3833 for (Iterator i = container.iterator(); i.hasNext(); ) { 3834 EntrySet.Entry e = (EntrySet.Entry)i.next(); 3835 OID oid = (OID)e.getKey(); 3836 State state = (State)e.getValue(); 3837 3838 PCStateMan sm; 3845 if (oid instanceof NewObjectOID) { 3846 sm = cache.getByNewObjectOID((NewObjectOID)oid); 3847 if (sm == null) { 3848 sm = cache.getByOID(oid, false); 3849 if (sm == null) continue; 3850 } else { 3851 ((NewObjectOID)sm.oid).setRealOid(oid.getRealOID()); 3852 } 3853 } else { 3854 sm = cache.getByOID(oid, false); 3855 if (sm == null) continue; 3856 } 3857 3858 if (state != null) { 3863 sm.updateAutoFields(state); 3864 } 3865 } 3866 } 3867 3868 3871 public void addToCache(StatesReturned container) { 3872 for (Iterator i = container.iterator(); i.hasNext(); ) { 3873 EntrySet.Entry e = (EntrySet.Entry)i.next(); 3874 cache.addStateOnly((OID)e.getKey(), (State)e.getValue()); 3875 } 3876 } 3877 3878 3883 private PCStateMan[] addToCacheAndManage(StatesReturned container) { 3884 PCStateMan[] smArray = new PCStateMan[1]; 3885 PCStateMan[] ans = new PCStateMan[container.size()]; 3886 int c = 0; 3887 for (Iterator i = container.iterator(); i.hasNext(); ) { 3888 EntrySet.Entry e = (EntrySet.Entry)i.next(); 3889 ans[c++] = cache.add((OID)e.getKey(), (State)e.getValue(), smArray); 3890 } 3891 return ans; 3892 } 3893 3894 3899 private PCStateMan addAndReturnFirstDirect(StatesReturned container) { 3900 OID firstDirectOID = container.getDirectOID(); 3901 if (firstDirectOID == null) { 3902 return null; 3903 } 3904 PCStateMan[] sm = new PCStateMan[1]; 3905 cache.add(firstDirectOID, container.get(firstDirectOID), sm); 3906 for (Iterator i = container.iterator(); i.hasNext(); ) { 3907 EntrySet.Entry e = (EntrySet.Entry)i.next(); 3908 cache.addStateOnly((OID)e.getKey(), (State)e.getValue()); 3909 } 3910 return sm[0]; 3911 } 3912 3913 3916 private void addToDetachStateContainer(StatesReturned container, 3917 DetachStateContainer dcs) { 3918 for (Iterator i = container.iterator(); i.hasNext(); ) { 3919 EntrySet.Entry e = (EntrySet.Entry)i.next(); 3920 dcs.add((OID)e.getKey(), (State)e.getValue()); 3921 } 3922 } 3923 3924 3928 public boolean isStateRequired(OID oid, FetchGroup fetchGroup) { 3929 State state = cache.getStateByOID(oid); 3930 if (state != null) { 3931 if (fetchGroup == null) { 3932 fetchGroup = state.getClassMetaData().fetchGroups[0]; 3933 } 3934 return !state.containsFetchGroup(fetchGroup); 3935 } 3936 return true; 3937 } 3938 3939} 3940 3941 | Popular Tags |