1 /***
2 *
3 */
4 package org.xvsm.internal;
5
6 import java.net.URI;
7 import java.util.ArrayList;
8 import java.util.List;
9 import java.util.Map;
10 import java.util.StringTokenizer;
11 import java.util.UUID;
12 import java.util.concurrent.ConcurrentHashMap;
13
14 import org.xvsm.core.aspect.AspectContext;
15 import org.xvsm.core.aspect.GlobalIPoint;
16 import org.xvsm.core.aspect.IAspect;
17 import org.xvsm.core.aspect.IPoint;
18 import org.xvsm.core.aspect.LocalIPoint;
19 import org.xvsm.internal.exceptions.AspectNotOkException;
20 import org.xvsm.internal.exceptions.AspectRescheduleException;
21 import org.xvsm.internal.exceptions.AspectSkipException;
22
23 /***
24 * @author Christian Schreiber, Michael Proestler
25 *
26 */
27 public class AspectManager {
28
29 /***
30 * Map contains all registered aspects.
31 */
32 private Map<IPoint, List<IAspect>> aspects = new ConcurrentHashMap<IPoint, List<IAspect>>();
33
34 private Map<String, IAspect> idaspectMapping = new ConcurrentHashMap<String, IAspect>();
35
36 /***
37 * Default constructor.
38 */
39 public AspectManager() {
40 for (LocalIPoint p : LocalIPoint.values()) {
41 aspects.put(p, new ArrayList<IAspect>());
42 }
43 for (GlobalIPoint p : GlobalIPoint.values()) {
44 aspects.put(p, new ArrayList<IAspect>());
45 }
46 }
47
48 /***
49 * Adds a new Aspect.
50 *
51 * @param p
52 * the ipoint for the new aspect.
53 * @param aspect
54 * the new aspect.
55 * @return the identifier of the aspect
56 */
57 public String addAspect(IPoint p, IAspect aspect) {
58 if (aspect.getId() == null) {
59 aspect.setId(UUID.randomUUID().toString());
60 }
61 this.aspects.get(p).add(aspect);
62 this.idaspectMapping.put(aspect.getId(), aspect);
63 return aspect.getId();
64 }
65
66 /***
67 * Removes an aspect.
68 *
69 * @param p
70 * the ipoint where the aspect shall be removed.
71 * @param uri
72 * the uri of the aspect which shall be removed.
73 */
74 public void removeAspect(IPoint p, URI uri) {
75 StringTokenizer st = new StringTokenizer(uri.getPath(), "/");
76 st.nextToken();
77 String id = st.nextToken();
78 this.aspects.get(p).remove(this.idaspectMapping.get(id));
79 for (IPoint pp : this.aspects.keySet()) {
80
81 if (this.aspects.containsKey(pp)) {
82 return;
83 }
84
85 this.idaspectMapping.remove(id);
86 System.gc();
87 }
88 }
89
90 /***
91 * Returns all registered aspects for the IPoint.
92 *
93 * @param p
94 * the IPoint.
95 * @return a list of aspects.
96 */
97 private List<IAspect> getAspects(IPoint p) {
98 return this.aspects.get(p);
99 }
100
101 /***
102 * Runs all aspects which have been registered for the IPoint defined in c.
103 *
104 * @param c
105 * the {@link AspectContext}.
106 * @throws AspectNotOkException
107 * thrown if the operation has to be rescheduled.
108 * @throws AspectRescheduleException
109 * thrown if the operation has to be undone and the transaction
110 * has to be rolled back.
111 * @throws AspectSkipException
112 * thrown if the operation shall be skiped.
113 */
114 public void execute(AspectContext c) throws AspectNotOkException,
115 AspectRescheduleException, AspectSkipException {
116
117 List<IAspect> allAspects = new ArrayList<IAspect>();
118 IPoint p = c.getLocalIPoint();
119 if (p != null) {
120 allAspects.addAll(this.getAspects(p));
121 }
122 p = c.getGlobalIPoint();
123 if (p != null) {
124 allAspects.addAll(this.getAspects(p));
125 }
126 for (IAspect a : allAspects) {
127
128 a.execute(c);
129 }
130
131 }
132 }