1 | package com.hammurapi.eventbus.snapshot.io; |
2 | |
3 | import java.lang.reflect.Method; |
4 | |
5 | import com.hammurapi.convert.AbstractReflectiveAtomicConvertersBundle; |
6 | import com.hammurapi.convert.ConverterMethod; |
7 | import com.hammurapi.convert.ConvertingService; |
8 | import com.hammurapi.eventbus.EventHandler; |
9 | import com.hammurapi.eventbus.ReflectiveEventHandler; |
10 | import com.hammurapi.eventbus.snapshot.Event; |
11 | import com.hammurapi.eventbus.snapshot.Handler; |
12 | import com.hammurapi.eventbus.snapshot.Predicate; |
13 | import com.hammurapi.eventbus.snapshot.SnapshotElement; |
14 | import com.hammurapi.eventbus.snapshot.SnapshotFactory; |
15 | |
16 | public class SnapshotConvertersBundle extends AbstractReflectiveAtomicConvertersBundle { |
17 | |
18 | private static final String ELLIPSIS = "..."; |
19 | private static final int MAX_NAME_LENGTH = 50; |
20 | |
21 | /** |
22 | * Basic converter sets last part of class name as name, and |
23 | * toString() as details. |
24 | * @param obj |
25 | * @return |
26 | */ |
27 | @ConverterMethod |
28 | public Event convertToSnapshotElement(Object obj) { |
29 | Event se = SnapshotFactory.eINSTANCE.createEvent(); |
30 | populate(obj, se); |
31 | return se; |
32 | } |
33 | |
34 | private void populate(Object src, SnapshotElement se) { |
35 | if (src==null) { |
36 | se.setName("(null)"); |
37 | } else { |
38 | Class<?> srcClass = src.getClass(); |
39 | String cName = shortClassName(srcClass); |
40 | if (cName.length()<MAX_NAME_LENGTH) { |
41 | String val = cName+" ("+src.toString(); |
42 | if (val.length()>MAX_NAME_LENGTH) { |
43 | val = val.substring(0, MAX_NAME_LENGTH)+"..."; |
44 | } |
45 | se.setName(val+")"); |
46 | } else { |
47 | se.setName(cName); |
48 | } |
49 | se.setDetails(src.toString()); |
50 | } |
51 | } |
52 | |
53 | private String shortClassName(Class<?> srcClass) { |
54 | String cName = srcClass.getName(); |
55 | int idx = cName.lastIndexOf('.'); |
56 | if (idx!=-1) { |
57 | cName=cName.substring(idx+1); |
58 | } |
59 | return cName; |
60 | } |
61 | |
62 | @ConverterMethod |
63 | public Handler convertToHandler(EventHandler<?, ?, ?, ?, ?> eventHandler) { |
64 | Handler ret = SnapshotFactory.eINSTANCE.createHandler(); |
65 | populate(eventHandler, ret); |
66 | return ret; |
67 | } |
68 | |
69 | @ConverterMethod |
70 | public Handler convertToHandler(ReflectiveEventHandler<?, ?, ?, ?> reflectiveHandler) { |
71 | Handler ret = SnapshotFactory.eINSTANCE.createHandler(); |
72 | StringBuilder sb = new StringBuilder("Reflective handler["); |
73 | Method m = reflectiveHandler.getMethod(); |
74 | sb.append(shortClassName(m.getDeclaringClass())+"."+m.getName()); |
75 | if (sb.length()<MAX_NAME_LENGTH) { |
76 | sb.append("("); |
77 | Class<?>[] pt = m.getParameterTypes(); |
78 | for (int i=0; i<pt.length; ++i) { |
79 | if (i>0) { |
80 | sb.append(","); |
81 | } |
82 | sb.append(shortClassName(pt[i])); |
83 | } |
84 | if (sb.length()>MAX_NAME_LENGTH) { |
85 | sb.delete(MAX_NAME_LENGTH, sb.length()); |
86 | sb.append(ELLIPSIS); |
87 | } |
88 | sb.append(")"); |
89 | } else { |
90 | sb.append(ELLIPSIS); |
91 | } |
92 | sb.append("]"); |
93 | ret.setName(sb.toString()); |
94 | ret.setDetails(reflectiveHandler.toString()); |
95 | return ret; |
96 | } |
97 | |
98 | @ConverterMethod |
99 | public com.hammurapi.eventbus.snapshot.Predicate convertToPredicate(com.hammurapi.extract.Predicate<?, ?> predicate) { |
100 | return (Predicate) convertToExtractor(predicate); |
101 | } |
102 | |
103 | @ConverterMethod |
104 | public com.hammurapi.eventbus.snapshot.Extractor convertToExtractor(com.hammurapi.extract.Extractor<?, ?, ?> extractor) { |
105 | com.hammurapi.eventbus.snapshot.Extractor ret; |
106 | if (extractor instanceof com.hammurapi.extract.Predicate) { |
107 | ret = SnapshotFactory.eINSTANCE.createPredicate(); |
108 | } else { |
109 | ret = SnapshotFactory.eINSTANCE.createExtractor(); |
110 | |
111 | } |
112 | setCostAndParameterIndices(extractor, ret); |
113 | |
114 | if (extractor instanceof com.hammurapi.extract.BinaryExtractor) { |
115 | ret.setName(shortClassName(extractor.getClass())); |
116 | |
117 | @SuppressWarnings("rawtypes") |
118 | com.hammurapi.extract.BinaryExtractor<?,?,?> bExtractor = (com.hammurapi.extract.BinaryExtractor) extractor; |
119 | com.hammurapi.eventbus.snapshot.Extractor left = ConvertingService.convert(bExtractor.getLeftExtractor(), com.hammurapi.eventbus.snapshot.Extractor.class); |
120 | left.setRole("left extractor"); |
121 | ret.getParts().add(left); |
122 | |
123 | com.hammurapi.eventbus.snapshot.Extractor right = ConvertingService.convert(bExtractor.getRightExtractor(), com.hammurapi.eventbus.snapshot.Extractor.class); |
124 | right.setRole("right extractor"); |
125 | ret.getParts().add(right); |
126 | } else { |
127 | populate(extractor, ret); |
128 | } |
129 | |
130 | if (ret.getDetails()==null || ret.getDetails().trim().length()==0) { |
131 | ret.setDetails(String.valueOf(extractor)); |
132 | } |
133 | |
134 | return ret; |
135 | } |
136 | |
137 | @ConverterMethod |
138 | public com.hammurapi.eventbus.snapshot.Extractor convertToExtractor(com.hammurapi.extract.Constant<?, ?, ?> constant) { |
139 | com.hammurapi.eventbus.snapshot.Extractor ret = SnapshotFactory.eINSTANCE.createExtractor(); |
140 | StringBuilder sb = new StringBuilder("Constant "); |
141 | Object value = constant.getValue(); |
142 | if (value!=null) { |
143 | ret.setDetails("type="+value.getClass().getName()+",\nvalue="+value); |
144 | sb.append("(type="+value.getClass().getName()+", value="); |
145 | int maxVal=MAX_NAME_LENGTH-sb.length(); |
146 | if (maxVal<=0) { |
147 | sb.append("...)"); |
148 | } else if (maxVal>String.valueOf(value).length()) { |
149 | sb.append(value+")"); |
150 | } else { |
151 | sb.append(String.valueOf(value).substring(0, maxVal)+"...)"); |
152 | } |
153 | } |
154 | ret.setName(sb.toString()); |
155 | setCostAndParameterIndices(constant, ret); |
156 | return ret; |
157 | } |
158 | |
159 | private void setCostAndParameterIndices(com.hammurapi.extract.Extractor<?, ?, ?> predicate, com.hammurapi.eventbus.snapshot.Extractor ret) { |
160 | ret.setCost(predicate.getCost()); |
161 | for (Integer pi: predicate.parameterIndices()) { |
162 | ret.getParameterIndices().add(pi); |
163 | } |
164 | } |
165 | |
166 | @ConverterMethod |
167 | public com.hammurapi.eventbus.snapshot.Predicate convertToPredicate(com.hammurapi.extract.CompositePredicate<?, ?, ?, ?> predicate) { |
168 | com.hammurapi.eventbus.snapshot.Predicate ret = SnapshotFactory.eINSTANCE.createPredicate(); |
169 | ret.setName(shortClassName(predicate.getClass())); |
170 | setCostAndParameterIndices(predicate, ret); |
171 | for (com.hammurapi.extract.Predicate<?, ?> part: predicate.getParts()) { |
172 | Predicate rPart = ConvertingService.convert(part, com.hammurapi.eventbus.snapshot.Predicate.class); |
173 | rPart.setRole("part"); |
174 | ret.getParts().add(rPart); |
175 | } |
176 | return ret; |
177 | } |
178 | |
179 | @ConverterMethod |
180 | public com.hammurapi.eventbus.snapshot.Predicate convertToPredicate(com.hammurapi.extract.InstanceOfPredicate<?, ?> predicate) { |
181 | com.hammurapi.eventbus.snapshot.Predicate ret = SnapshotFactory.eINSTANCE.createPredicate(); |
182 | ret.setName(shortClassName(predicate.getClass())+"("+predicate.getInstanceType()+")"); |
183 | setCostAndParameterIndices(predicate, ret); |
184 | |
185 | com.hammurapi.eventbus.snapshot.Extractor extractor = ConvertingService.convert(predicate.getExtractor(), com.hammurapi.eventbus.snapshot.Extractor.class); |
186 | extractor.setRole("extractor"); |
187 | ret.getParts().add(extractor); |
188 | |
189 | return ret; |
190 | } |
191 | // TODO - composite and facade predicates. |
192 | |
193 | |
194 | |
195 | } |