65eff8d1d611885147242662fb78ad535820f09f
[lttng-ust-java-tests.git] /
1 /*
2 * Copyright (C) 2016, EfficiOS Inc., Alexandre Montplaisir <alexmonthy@efficios.com>
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License along
15 * with this program; if not, write to the Free Software Foundation, Inc.,
16 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
17 */
18
19 package org.lttng.ust.agent.integration.context;
20
21 import static org.junit.Assert.assertFalse;
22 import static org.junit.Assert.assertNotNull;
23 import static org.junit.Assert.assertTrue;
24 import static org.junit.Assert.fail;
25
26 import java.io.IOException;
27 import java.util.List;
28
29 import org.junit.After;
30 import org.junit.Before;
31 import org.junit.Test;
32 import org.junit.runner.RunWith;
33 import org.lttng.tools.ILttngSession;
34 import org.lttng.tools.ILttngSession.Domain;
35 import org.lttng.ust.agent.ILttngHandler;
36 import org.lttng.ust.agent.context.ContextInfoManager;
37 import org.lttng.ust.agent.utils.TestPrintRunner;
38
39 /**
40 * Base abstract class to implement all sorts of integration tests verifying the
41 * presence of enabled application contexts in resulting traces.
42 */
43 @RunWith(TestPrintRunner.class)
44 public abstract class AppContextITBase {
45
46 protected static final String EVENT_NAME = "EventName";
47
48 protected static final String RETRIEVER_NAME_1 = "Retriever1";
49 protected static final String RETRIEVER_NAME_2 = "Retriever2";
50
51 private static final String CONTEXT_NAME = ContextInfoRetrieverStubs.CONTEXT_NAME;
52
53 private ContextInfoManager cim;
54 private ILttngSession session;
55
56 /* Field defined by the sub-class */
57 protected ILttngHandler logHandler;
58
59 protected abstract Domain getDomain();
60
61 protected abstract void sendEventsToLoggers();
62
63 /**
64 * Base test setup
65 */
66 @Before
67 public void testSetup() {
68 try {
69 cim = ContextInfoManager.getInstance();
70 } catch (SecurityException | IOException e) {
71 /* The native library is not available! */
72 fail();
73 }
74 session = ILttngSession.createSession(null, getDomain());
75 }
76
77 /**
78 * Base test teardown
79 */
80 @After
81 public void testTeardown() {
82 session.close();
83
84 logHandler.close();
85 logHandler = null;
86
87 /* In case some tests fail or forget to unregister their retrievers */
88 cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1);
89 cim.unregisterContextInfoRetriever(RETRIEVER_NAME_2);
90 }
91
92 // ------------------------------------------------------------------------
93 // Context enabled/disabled tests
94 // ------------------------------------------------------------------------
95
96 /**
97 * Utility method to check that a context is present in all events of a
98 * trace output.
99 */
100 private static void testContextPresentInTrace(List<String> traceOutput, String retrieverName, String contextName, String contextValue) {
101 String fullString = "_app_" + retrieverName + "_" + contextName + " = " + contextValue;
102 traceOutput.forEach(line -> assertTrue(line.contains(fullString)));
103 }
104
105 /**
106 * Utility method to check that a context is *absent* from all events of a
107 * trace output
108 */
109 private static void testContextNotPresentInTrace(List<String> traceOutput, String retrieverName, String contextName) {
110 String fullString = "_app_" + retrieverName + "_" + contextName;
111 traceOutput.forEach(line -> assertFalse(line.contains(fullString)));
112 }
113
114 /**
115 * Test that if no retrievers are declared, no context info is passed at
116 * all.
117 */
118 @Test
119 public void testNoContexts() {
120 assertTrue(session.enableAllEvents());
121 assertTrue(session.start());
122 sendEventsToLoggers();
123 assertTrue(session.stop());
124
125 List<String> output = session.view();
126 assertNotNull(output);
127 assertFalse(output.isEmpty());
128
129 /* Test that there is no "_app" contexts in the output */
130 output.forEach(line -> assertFalse(line.contains("_app")));
131 }
132
133 /**
134 * Test that if a retriever is registered and provides a context, but this
135 * context is not enabled in the tracing session, that it is not present in
136 * the trace.
137 */
138 @Test
139 public void testContextAvailableButNotEnabled() {
140 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
141
142 assertTrue(session.enableAllEvents());
143 assertTrue(session.start());
144 sendEventsToLoggers();
145 assertTrue(session.stop());
146
147 List<String> output = session.view();
148 assertNotNull(output);
149 assertFalse(output.isEmpty());
150
151 /* Test that there is no "_app" contexts in the output */
152 output.forEach(line -> assertFalse(line.contains("_app")));
153
154 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
155 }
156
157 /**
158 * Test that if a context is enabled, but no retriever provides it, that the
159 * retriever/context names are still mentioned in the event but no value is
160 * provided.
161 */
162 @Test
163 public void testContextNotAvailableButEnabled() {
164 assertTrue(session.enableAllEvents());
165 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
166
167 assertTrue(session.start());
168 sendEventsToLoggers();
169 assertTrue(session.stop());
170
171 List<String> output = session.view();
172 assertNotNull(output);
173 assertFalse(output.isEmpty());
174
175 /* Test that context name is there but value is not */
176 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME, "{ none = { } } }");
177 }
178
179 /**
180 * Test that if a context is enabled and provided by a retriever that it is
181 * correctly present in the tracing session.
182 */
183 @Test
184 public void testContextAvailableAndEnabled() {
185 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
186
187 assertTrue(session.enableAllEvents());
188 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
189
190 assertTrue(session.start());
191 sendEventsToLoggers();
192 assertTrue(session.stop());
193
194 List<String> output = session.view();
195 assertNotNull(output);
196 assertFalse(output.isEmpty());
197
198 /* Test that context name + value are present */
199 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
200 "{ string = \"" + ContextInfoRetrieverStubs.STRING_VALUE + "\" }");
201
202 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
203 }
204
205 /**
206 * Test that one context is available by a retriever, but another is is
207 * enabled in the session. Only the latter should be mentioned in events,
208 * with no value.
209 */
210 @Test
211 public void testContextsOneAvailableOtherEnabled() {
212 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
213
214 assertTrue(session.enableAllEvents());
215 assertTrue(session.enableAppContext(RETRIEVER_NAME_2, CONTEXT_NAME));
216
217 assertTrue(session.start());
218 sendEventsToLoggers();
219 assertTrue(session.stop());
220
221 List<String> output = session.view();
222 assertNotNull(output);
223 assertFalse(output.isEmpty());
224
225 /* Test that only retriever-name-2 is present, with no value */
226 testContextNotPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME);
227 testContextPresentInTrace(output, RETRIEVER_NAME_2, CONTEXT_NAME, "{ none = { } } }");
228
229 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
230 }
231
232 /**
233 * Test with two contexts provided in the application, but only one of them
234 * is enabled in the session. Only that one should be present in the trace,
235 * name and value.
236 */
237 @Test
238 public void testContextsTwoAvailableOneEnabled() {
239 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
240 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_2, ContextInfoRetrieverStubs.INTEGER_RETRIEVER));
241
242 assertTrue(session.enableAllEvents());
243 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
244
245 assertTrue(session.start());
246 sendEventsToLoggers();
247 assertTrue(session.stop());
248
249 List<String> output = session.view();
250 assertNotNull(output);
251 assertFalse(output.isEmpty());
252
253 /* Test that only retriever-name-1 is present, name + value */
254 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
255 "{ string = \"" + ContextInfoRetrieverStubs.STRING_VALUE + "\" }");
256 testContextNotPresentInTrace(output, RETRIEVER_NAME_2, CONTEXT_NAME);
257
258 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
259 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_2));
260 }
261
262 /**
263 * Test with two contexts enabled in the session but only one of them is
264 * provided by the application. Both should be mentioned in the trace, but
265 * only the provided one will have a value.
266 */
267 @Test
268 public void testContextsOneAvailableTwoEnabled() {
269 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
270
271 assertTrue(session.enableAllEvents());
272 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
273 assertTrue(session.enableAppContext(RETRIEVER_NAME_2, CONTEXT_NAME));
274
275 assertTrue(session.start());
276 sendEventsToLoggers();
277 assertTrue(session.stop());
278
279 List<String> output = session.view();
280 assertNotNull(output);
281 assertFalse(output.isEmpty());
282
283 /* Test that both contexts are present, but only retriever-1's has a value */
284 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
285 "{ string = \"" + ContextInfoRetrieverStubs.STRING_VALUE + "\" }");
286 testContextPresentInTrace(output, RETRIEVER_NAME_2, CONTEXT_NAME, "{ none = { } } }");
287
288 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
289 }
290
291 // ------------------------------------------------------------------------
292 // Context types tests
293 // ------------------------------------------------------------------------
294
295 /**
296 * Utility method to enable all events, add the one context we are looking
297 * for, take a trace, and return the trace output.
298 */
299 private List<String> enableContextAndTrace() {
300 assertTrue(session.enableAllEvents());
301 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
302 assertTrue(session.start());
303 sendEventsToLoggers();
304 assertTrue(session.stop());
305
306 List<String> output = session.view();
307 assertNotNull(output);
308 assertFalse(output.isEmpty());
309
310 return output;
311 }
312
313 /**
314 * Test a "null" context value.
315 */
316 @Test
317 public void testContextValueNull() {
318 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.NULL_RETRIEVER));
319
320 List<String> output = enableContextAndTrace();
321 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME, "{ none = { } } }");
322
323 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
324 }
325
326 /**
327 * Test an integer (int32) context value.
328 */
329 @Test
330 public void testContextValueInteger() {
331 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.INTEGER_RETRIEVER));
332
333 List<String> output = enableContextAndTrace();
334 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
335 "{ int32 = " + ContextInfoRetrieverStubs.INTEGER_VALUE + " } }");
336
337 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
338 }
339
340 /**
341 * Test a long (int64) context value.
342 */
343 @Test
344 public void testContextValueLong() {
345 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.LONG_RETRIEVER));
346
347 List<String> output = enableContextAndTrace();
348 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
349 "{ int64 = " + ContextInfoRetrieverStubs.LONG_VALUE + " } }");
350
351 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
352 }
353
354 /**
355 * Test a double context value.
356 */
357 @Test
358 public void testContextValueDouble() {
359 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.DOUBLE_RETRIEVER));
360
361 List<String> output = enableContextAndTrace();
362 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
363 "{ double = " + ContextInfoRetrieverStubs.DOUBLE_VALUE + " } }");
364
365 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
366 }
367
368 /**
369 * Test a character context value (should get converted to a string).
370 */
371 @Test
372 public void testContextValueCharacter() {
373 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.CHARACTER_RETRIEVER));
374
375 List<String> output = enableContextAndTrace();
376 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
377 "{ string = \"" + ContextInfoRetrieverStubs.CHARACTER_VALUE + "\" } }");
378
379 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
380 }
381
382 /**
383 * Test a float context value.
384 */
385 @Test
386 public void testContextValueFloat() {
387 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.FLOAT_RETRIEVER));
388
389 List<String> output = enableContextAndTrace();
390 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
391 "{ float = " + ContextInfoRetrieverStubs.FLOAT_VALUE + " } }");
392
393 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
394 }
395
396 /**
397 * Test a byte (int8) context value.
398 */
399 @Test
400 public void testContextValueByte() {
401 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.BYTE_RETRIEVER));
402
403 List<String> output = enableContextAndTrace();
404 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
405 "{ int8 = " + ContextInfoRetrieverStubs.BYTE_VALUE + " } }");
406
407 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
408 }
409
410 /**
411 * Test a short (int16) context value.
412 */
413 @Test
414 public void testContextValueShort() {
415 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.SHORT_RETRIEVER));
416
417 List<String> output = enableContextAndTrace();
418 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
419 "{ int16 = " + ContextInfoRetrieverStubs.SHORT_VALUE + " } }");
420
421 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
422 }
423
424 /**
425 * Test a "true" boolean context value (gets converted to a int8 of value 1).
426 */
427 @Test
428 public void testContextValueBooleanTrue() {
429 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.BOOLEAN_TRUE_RETRIEVER));
430
431 List<String> output = enableContextAndTrace();
432 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME, "{ int8 = 1 } }");
433
434 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
435 }
436
437 /**
438 * Test a "false" boolean context value (gets converted to a int8 of value 0).
439 */
440 @Test
441 public void testContextValueBooleanFalse() {
442 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.BOOLEAN_FALSE_RETRIEVER));
443
444 List<String> output = enableContextAndTrace();
445 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME, "{ int8 = 0 } }");
446
447 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
448 }
449
450 /**
451 * Test a string context value.
452 */
453 @Test
454 public void testContextValueString() {
455 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
456
457 List<String> output = enableContextAndTrace();
458 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
459 "{ string = \"" + ContextInfoRetrieverStubs.STRING_VALUE + "\" } }");
460
461 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
462 }
463
464 /**
465 * Test a Object context value (should be converted to a String via .toString()).
466 */
467 @Test
468 public void testContextValueObject() {
469 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.OBJECT_RETRIEVER));
470
471 List<String> output = enableContextAndTrace();
472 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
473 "{ string = \"" + ContextInfoRetrieverStubs.OBJECT_VALUE.toString() + "\" } }");
474
475 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
476 }
477
478 // ------------------------------------------------------------------------
479 // Tests related to filtering
480 // ------------------------------------------------------------------------
481
482 /**
483 * Test with a filter expression using a context, but not having the actual
484 * context enabled.
485 *
486 * The JNI should still send the context so UST can use it for filtering,
487 * but it should not be present in the resulting trace.
488 */
489 @Test
490 public void testContextFilterExpressionNotEnabled() {
491 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
492
493 assertTrue(session.enableEvent(EVENT_NAME, null, false,
494 "$app." + RETRIEVER_NAME_1 + ':' + CONTEXT_NAME + "==\"" + ContextInfoRetrieverStubs.STRING_VALUE + '\"'));
495
496 assertTrue(session.start());
497 sendEventsToLoggers();
498 assertTrue(session.stop());
499
500 List<String> output = session.view();
501 assertNotNull(output);
502 assertFalse(output.isEmpty());
503
504 testContextNotPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME);
505
506 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
507 }
508
509 /**
510 * Test with a filter expression and an enabled context. The filter however
511 * should *exclude* the events, so no events should be present in the
512 * resulting trace.
513 */
514 @Test
515 public void testContextFilterExpressionEnabledNotMatching() {
516 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
517
518 assertTrue(session.enableEvent(EVENT_NAME, null, false,
519 "$app." + RETRIEVER_NAME_1 + ':' + CONTEXT_NAME + "!=\"" + ContextInfoRetrieverStubs.STRING_VALUE + '\"'));
520
521 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
522 assertTrue(session.start());
523 sendEventsToLoggers();
524 assertTrue(session.stop());
525
526 List<String> output = session.view();
527 assertNotNull(output);
528 assertTrue(output.isEmpty());
529
530 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
531 }
532
533 /**
534 * Test with a filter expression and an enabled context. The filter however
535 * should match the events, so events with the context info should be
536 * present in the resulting trace.
537 */
538 @Test
539 public void testContextFilterExpressionEnabledMatching() {
540 assertTrue(cim.registerContextInfoRetriever(RETRIEVER_NAME_1, ContextInfoRetrieverStubs.STRING_RETRIEVER));
541
542 assertTrue(session.enableEvent(EVENT_NAME, null, false,
543 "$app." + RETRIEVER_NAME_1 + ':' + CONTEXT_NAME + "==\"" + ContextInfoRetrieverStubs.STRING_VALUE + '\"'));
544
545 assertTrue(session.enableAppContext(RETRIEVER_NAME_1, CONTEXT_NAME));
546 assertTrue(session.start());
547 sendEventsToLoggers();
548 assertTrue(session.stop());
549
550 List<String> output = session.view();
551 assertNotNull(output);
552 assertFalse(output.isEmpty());
553
554 testContextPresentInTrace(output, RETRIEVER_NAME_1, CONTEXT_NAME,
555 "{ string = \"" + ContextInfoRetrieverStubs.STRING_VALUE + "\" } }");
556
557 assertTrue(cim.unregisterContextInfoRetriever(RETRIEVER_NAME_1));
558 }
559 }
This page took 0.038595 seconds and 3 git commands to generate.