KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > versant > core > jdo > sco > MapDiffUtil


1
2 /*
3  * Copyright (c) 1998 - 2005 Versant Corporation
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v1.0
6  * which accompanies this distribution, and is available at
7  * http://www.eclipse.org/legal/epl-v10.html
8  *
9  * Contributors:
10  * Versant Corporation - initial API and implementation
11  */

12 package com.versant.core.jdo.sco;
13
14 import javax.jdo.spi.PersistenceCapable;
15 import java.util.*;
16
17 import com.versant.core.common.OID;
18 import com.versant.core.common.*;
19
20 /**
21  * This is a util used to extract a diff from to map's.
22  * <p/>
23  * This is not thread safe.
24  *
25  */

26 public final class MapDiffUtil {
27
28     private VersantFieldMetaData fmd;
29     private boolean keyIsPC;
30     private boolean valueIsPC;
31     private List toDelete = new ArrayList();
32     private Map toInsert = new java.util.HashMap JavaDoc();
33     private static final Map EMPTY_BEFORE_MAP = new HashMap();
34
35     public MapDiffUtil(VersantFieldMetaData fmd) {
36         this.fmd = fmd;
37         valueIsPC = fmd.isElementTypePC();
38         keyIsPC = fmd.isKeyTypePC();
39     }
40
41     private void addForDelete(Object JavaDoc key) {
42         toDelete.add(key);
43     }
44
45     private void addForInsert(Object JavaDoc key, Object JavaDoc value) {
46         toInsert.put(key, value);
47     }
48
49     private void addForUpdate(Object JavaDoc key, Object JavaDoc value) {
50         toDelete.add(key);
51         toInsert.put(key, value);
52     }
53
54     /**
55      * @param currentMap The dirty map
56      * @param beforeMap The map as before the changes. Null or Empty if first insert.
57      * @return
58      */

59     public MapDiff getDiff(Map currentMap, Map beforeMap,
60             PersistenceContext pm) {
61 //[BEGIN CHANGE: Pinaki]
62
// VDS Datastore requires the entire content of the map rather than the difference
63
// during flush. The corresponding flag is set in FieldMetaData during definition.
64

65         if (fmd.isIncludeAllDataInDiff()){
66             if (currentMap==null) return null;
67             MapDiff mapDiff = new MapDiff(fmd);
68             int mapSize = currentMap.size();
69             mapDiff.insertedKeys = new Object JavaDoc[mapSize];
70             mapDiff.insertedValues = new Object JavaDoc[mapSize];
71             int i = 0;
72             for (Iterator keys=currentMap.keySet().iterator(); keys.hasNext();i++){
73                 Object JavaDoc key = keys.next();
74                 Object JavaDoc value = currentMap.get(key);
75                     mapDiff.insertedKeys[i] = (keyIsPC) ?
76                             pm.getInternalOID((PersistenceCapable)key)
77                             : key;
78                     mapDiff.insertedValues[i] = (valueIsPC) ?
79                             pm.getInternalOID((PersistenceCapable)value)
80                             : value;
81             }
82             return mapDiff;
83         }
84 //[END CHANGE: Pinaki]
85
if (beforeMap == null) {
86             beforeMap = EMPTY_BEFORE_MAP;
87         }
88         doAdded(currentMap, beforeMap);
89         doRemoved(currentMap, beforeMap);
90         doUpdates(currentMap, beforeMap);
91
92         MapDiff mapDiff = new MapDiff(fmd);
93         doDeletes(mapDiff, pm);
94         if (!keyIsPC && !valueIsPC) {
95             mapDiff.insertedKeys = toInsert.keySet().toArray();
96             mapDiff.insertedValues = toInsert.values().toArray();
97         } else if (keyIsPC && valueIsPC) {
98             Object JavaDoc[] insKeys = new OID[toInsert.size()];
99             Object JavaDoc[] insVals = new OID[toInsert.size()];
100
101             int c = 0;
102             Set insertedSet = toInsert.entrySet();
103             for (Iterator iterator = insertedSet.iterator(); iterator.hasNext();) {
104                 Map.Entry entry = (Map.Entry)iterator.next();
105                 Object JavaDoc key = entry.getKey();
106                 key = pm.getInternalOID((PersistenceCapable)key);
107                 Object JavaDoc val = entry.getValue();
108                 val = pm.getInternalOID((PersistenceCapable)val);
109                 insKeys[c] = key;
110                 insVals[c++] = val;
111             }
112             mapDiff.insertedKeys = insKeys;
113             mapDiff.insertedValues = insVals;
114         } else if (keyIsPC) {
115             Object JavaDoc[] insKeys = new OID[toInsert.size()];
116             Object JavaDoc[] insVals = toInsert.values().toArray();
117
118             int c = 0;
119             Set insertedSet = toInsert.keySet();
120             for (Iterator iterator = insertedSet.iterator(); iterator.hasNext();) {
121                 Object JavaDoc key = iterator.next();
122                 key = pm.getInternalOID((PersistenceCapable)key);
123                 insKeys[c++] = key;
124             }
125             mapDiff.insertedKeys = insKeys;
126             mapDiff.insertedValues = insVals;
127
128         } else if (valueIsPC) {
129             Object JavaDoc[] insKeys = toInsert.keySet().toArray();
130             Object JavaDoc[] insVals = new OID[toInsert.size()];
131             int c = 0;
132             Set insertedSet = toInsert.keySet();
133             for (Iterator iterator = insertedSet.iterator(); iterator.hasNext();) {
134                 Object JavaDoc value = toInsert.get(iterator.next());
135                 value = pm.getInternalOID((PersistenceCapable)value);
136                 insVals[c++] = value;
137             }
138             mapDiff.insertedKeys = insKeys;
139             mapDiff.insertedValues = insVals;
140
141         }
142         toInsert.clear();
143         toDelete.clear();
144         return mapDiff;
145     }
146
147     private void doDeletes(MapDiff mapDiff, PersistenceContext pm) {
148         Object JavaDoc[] delArray;
149         if (keyIsPC) {
150             delArray = new OID[toDelete.size()];
151             for (int i = 0; i < toDelete.size(); i++) {
152                 delArray[i] = pm.getInternalOID((PersistenceCapable)toDelete.get(i));
153             }
154         } else {
155             delArray = toDelete.toArray();
156         }
157         mapDiff.deletedKeys = delArray;
158     }
159
160     private void doAdded(Map currentMap, Map beforeMap) {
161         Set newKeys = new java.util.HashSet JavaDoc(currentMap.keySet());
162         newKeys.removeAll(beforeMap.keySet());
163         for (Iterator iterator = newKeys.iterator(); iterator.hasNext();) {
164             Object JavaDoc key = iterator.next();
165             Object JavaDoc val = currentMap.get(key);
166             addForInsert(key, val);
167         }
168     }
169
170     private void doRemoved(Map currentMap, Map beforeMap) {
171         Set removedKeys = new java.util.HashSet JavaDoc(beforeMap.keySet());
172         removedKeys.removeAll(currentMap.keySet());
173         for (Iterator iterator = removedKeys.iterator(); iterator.hasNext();) {
174             addForDelete(iterator.next());
175         }
176     }
177
178     private void doUpdates(Map currentMap, Map beforeMap) {
179         Set keys = currentMap.keySet();
180         for (Iterator iterator = keys.iterator(); iterator.hasNext();) {
181             Object JavaDoc key = iterator.next();
182             if (beforeMap.containsKey(key)) {
183                 Object JavaDoc currentVal = currentMap.get(key);
184                 Object JavaDoc beforeVal = beforeMap.get(key);
185                 if (currentVal != null) {
186                     if (!currentVal.equals(beforeVal)) {
187                         addForUpdate(key, currentVal);
188                     }
189                 } else if (currentVal == null) {
190                     if (beforeVal != null) {
191                         addForUpdate(key, currentVal);
192                     }
193                 }
194             }
195         }
196     }
197 }
198
199
Popular Tags