41
41
import java .util .List ;
42
42
import java .util .Map ;
43
43
import java .util .UUID ;
44
+ import java .util .concurrent .Callable ;
44
45
import java .util .concurrent .ExecutorService ;
45
46
import java .util .concurrent .Executors ;
47
+ import java .util .concurrent .Future ;
46
48
47
49
public class EventBuilder {
48
50
private static final Logger logger = LoggerFactory .getLogger (EventBuilder .class );
@@ -55,6 +57,8 @@ public class EventBuilder {
55
57
@ VisibleForTesting
56
58
public final EventBatch .ClientEngine clientEngine ;
57
59
60
+ private Future <EventBatch > primedEvent = null ;
61
+
58
62
public EventBuilder () {
59
63
this (EventBatch .ClientEngine .JAVA_SDK , BuildVersionInfo .VERSION );
60
64
}
@@ -64,18 +68,33 @@ public EventBuilder(EventBatch.ClientEngine clientEngine, String clientVersion)
64
68
this .clientVersion = clientVersion ;
65
69
this .serializer = DefaultJsonSerializer .getInstance ();
66
70
67
- Runnable r = new Runnable () {
68
- public void run () {
69
- primeSerializer ();
71
+ Callable <EventBatch > callable = new Callable <EventBatch >() {
72
+ @ Override
73
+ public EventBatch call () throws Exception {
74
+ EventBatch eventBatch = null ;
75
+ try {
76
+ eventBatch = primeSerializer ();
77
+ } catch (Exception e ) {
78
+ logger .error ("Problem priming the JsonSerializer " , e );
79
+ }
80
+ finally {
81
+ return eventBatch ;
82
+ }
70
83
}
71
84
};
72
85
73
- ExecutorService executor = Executors .newCachedThreadPool ();
74
- executor .submit (r );
86
+ ExecutorService ex = Executors .newSingleThreadExecutor ();
87
+ primedEvent = ex .submit (callable );
88
+ ex .shutdown ();
75
89
76
90
}
77
91
78
- private void primeSerializer () {
92
+ /**
93
+ * primeSerializer primes the JsonSerializer and Json annotations from the EventBatch object and it's contained
94
+ * hierarchy. The introspection overhead is very high for the first time hit. This sets up all the serializer
95
+ * caching, taking the burden off of the first time hit in sending an event.
96
+ */
97
+ private EventBatch primeSerializer () {
79
98
Decision decision = new Decision ("" , "" ,
80
99
"" , false );
81
100
Event impressionEvent = new Event (System .currentTimeMillis (),UUID .randomUUID ().toString (), "" ,
@@ -86,15 +105,61 @@ private void primeSerializer() {
86
105
List <Visitor > visitors = Arrays .asList (visitor );
87
106
EventBatch eventBatch = new EventBatch (clientEngine .getClientEngineValue (), clientVersion , "" , visitors , true , "" , "" );
88
107
String payload = this .serializer .serialize (eventBatch );
89
- LogEvent retVal = new LogEvent (LogEvent .RequestMethod .POST , EVENT_ENDPOINT , Collections .<String , String >emptyMap (), payload );
90
- logger .debug (String .format ("Prime Serializer with event body %s" , retVal .getBody ()));
108
+ logger .debug ("JSON Serializer primed for payload {}" , payload );
109
+
110
+ return eventBatch ;
111
+ }
112
+
113
+ private LogEvent usePrimedEvent (@ Nonnull ProjectConfig projectConfig ,
114
+ @ Nonnull Experiment activatedExperiment ,
115
+ @ Nonnull Variation variation ,
116
+ @ Nonnull String userId ,
117
+ @ Nonnull Map <String , String > attributes ) {
118
+ try {
119
+ EventBatch eventBatch = primedEvent .get ();
120
+ primedEvent = null ;
121
+ Decision decision = new Decision (activatedExperiment .getLayerId (), activatedExperiment .getId (),
122
+ variation .getId (), false );
123
+
124
+ eventBatch .getVisitors ().get (0 ).getSnapshots ().get (0 ).setDecisions (Arrays .asList (decision ));
125
+ Event event = eventBatch .getVisitors ().get (0 ).getSnapshots ().get (0 ).getEvents ().get (0 );
126
+ event .setEntityId (activatedExperiment .getLayerId ());
127
+
128
+ Visitor visitor = eventBatch .getVisitors ().get (0 );
129
+ visitor .setVisitorId (userId );
130
+ visitor .setAttributes (buildAttributeList (projectConfig , attributes ));
131
+
132
+ eventBatch .setClientName (clientEngine .getClientEngineValue ());
133
+ eventBatch .setClientVersion (clientVersion );
134
+
135
+ eventBatch .setAccountId (projectConfig .getAccountId ());
136
+ eventBatch .setAnonymizeIp (projectConfig .getAnonymizeIP ());
137
+ eventBatch .setProjectId (projectConfig .getProjectId ());
138
+ eventBatch .setRevision (projectConfig .getRevision ());
139
+
140
+ String payload = this .serializer .serialize (eventBatch );
141
+ return new LogEvent (LogEvent .RequestMethod .POST , EVENT_ENDPOINT , Collections .<String , String >emptyMap (), payload );
142
+
143
+ }
144
+ catch (Exception e ) {
145
+ logger .error ("Problem getting lock " , e );
146
+ return null ;
147
+ }
91
148
}
92
149
93
150
public LogEvent createImpressionEvent (@ Nonnull ProjectConfig projectConfig ,
94
151
@ Nonnull Experiment activatedExperiment ,
95
152
@ Nonnull Variation variation ,
96
153
@ Nonnull String userId ,
97
154
@ Nonnull Map <String , String > attributes ) {
155
+ if (primedEvent != null ) {
156
+ logger .debug ("had to wait for prime" );
157
+ LogEvent logEvent = usePrimedEvent (projectConfig , activatedExperiment , variation ,
158
+ userId , attributes );
159
+ if (logEvent != null ) {
160
+ return logEvent ;
161
+ }
162
+ }
98
163
99
164
Decision decision = new Decision (activatedExperiment .getLayerId (), activatedExperiment .getId (),
100
165
variation .getId (), false );
0 commit comments