KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > sun > jts > CosTransactions > CoordinatorTerm


1 /*
2  * The contents of this file are subject to the terms
3  * of the Common Development and Distribution License
4  * (the License). You may not use this file except in
5  * compliance with the License.
6  *
7  * You can obtain a copy of the license at
8  * https://glassfish.dev.java.net/public/CDDLv1.0.html or
9  * glassfish/bootstrap/legal/CDDLv1.0.txt.
10  * See the License for the specific language governing
11  * permissions and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL
14  * Header Notice in each file and include the License file
15  * at glassfish/bootstrap/legal/CDDLv1.0.txt.
16  * If applicable, add the following below the CDDL Header,
17  * with the fields enclosed by brackets [] replaced by
18  * you own identifying information:
19  * "Portions Copyrighted [year] [name of copyright owner]"
20  *
21  * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
22  */

23
24 /*
25  * Copyright 2004-2005 Sun Microsystems, Inc. All rights reserved.
26  * Use is subject to license terms.
27  */

28 //----------------------------------------------------------------------------
29
//
30
// Module: CoordinatorTerm.java
31
//
32
// Description: Client Coordinator termination.
33
//
34
// Product: com.sun.jts.CosTransactions
35
//
36
// Author: Simon Holdsworth
37
//
38
// Date: March, 1997
39
//
40
// Copyright (c): 1995-1997 IBM Corp.
41
//
42
// The source code for this program is not published or otherwise divested
43
// of its trade secrets, irrespective of what has been deposited with the
44
// U.S. Copyright Office.
45
//
46
// This software contains confidential and proprietary information of
47
// IBM Corp.
48
//----------------------------------------------------------------------------
49

50 package com.sun.jts.CosTransactions;
51
52 // Import required classes.
53

54 import org.omg.CORBA.*;
55 import org.omg.CosTransactions.*;
56 import com.sun.jts.trace.*;
57 import java.util.logging.Logger JavaDoc;
58 import java.util.logging.Level JavaDoc;
59 import com.sun.logging.LogDomains;
60 import com.sun.jts.utils.LogFormatter;
61
62 /**The CoordinatorTerm interface provides operations that allow an
63  * Terminator to direct completion of a transaction without any dependency
64  * on the Coordinator interface.
65  *
66  * @version 0.01
67  *
68  * @author Simon Holdsworth, IBM Corporation
69  *
70  * @see
71 */

72 //----------------------------------------------------------------------------
73
// CHANGE HISTORY
74
//
75
// Version By Change Description
76
// 0.01 SAJH Initial implementation.
77
//------------------------------------------------------------------------------
78

