KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > tc > objectserver > persistence > impl > TransactionStoreImpl


1 /*
2  * All content copyright (c) 2003-2006 Terracotta, Inc., except as may otherwise be noted in a separate copyright notice. All rights reserved.
3  */

4 package com.tc.objectserver.persistence.impl;
5
6 import com.tc.net.protocol.tcm.ChannelID;
7 import com.tc.object.gtx.GlobalTransactionID;
8 import com.tc.object.tx.ServerTransactionID;
9 import com.tc.objectserver.gtx.GlobalTransactionDescriptor;
10 import com.tc.objectserver.persistence.api.PersistenceTransaction;
11 import com.tc.objectserver.persistence.api.TransactionPersistor;
12 import com.tc.objectserver.persistence.api.TransactionStore;
13 import com.tc.util.sequence.Sequence;
14
15 import java.util.Collection JavaDoc;
16 import java.util.Collections JavaDoc;
17 import java.util.HashMap JavaDoc;
18 import java.util.HashSet JavaDoc;
19 import java.util.Iterator JavaDoc;
20 import java.util.Map JavaDoc;
21 import java.util.SortedSet JavaDoc;
22 import java.util.TreeSet JavaDoc;
23
24 public class TransactionStoreImpl implements TransactionStore {
25
26   private final Map JavaDoc serverTransactionIDMap = Collections.synchronizedMap(new HashMap JavaDoc());
27   private final Map JavaDoc globalTransactionIDMap = Collections.synchronizedMap(new HashMap JavaDoc());
28
29   private final SortedSet JavaDoc ids = Collections
30                                                                 .synchronizedSortedSet(new TreeSet JavaDoc(
31                                                                                                    GlobalTransactionID.COMPARATOR));
32   private final TransactionPersistor persistor;
33   private final Sequence globalIDSequence;
34
35   public TransactionStoreImpl(TransactionPersistor persistor, Sequence globalIDSequence) {
36     this.persistor = persistor;
37     this.globalIDSequence = globalIDSequence;
38     // Ok, this is relying on the fact that GlobalTransactionIDs are never given out negative,
39
// except for NULL_ID which is -1
40
// We don't want to hit the DB (globalIDsequence) until all the stages are started.
41
int negativeID = -2;
42     for (Iterator JavaDoc i = this.persistor.loadAllGlobalTransactionDescriptors().iterator(); i.hasNext();) {
43       GlobalTransactionDescriptor gtx = (GlobalTransactionDescriptor) i.next();
44       ServerTransactionID stxID = gtx.getServerTransactionID();
45       basicAdd(stxID, gtx);
46       // this will be reassigned later when the clients resend the transaction
47
addGlobalTransactionID(stxID, new GlobalTransactionID(negativeID--));
48     }
49   }
50
51   private GlobalTransactionID addGlobalTransactionID(ServerTransactionID serverTransactionID) {
52     return addGlobalTransactionID(serverTransactionID, new GlobalTransactionID(globalIDSequence.next()));
53   }
54
55   private GlobalTransactionID addGlobalTransactionID(ServerTransactionID serverTransactionID, GlobalTransactionID gid) {
56     Object JavaDoc previousID = globalTransactionIDMap.put(serverTransactionID, gid);
57     if (previousID != null) {
58       // GlobalTransactionID's will be remapped on server restarts
59
ids.remove(previousID);
60     }
61     ids.add(gid);
62     return gid;
63   }
64
65   public void commitTransactionDescriptor(PersistenceTransaction transaction, GlobalTransactionDescriptor gtx) {
66     persistor.saveGlobalTransactionDescriptor(transaction, gtx);
67   }
68
69   public GlobalTransactionDescriptor getTransactionDescriptor(ServerTransactionID serverTransactionID) {
70     return (GlobalTransactionDescriptor) this.serverTransactionIDMap.get(serverTransactionID);
71   }
72
73   public GlobalTransactionDescriptor createTransactionDescriptor(ServerTransactionID serverTransactionID) {
74     GlobalTransactionDescriptor rv = new GlobalTransactionDescriptor(serverTransactionID);
75     basicAdd(serverTransactionID, rv);
76     return rv;
77   }
78
79   private void basicAdd(ServerTransactionID serverTransactionID, GlobalTransactionDescriptor gtx) {
80     this.serverTransactionIDMap.put(serverTransactionID, gtx);
81   }
82
83   public GlobalTransactionID getLeastGlobalTransactionID() {
84     synchronized (ids) {
85       return (GlobalTransactionID) ((ids.isEmpty()) ? GlobalTransactionID.NULL_ID : ids.first());
86     }
87   }
88
89   public void removeAllByServerTransactionID(PersistenceTransaction tx, Collection JavaDoc stxIDs) {
90     Collection JavaDoc toDelete = new HashSet JavaDoc();
91     synchronized (ids) {
92       for (Iterator JavaDoc i = stxIDs.iterator(); i.hasNext();) {
93         ServerTransactionID stxID = (ServerTransactionID) i.next();
94         GlobalTransactionDescriptor desc = (GlobalTransactionDescriptor) this.serverTransactionIDMap.remove(stxID);
95         GlobalTransactionID gid = (GlobalTransactionID) this.globalTransactionIDMap.remove(stxID);
96         if (gid != null) {
97           ids.remove(gid);
98         }
99         if (desc != null) {
100           toDelete.add(stxID);
101         }
102       }
103     }
104     persistor.deleteAllByServerTransactionID(tx, toDelete);
105   }
106
107   public GlobalTransactionID createGlobalTransactionID(ServerTransactionID stxnID) {
108     return addGlobalTransactionID(stxnID);
109   }
110
111   public void shutdownClient(PersistenceTransaction tx, ChannelID client) {
112     Collection JavaDoc stxIDs = new HashSet JavaDoc();
113     synchronized (serverTransactionIDMap) {
114       for (Iterator JavaDoc iter = serverTransactionIDMap.keySet().iterator(); iter.hasNext();) {
115         ServerTransactionID stxID = (ServerTransactionID) iter.next();
116         if (stxID.getChannelID().equals(client)) {
117           stxIDs.add(stxID);
118         }
119       }
120     }
121     removeAllByServerTransactionID(tx, stxIDs);
122   }
123 }
Popular Tags