4141import java .util .List ;
4242import java .util .Map ;
4343import java .util .concurrent .atomic .AtomicReference ;
44+ import java .util .regex .Pattern ;
4445
4546@ Log4j2
4647public class TraceValidator implements IValidator {
@@ -65,39 +66,47 @@ public void init(
6566
6667 @ Override
6768 public void validate () throws Exception {
68- // get stored trace
69- Map <String , Object > storedTrace = this .getStoredTrace ();
70- log .info ("value of stored trace map: {}" , storedTrace );
71- // create trace id list to retrieve trace from x-ray service
72- String traceId = (String ) storedTrace .get ("[0].trace_id" );
73- List <String > traceIdList = Collections .singletonList (traceId );
74-
75- // get retrieved trace from x-ray service
76- boolean isMatched = RetryHelper .retry (10 ,
69+ // 2 retries for calling the sample app to handle the Lambda case,
70+ // where first request might be a cold start and have an additional unexpected subsegment
71+ boolean isMatched = RetryHelper .retry (2 ,
7772 Integer .parseInt (GenericConstants .SLEEP_IN_MILLISECONDS .getVal ()),
7873 false ,
7974 () -> {
80- Map <String , Object > retrievedTrace = this .getRetrievedTrace (traceIdList );
81- log .info ("value of retrieved trace map: {}" , retrievedTrace );
82- // data model validation of other fields of segment document
83- for (Map .Entry <String , Object > entry : storedTrace .entrySet ()) {
84- String targetKey = entry .getKey ();
85- if (retrievedTrace .get (targetKey ) == null ) {
86- log .error ("mis target data: {}" , targetKey );
87- throw new BaseException (ExceptionCode .DATA_MODEL_NOT_MATCHED );
88- }
89- if (!entry
90- .getValue ()
91- .toString ()
92- .equalsIgnoreCase (retrievedTrace .get (targetKey ).toString ())) {
93- log .error ("data model validation failed" );
94- log .info ("mis matched data model field list" );
95- log .info ("value of stored trace map: {}" , entry .getValue ());
96- log .info ("value of retrieved map: {}" , retrievedTrace .get (entry .getKey ()));
97- log .info ("==========================================" );
98- throw new BaseException (ExceptionCode .DATA_MODEL_NOT_MATCHED );
99- }
100- }
75+ // Call sample app and get locally stored trace
76+ Map <String , Object > storedTrace = this .getStoredTrace ();
77+ log .info ("value of stored trace map: {}" , storedTrace );
78+
79+ // prepare list of trace IDs to retrieve from X-Ray service
80+ String traceId = (String ) storedTrace .get ("[0].trace_id" );
81+ List <String > traceIdList = Collections .singletonList (traceId );
82+
83+ // Retry 5 times to since segments might not be immediately available in X-Ray service
84+ RetryHelper .retry (
85+ 5 ,
86+ () -> {
87+ // get retrieved trace from x-ray service
88+ Map <String , Object > retrievedTrace = this .getRetrievedTrace (traceIdList );
89+ log .info ("value of retrieved trace map: {}" , retrievedTrace );
90+
91+ // data model validation of other fields of segment document
92+ for (Map .Entry <String , Object > entry : storedTrace .entrySet ()) {
93+ String targetKey = entry .getKey ();
94+ if (retrievedTrace .get (targetKey ) == null ) {
95+ log .error ("mis target data: {}" , targetKey );
96+ throw new BaseException (ExceptionCode .DATA_MODEL_NOT_MATCHED );
97+ }
98+
99+ if (!Pattern .matches (entry .getValue ().toString (),
100+ retrievedTrace .get (targetKey ).toString ())) {
101+ log .error ("data model validation failed" );
102+ log .info ("mis matched data model field list" );
103+ log .info ("value of stored trace map: {}" , entry .getValue ());
104+ log .info ("value of retrieved map: {}" , retrievedTrace .get (entry .getKey ()));
105+ log .info ("==========================================" );
106+ throw new BaseException (ExceptionCode .DATA_MODEL_NOT_MATCHED );
107+ }
108+ }
109+ });
101110 });
102111
103112 if (!isMatched ) {
@@ -109,28 +118,12 @@ public void validate() throws Exception {
109118
110119 // this method will hit get trace from x-ray service and get retrieved trace
111120 private Map <String , Object > getRetrievedTrace (List <String > traceIdList ) throws Exception {
112- AtomicReference <Map <String , Object >> flattenedJsonMapForRetrievedTrace =
113- new AtomicReference <>();
114- RetryHelper .retry (
115- 30 ,
116- () -> {
117- List <Trace > retrieveTraceList = null ;
118- retrieveTraceList = xrayService .listTraceByIds (traceIdList );
119- if (retrieveTraceList == null || retrieveTraceList .isEmpty ()) {
120- throw new BaseException (ExceptionCode .EMPTY_LIST );
121- }
122-
123- // in case the json format is wrong, retry it.
124- if (!retrieveTraceList .isEmpty ()) {
125- flattenedJsonMapForRetrievedTrace .set (
126- this .flattenDocument (retrieveTraceList .get (0 ).getSegments ()));
127- } else {
128- log .error ("retrieved trace list is empty or null" );
129- throw new BaseException (ExceptionCode .EMPTY_LIST );
130- }
131- });
132-
133- return flattenedJsonMapForRetrievedTrace .get ();
121+ List <Trace > retrieveTraceList = xrayService .listTraceByIds (traceIdList );
122+ if (retrieveTraceList == null || retrieveTraceList .isEmpty ()) {
123+ throw new BaseException (ExceptionCode .EMPTY_LIST );
124+ }
125+
126+ return this .flattenDocument (retrieveTraceList .get (0 ).getSegments ());
134127 }
135128
136129 private Map <String , Object > flattenDocument (List <Segment > segmentList ) {
0 commit comments