79 class CoordinatorTerm implements CompletionHandler {
80     private CoordinatorImpl coordinator = null;
81     private boolean subtransaction = false;
82     private boolean aborted = false;
83     private boolean heuristicDamage = false;
84     private boolean completed = false;
85     private boolean completing = false;
86
87     /*
88         Logger to log transaction messages
89     */

90     
91     static Logger JavaDoc _logger = LogDomains.getLogger(LogDomains.TRANSACTION_LOGGER);
92
93     /**Default CoordinatorTerm constructor.
94      *
95      * @param
96      *
97      * @return
98      *
99      * @see
100      */

101     CoordinatorTerm() {
102     }
103
104     /**Normal constructor.
105      * <p>
106      * Sets up the CoordinatorTerm with the Coordinator reference so that the
107      * CoordinatorTerm can find the Coordinator to pass on the two-phase commit
108      * messages.
109      * <p>
110      * A flag is passed to indicate whether the CoordinatorTerm
111      * represents a subtransaction.
112      *
113      * @param coord The Coordinator for the transaction.
114      * @param subtran The subtransaction indicator.
115      *
116      * @return
117      *
118      * @see
119      */

120     CoordinatorTerm( CoordinatorImpl coord,
121                      boolean subtran ) {
122
123         // Set up the instance variables from the values passed.
124

125         coordinator = coord;
126         subtransaction = subtran;
127
128         // Inform the Coordinator that this is the object that normally terminates
129
// the transaction.
130

131         if( coordinator != null )
132             coordinator.setTerminator(this);
133
134     }
135
136     /**Cleans up the objects state.
137      *
138      * @param
139      *
140      * @return
141      *
142      * @see
143      */

144     public void finalize() {
145
146         // If the transaction has not been completed as far as the CoordinatorTerm
147
// object is concerned, then roll back the Coordinator.
148

149         if( !completed ) {
150             completing = true;
151             try {
152                 coordinator.rollback(true);
153             } catch( Throwable JavaDoc exc ) {
154             }
155             if( !subtransaction )
156                 ((TopCoordinator)coordinator).afterCompletion(Status.StatusRolledBack);
157         }
158
159         coordinator = null;
160
161     }
162
163     /**Informs the object that the transaction is to be committed.
164      * <p>
165      * Uses a private interface to pass the Terminator's commit request on to the
166      * Coordinator.
167      * <p>
168      * This operation does not check for outstanding requests, that is done by
169      * the Current operations (when the client is using direct interaction we
170      * cannot provide checked behavior).
171      * <p>
172      * Before telling the Coordinator to commit, it is informed that the
173      * transaction is about to complete, and afterwards it is told that the
174      * transaction has completed, with an indication of commit or rollback.
175      *
176      * @param promptReturn Indicates whether to return promptly.
177      *
178      * @return
179      *
180      * @exception TRANSACTION_ROLLEDBACK The transaction could not be committed and
181      * has been rolled back.
182      * @exception HeuristicHazard Heuristic action may have been taken by a
183      * participant in the transaction.
184      * @exception HeuristicMixed Heuristic action has been taken by a participant
185      * in the transaction so part of the transaction has
186      * been rolled back.
187      * @exception SystemException An error occurred calling another object.
188      * @exception LogicErrorException An internal logic error occurred.
189      *
190      * @see
191      */

192     void commit( boolean promptReturn )
193         throws HeuristicMixed, HeuristicHazard, TRANSACTION_ROLLEDBACK,
194         SystemException, LogicErrorException {
195
196         // BUGFIX(Ram J) (12/16/2000) This was previously set to true, which the
197
// caused commit_one_phase exceptions not to be reported.
198
boolean commit_one_phase_worked_ok = false;
199
200         // If the transaction that this object represents has already been rolled
201
// back, raise the TRANSACTION_ROLLEDBACK exception and return.
202
// If the transaction completed with heuristic damage, report that.
203

204         if( aborted ) {
205             throw new TRANSACTION_ROLLEDBACK(0,CompletionStatus.COMPLETED_NO);
206         }
207
208         // If there is no Coordinator reference, raise an exception.
209

210         if( coordinator == null ) {
211             String JavaDoc msg = LogFormatter.getLocalizedMessage(_logger,
212                                       "jts.no_coordinator_available");
213             LogicErrorException exc =
214                 new LogicErrorException(msg);
215             throw exc;
216         }
217
218         // Remember that it is us that have initiated the completion so that we can
219
// ignore the aborted operation if it happens subsequently.
220

221         completing = true;
222
223         // Determine the current Control object and Coordinator. Determine whether
224
// the current transaction is the same as that being committed.
225

226         ControlImpl current = CurrentTransaction.getCurrent();
227         ControlImpl establishedControl = null;
228         Coordinator currentCoord = null;
229         boolean sameCoordinator = false;
230
231         if( current != null )
232             try {
233                 if (Configuration.isLocalFactory()) {
234                   currentCoord = current.get_localCoordinator();
235                 } else {
236                   currentCoord = current.get_coordinator();
237                 }
238
239                 sameCoordinator = coordinator.is_same_transaction(currentCoord);
240             } catch( Unavailable exc ) {}
241
242         // We must ensure that there is a current transaction at this point if it is a
243
// top-level transaction because the Synchronization objects expect to have
244
// transaction context.
245
// If this CoordinatorTerm was created by a Factory, then this commit will
246
// not have context because the Terminator is not a transactional object.
247

248         if( !subtransaction ) {
249             try {
250                 if( current == null ||
251                     !sameCoordinator ) {
252                     establishedControl = new ControlImpl(null,coordinator,
253                                                          new GlobalTID(coordinator.getGlobalTID()),
254                                                          new Long JavaDoc(coordinator.getLocalTID()));
255                     CurrentTransaction.setCurrent(establishedControl,true);
256                 }
257             } catch( Throwable JavaDoc exc ) {
258             }
259
260             // Tell the Coordinator that the transaction is about to complete.
261

262             try {
263                 ((TopCoordinator)coordinator).beforeCompletion();
264             }
265
266             // If the Coordinator raised an exception, return it to the caller.
267

268             catch( SystemException exc ) {
269                 completing = false;
270                 throw exc;
271             }
272
273             // If a temporary context was established, end it now.
274

275             finally {
276                 if( establishedControl != null ) {
277                     CurrentTransaction.endCurrent(true);
278                     establishedControl.finalize();
279                 }
280             }
281         }
282
283         // End the association of the current Control object with the current thread
284
// if it is the same transaction as the one being committed.
285
// This is done here rather than in Current because the before completion
286
// method must be invoked while the transaction is still active.
287

288         Status status = Status.StatusCommitted;
289         if( sameCoordinator )
290             CurrentTransaction.endCurrent(true);
291
292
293         // Now, process the actual 2PC
294

295         Throwable JavaDoc heuristicExc = null;
296
297         // GDH Now see if we can legally call commit one phase
298
// the commitOnePhase method will return false if this is
299
// not possible.
300

301         try {
302             commit_one_phase_worked_ok = coordinator.commitOnePhase();
303         } catch( Throwable JavaDoc exc ) {
304
305             if( exc instanceof HeuristicHazard ||
306                 exc instanceof HeuristicMixed ) {
307                 heuristicExc = exc;
308             } else if( exc instanceof TRANSACTION_ROLLEDBACK ) {
309                 status = Status.StatusRolledBack;
310             } else if( exc instanceof INVALID_TRANSACTION ) {
311                 // Why have we driven before completion before now?
312
throw (INVALID_TRANSACTION)exc;
313             } if (exc instanceof INTERNAL) {
314                 // ADDED(Ram J) percolate any system exception
315
// back to the caller.
316
throw (INTERNAL) exc;
317             }else {
318             }
319         }
320
321         if( commit_one_phase_worked_ok ) {
322             // Then we have done the commit already above
323
// Set the status for the after completion call
324
// even though currently the parm is not used
325
// inside the call - it get's the state from transtate
326
// the status variable here is a local flag.
327
status = Status.StatusCommitted; // GDH COPDEF1 Added this for neatness
328

329         } else if (status != Status.StatusRolledBack) { // Added (Ram J) (12/06/2000)
330
// commit two phase now
331

332             // Get the prepare vote from the root Coordinator.
333
Vote prepareResult = Vote.VoteRollback;
334
335             try {
336                 prepareResult = coordinator.prepare();
337             } catch( HeuristicHazard exc ) {
338                 heuristicExc = exc;
339             } catch( HeuristicMixed exc ) {
340                 heuristicExc = exc;
341             } catch( INVALID_TRANSACTION exc ) {
342                 throw exc;
343             } catch( Throwable JavaDoc exc ) {
344             }
345
346             if( subtransaction ) {
347                 // Depending on the prepare result, commit or abort the transaction.
348

349                 if( prepareResult == Vote.VoteCommit )
350                     try {
351             
352             if(_logger.isLoggable(Level.FINE))
353             {
354                 _logger.logp(Level.FINE,"CoordinatorTerm","commit()",
355                         "Before invoking coordinator.commit() :"+"GTID is: "+
356                         ((TopCoordinator)coordinator).superInfo.globalTID.toString());
357                 
358             }
359                         coordinator.commit();
360                     } catch( NotPrepared exc ) {
361                         prepareResult = Vote.VoteRollback;
362                     }
363
364                 if( prepareResult == Vote.VoteRollback ) {
365                     if(_logger.isLoggable(Level.FINE))
366                     {
367                          _logger.logp(Level.FINE,"CoordinatorTerm","commit()",
368                                 "Before invoking coordinator.rollback :"+
369                                 "GTID is : "+
370                                 ((TopCoordinator)coordinator).superInfo.globalTID.toString());
371                     }
372                     coordinator.rollback(true);
373                     status = Status.StatusRolledBack;
374                 }
375             }
376
377             // End of dealing with top-level transactions.
378

379             else {
380
381                 // Depending on the prepare result, commit or abort the transaction.
382

383                 //$ DO SOMETHING ABOUT PROMPT RETURN */
384

385                 try {
386                     if( prepareResult == Vote.VoteCommit )
387                         try {
388                             coordinator.commit();
389                         } catch( NotPrepared exc ) {
390                             prepareResult = Vote.VoteRollback;
391                         }
392
393                     if( prepareResult == Vote.VoteRollback && heuristicExc == null ) {
394                         status = Status.StatusRolledBack; // GDH COPDEF1 Swapped these two lines
395
coordinator.rollback(true); // (not stricly necessary for problem fix)
396
}
397                 } catch( Throwable JavaDoc exc ) {
398                     if (exc instanceof HeuristicHazard ||
399                         exc instanceof HeuristicMixed) {
400                         heuristicExc = exc;
401                     }
402
403                     // ADDED(Ram J) percolate any system exception
404
// back to the caller.
405
if (exc instanceof INTERNAL) {
406                         throw (INTERNAL) exc;
407                     }
408                 }
409
410
411             } // end else was top level txn
412

413         } // end else used two phase else
414

415         // Tell the Coordinator that the transaction has completed (top-level
416
// transactions only).
417
if( !subtransaction ) {
418             ((TopCoordinator)coordinator).afterCompletion(status);
419         }
420
421         // Inform the Control object that the transaction has completed.
422

423         completed = true;
424         if( current != null && sameCoordinator )
425             current.setTranState(status);
426
427         // If a heuristic was thrown, throw the exception.
428

429         if( heuristicExc != null ) {
430             if( heuristicExc instanceof HeuristicMixed )
431                 throw (HeuristicMixed)heuristicExc;
432             else
433                 throw (HeuristicHazard)heuristicExc;
434         }
435
436         // If the transaction was rolled back, raise an exception.
437

438         if( status == Status.StatusRolledBack ) {
439             TRANSACTION_ROLLEDBACK exc = new TRANSACTION_ROLLEDBACK(0,CompletionStatus.COMPLETED_YES);
440             throw exc;
441         }
442
443     }
444
445     /**Informs the object that the transaction is to be rolled back.
446      * <p>
447      * Uses a private interface to pass the Terminator's rollback request on to
448      * the Coordinator.
449      *
450      * @param
451      *
452      * @return
453      *
454      * @exception HeuristicHazard Heuristic action may have been taken by a
455      * participant in the transaction.
456      * @exception HeuristicMixed Heuristic action has been taken by a participant
457      * in the transaction so part of the transaction has
458      * been committed.
459      * @exception SystemException An error occurred calling another object.
460      * @exception LogicErrorException An internal logic error occurred.
461      *
462      * @see
463      */

464     void rollback()
465         throws HeuristicMixed, HeuristicHazard, SystemException,
466         LogicErrorException {
467
468         // If the transaction that this object represents has already been rolled
469
// back, raise an exception. Note that we cannot raise a heuristic exception
470
// here as it is not in the OMG interface.
471

472         if( aborted ) {
473             TRANSACTION_ROLLEDBACK exc = new TRANSACTION_ROLLEDBACK(0,CompletionStatus.COMPLETED_NO);
474             throw exc;
475         }
476
477         // If there is no Coordinator reference, raise an exception.
478

479         if( coordinator == null ) {
480              String JavaDoc msg = LogFormatter.getLocalizedMessage(_logger,
481                                         "jts.no_coordinator_available");
482                                        
483             LogicErrorException exc =
484                 new LogicErrorException(msg);
485             throw exc;
486         }
487
488         // Remember that it is us that have initiated the completion so that we can
489
// ignore the aborted operation if it happens subsequently.
490

491         Coordinator currentCoord = null;
492         ControlImpl current = null;
493
494         completing = true;
495
496         // End the association of the current Control object with the current thread
497
// if it is the same transaction as the one being committed.
498

499         try {
500             current = CurrentTransaction.getCurrent();
501         } catch( Throwable JavaDoc exc ) {}
502
503         if( current != null )
504             try {
505                 if (Configuration.isLocalFactory()) {
506                   currentCoord = current.get_localCoordinator();
507                 } else {
508                   currentCoord = current.get_coordinator();
509                 }
510
511                 if( coordinator.is_same_transaction(currentCoord) )
512                     CurrentTransaction.endCurrent(true);
513             }
514
515         // If an exception was raised, it must be because the transaction that the
516
// current Control object represents was rolled back. In that case, always
517
// end the current thread association.
518

519         catch( Throwable JavaDoc exc ) {
520             CurrentTransaction.endCurrent(true);
521         }
522
523         // Rollback the transaction and inform synchronisation objects.
524

525         Throwable JavaDoc heuristicExc = null;
526         try {
527             coordinator.rollback(true);
528         }
529         catch (Throwable JavaDoc exc) {
530             if (exc instanceof HeuristicHazard ||
531                 exc instanceof HeuristicMixed) {
532                    heuristicExc = exc;
533             }
534
535             // ADDED (Ram J) percolate any system exception to the caller
536
if (exc instanceof INTERNAL) {
537                 throw (INTERNAL) exc;
538             }
539         } finally {
540             if( !subtransaction )
541                 ((TopCoordinator)coordinator).afterCompletion(Status.StatusRolledBack);
542         }
543
544         // Inform the Control object that the transaction has completed.
545

546         completed = true;
547         if( current != null )
548             current.setTranState(Status.StatusRolledBack);
549
550         // If a heuristic was thrown, throw the exception.
551

552         if( heuristicExc != null ) {
553             if( heuristicExc instanceof HeuristicMixed )
554                 throw (HeuristicMixed)heuristicExc;
555             else
556                 throw (HeuristicHazard)heuristicExc;
557         }
558
559         // Otherwise return normally.
560

561     }
562
563     /**Informs the CoordinatorTerm object that the transaction it represents
564      * has completed.
565      * <p>
566      * Flags indicate whether the transaction aborted, and
567      * whether there was heuristic damage.
568      * <p>
569      * This operation is invoked by a Coordinator when it is rolled back,
570      * potentially by a caller other than the CoordinatorTerm itself. In the
571      * event that it is some other caller, the CoordinatorTerm object performs the
572      * after rollback synchronisation, and remembers the fact that it has aborted
573      * for later.
574      *
575      * @param aborted Indicates whether the transaction locally aborted.
576      * @param heuristicDamage Indicates local heuristic damage.
577      *
578      * @return
579      *
580      * @see
581      */

582
583     public void setCompleted( boolean aborted,
584                               boolean heuristicDamage ) {
585
586         // If the transaction that this object represents has already been rolled
587
// back, or is being rolled back by this object, just return.
588

589         if( !completing ) {
590
591             // If there is no Coordinator reference, we cannot do anything. Note that
592
// CompletionHandler does not permit an exception through this method so we
593
// cannot throw one.
594

595             // Set the flags and distribute after completion operations for the
596
// transaction.
597

598             completed = true;
599             this.aborted = aborted;
600             this.heuristicDamage = heuristicDamage;
601
602             if( coordinator == null ) {
603             } else if( !subtransaction )
604                 ((TopCoordinator)coordinator).afterCompletion(Status.StatusRolledBack);
605         }
606
607     }
608
609     /**Dumps the state of the object.
610      *
611      * @param
612      *
613      * @return
614      *
615      * @see
616      */

617     void dump() {
618     }
619
620 }
621
622
Popular Tags