2323#import " AWSLogging.h"
2424#import " AWSMobileAnalyticsERS.h"
2525
26- NSString *const AWSMobileAnalyticsDefaultRunLoopMode = @" com.amazonaws.mobile-analytics.AWSMobileAnalyticsDefaultRunLoopMode" ;
26+ @interface AWSMobileAnalyticsDefaultHttpClient ()
27+
28+ @property (nonatomic , strong ) NSMutableArray *interceptors;
29+
30+ @end
2731
2832@implementation AWSMobileAnalyticsDefaultHttpClient
2933
30- +(AWSMobileAnalyticsDefaultHttpClient *) httpClient
31- {
34+ + (AWSMobileAnalyticsDefaultHttpClient *)httpClient {
3235 return [[AWSMobileAnalyticsDefaultHttpClient alloc ] init ];
3336}
3437
35- -(id ) init
36- {
37- if (self = [super init ])
38- {
39- self->_interceptors = [NSMutableArray array ];
38+ - (id )init {
39+ if (self = [super init ]) {
40+ _interceptors = [NSMutableArray array ];
4041 }
4142 return self;
4243}
4344
44- -(void ) addInterceptor : (id <AWSMobileAnalyticsInterceptor>) theInterceptor
45- {
46- if (theInterceptor == nil )
47- {
45+ - (void )addInterceptor : (id <AWSMobileAnalyticsInterceptor>)theInterceptor {
46+ if (theInterceptor == nil ) {
4847 return ;
4948 }
50-
51- [self ->_interceptors addObject: theInterceptor];
49+
50+ [self .interceptors addObject: theInterceptor];
5251}
5352
54- -(id <AWSMobileAnalyticsRequest>) newRequest
55- {
53+ - (id <AWSMobileAnalyticsRequest>)freshRequest {
5654 return [[AWSMobileAnalyticsDefaultRequest alloc ] init ];
5755}
5856
59- -(id <AWSMobileAnalyticsResponse>) execute : (id <AWSMobileAnalyticsRequest>) theRequest withRetries : (int ) theRetries withTimeout : (NSTimeInterval ) theTimeout
60- {
61- return [self execute: theRequest withRetries: theRetries withTimeout: theTimeout withRetryHandler: nil ];
57+ - (id <AWSMobileAnalyticsResponse>)execute : (id <AWSMobileAnalyticsRequest>)request
58+ withRetries : (int )retries
59+ withTimeout : (NSTimeInterval )timeout {
60+ return [self execute: request
61+ withRetries: retries
62+ withTimeout: timeout
63+ withRetryHandler: nil ];
6264}
6365
64- -(id <AWSMobileAnalyticsResponse>) execute : (id <AWSMobileAnalyticsRequest>) theRequest withRetries : (int ) theRetries withTimeout : (NSTimeInterval ) theTimeout withRetryHandler : (RetryHandler) theRetryHandler
65- {
66+ - (id <AWSMobileAnalyticsResponse>)execute : (id <AWSMobileAnalyticsRequest>)theRequest
67+ withRetries : (int )theRetries
68+ withTimeout : (NSTimeInterval )theTimeout
69+ withRetryHandler : (RetryHandler)theRetryHandler {
6670 __block AWSMobileAnalyticsDefaultResponse *response = [[AWSMobileAnalyticsDefaultResponse alloc ] init ];
67- if (theRequest == nil )
68- {
71+ if (theRequest == nil ) {
6972 response.originatingRequest = theRequest;
7073 response.code = 0 ;
7174 response.message = @" Nil request" ;
7275 return response;
7376 }
74-
77+
7578 // Apply the interceptors to the built request
76- for (id <AWSMobileAnalyticsInterceptor> interceptor in self->_interceptors )
77- {
79+ for (id <AWSMobileAnalyticsInterceptor> interceptor in self.interceptors ) {
7880 [interceptor before: theRequest];
7981 }
80-
82+
8183 AWSMobileAnalyticsERS *ers = self.ers ;
82- if (ers == nil ) {
83- AWSLogError ( @" AWSMobileAnalyticsERS is nil! " );
84+ if (ers == nil ){
85+ AWSLogError ( @" AWSMobileAnalyticsERS is nil. " );
8486 }
85-
87+
8688 AWSMobileAnalyticsERSPutEventsInput *putEventInput = [AWSMobileAnalyticsERSPutEventsInput new ];
87-
89+
8890 // the client-Context-id in the header should be moved to Client-Context
8991 NSString *clientContextString = [[theRequest headers ] objectForKey: AWSMobileAnalyticsClientContextHeader];
9092 NSMutableDictionary *clientContextDic = [[NSJSONSerialization JSONObjectWithData: [clientContextString dataUsingEncoding: NSUTF8StringEncoding]
9193 options: kNilOptions
9294 error: NULL ] mutableCopy ];
93- if (clientContextDic && [clientContextDic isKindOfClass: [NSDictionary class ]] && [[theRequest headers ] objectForKey: INSTANCE_ID_HEADER_KEY]) {
95+ if (clientContextDic
96+ && [clientContextDic isKindOfClass: [NSDictionary class ]]
97+ && [[theRequest headers ] objectForKey: INSTANCE_ID_HEADER_KEY]) {
9498 NSMutableDictionary *mutableClientDic = [clientContextDic[@" client" ] mutableCopy ];
9599 [mutableClientDic setObject: [[theRequest headers ] objectForKey: INSTANCE_ID_HEADER_KEY] forKey: @" client_id" ];
96100 [clientContextDic setObject: mutableClientDic forKey: @" client" ];
97101 }
98- NSData *jsonData = [NSJSONSerialization dataWithJSONObject: clientContextDic options: kNilOptions error: NULL ];
102+
103+ NSData *jsonData = [NSJSONSerialization dataWithJSONObject: clientContextDic
104+ options: kNilOptions
105+ error: NULL ];
99106 if (jsonData) {
100- putEventInput.clientContext = [[NSString alloc ] initWithData: jsonData encoding: NSUTF8StringEncoding];
107+ putEventInput.clientContext = [[NSString alloc ] initWithData: jsonData
108+ encoding: NSUTF8StringEncoding];
101109 }
102-
103-
110+
104111 // adapt the body
105112 if ([theRequest postBody ]) {
106113 NSData *unzippedBody = [[theRequest postBody ] gunzippedData ];
107114 NSArray *sourceEventsArray = [NSJSONSerialization JSONObjectWithData: unzippedBody options: kNilOptions error: NULL ];
108115 NSAssert ([sourceEventsArray isKindOfClass: [NSArray class ]] , @" invalid postBody: postBody should be an array" );
109-
116+
110117 NSMutableArray *parsedEventsArray = [NSMutableArray new ];
111118 for (NSDictionary *event in sourceEventsArray) {
112-
119+
113120 AWSMobileAnalyticsERSEvent *serviceEvent = [AWSMobileAnalyticsERSEvent new ];
114121 AWSMobileAnalyticsERSSession *serviceSession = [AWSMobileAnalyticsERSSession new ];
115-
122+
116123 // process the attributes
117124 NSMutableDictionary *mutableAttributesDic = [event[@" attributes" ] mutableCopy ];
118125 NSMutableDictionary *mutableMetricsDic = [event[@" metrics" ] mutableCopy ];
119126 serviceEvent.version = mutableAttributesDic[@" ver" ];
120127 [mutableAttributesDic removeObjectForKey: @" ver" ];
121-
128+
122129 serviceSession.id = mutableAttributesDic[AWSSessionIDAttributeKey];
123130 [mutableAttributesDic removeObjectForKey: AWSSessionIDAttributeKey];
124-
131+
125132 serviceSession.startTimestamp = mutableAttributesDic[AWSSessionStartTimeAttributeKey];
126133 [mutableAttributesDic removeObjectForKey: AWSSessionStartTimeAttributeKey];
127-
134+
128135 // move sessionStop time attribute session section
129136 serviceSession.stopTimestamp = mutableAttributesDic[AWSSessionEndTimeAttributeKey];
130137 [mutableAttributesDic removeObjectForKey: AWSSessionEndTimeAttributeKey];
131-
138+
132139 // move session duration Time metrics to session section
133140 serviceSession.duration = mutableMetricsDic[AWSSessionDurationMetricKey];
134141 [mutableMetricsDic removeObjectForKey: AWSSessionDurationMetricKey];
135-
142+
136143 serviceEvent.session = serviceSession;
137144 serviceEvent.attributes = mutableAttributesDic;
138145 serviceEvent.metrics = mutableMetricsDic;
139-
146+
140147 // process others
141148 serviceEvent.eventType = event[@" event_type" ];
142- serviceEvent.timestamp = [[NSDate date ] aws_stringValue: AWSDateISO8601DateFormat3];
143-
144-
145-
149+ serviceEvent.timestamp = event[@" timestamp" ];
150+
146151 [parsedEventsArray addObject: serviceEvent];
147152 }
148153 putEventInput.events = parsedEventsArray;
149154 }
150-
155+
151156 // Attach the request to the response
152157 id <AWSMobileAnalyticsRequest> request = [[AWSMobileAnalyticsDefaultRequest alloc ] init ];
153158 [request setUrl: ers.configuration.URL];
154159 response.originatingRequest = request;
155-
160+
156161 NSDate * requestStartDate = [NSDate date ];
157162 [[[ers putEvents: putEventInput] continueWithBlock: ^id (BFTask *task) {
158-
163+
159164 NSDictionary *resultDictionary = nil ;
160165 if (task.error ) {
161166 response.error = task.error ;
@@ -165,124 +170,55 @@ -(void) addInterceptor: (id<AWSMobileAnalyticsInterceptor>) theInterceptor
165170 resultDictionary = task.result ;
166171 }
167172 }
168-
173+
169174 if (resultDictionary) {
170175 [[resultDictionary objectForKey: @" responseHeaders" ] enumerateKeysAndObjectsUsingBlock: ^(NSString *headerName, id headerValue, BOOL *stop) {
171176 [response addHeader: headerValue withName: headerName];
172177 }];
173178 response.responseSize = [resultDictionary[@" responseDataSize" ] longValue ];
174179 response.code = [resultDictionary[@" responseStatusCode" ] intValue ];
175180 }
176-
181+
177182 response.isFinishedLoading = YES ;
178-
183+
179184 // it may be possible for the timer that controls the connectionTimeout
180185 // to fire at the exact same as this method. To ensure a correct state,
181186 // reset the connection timeout since we truly did succeed if this method is
182187 // called. We do not process the connectionTimeout if this method
183188 // is called before the timer
184189 response.didConnectionTimeout = NO ;
185-
190+
186191 NSTimeInterval elapsedTime = [[NSDate date ] timeIntervalSinceDate: requestStartDate];
187192 response.timeToComplete = elapsedTime;
188-
193+
189194 response.requiredAttempts = 1 ;
190195 response.connectionTimeout = theTimeout;
191-
196+
192197 return nil ;
193-
194- }] waitUntilFinished ];
195198
196-
197- // NSMutableURLRequest *request = [self buildRequest:theRequest withTimeout:theTimeout];
198- //
199- // int attempts = 1;
200- // int maxAttempts = (theRetries > 0) ? theRetries + 1 : 1;
201- //
202- // AWSLogDebug( @"Will attempt the request a maximum of %d times", maxAttempts);
203- // NSTimeInterval totalRequestTime = 0.0;
204- // while (attempts <= maxAttempts) {
205- //
206- // NSDate* requestStartDate = [NSDate date];
207- // AWSLogDebug( @"Attempt %d of %d", attempts, maxAttempts);
208- //
209- // //Attach the request to the response
210- // response.originatingRequest = theRequest;
211- //
212- // NSURLConnection *urlConnection = [[NSURLConnection alloc] initWithRequest:request
213- // delegate:response
214- // startImmediately:NO];
215- // //Schedule the urlConnection to run in the currentRunLoop
216- // [urlConnection scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:insightsDefaultRunLoopMode];
217- //
218- // //Start the request execution
219- // [urlConnection start];
220- //
221- // NSTimer *connectionTimeoutTimer = [NSTimer timerWithTimeInterval:theTimeout
222- // target:response
223- // selector:@selector(processConnectionTimeout)
224- // userInfo:nil
225- // repeats:NO];
226- //
227- // //Attach a timer to the currentRunLoop to timeout the execution of the request if necessary
228- // [[NSRunLoop currentRunLoop] addTimer:connectionTimeoutTimer forMode:insightsDefaultRunLoopMode];
229- //
230- // //Block while the request has not been completed. Do not block longer
231- // //than the timeout interval since a timer tick will not cause the
232- // //run loop blocking call to wake up
233- // NSDate* timeoutDate = [NSDate dateWithTimeIntervalSinceNow:theTimeout];
234- // while (!response.isFinishedLoading) {
235- // [[NSRunLoop currentRunLoop] runMode:insightsDefaultRunLoopMode beforeDate:timeoutDate];
236- // }
237- //
238- // NSTimeInterval elapsedTime = [[NSDate date] timeIntervalSinceDate:requestStartDate];
239- // AWSLogDebug( @"Time of request %f", elapsedTime);
240- // totalRequestTime += elapsedTime;
241- //
242- // if (response.didTimeout) {
243- // // cancel current connection to ensure all resources are freed
244- // [urlConnection cancel];
245- // }
246- //
247- // // always invalidate the timer so that it is removed from the run loop
248- // [connectionTimeoutTimer invalidate];
249- //
250- // if (theRetryHandler != nil && theRetryHandler(response.code)) {
251- // attempts++;
252- // }
253- // else {
254- // break;
255- // }
256- // //If the request is going to be reattempted then create a new response object
257- // response = [[AWSMobileAnalyticsDefaultResponse alloc] init];
258- // }
259- //
260- // response.timeToComplete = totalRequestTime;
261- // response.requiredAttempts = attempts <= maxAttempts ? attempts : maxAttempts;
262- // response.connectionTimeout = theTimeout;
263-
264- for (id <AWSMobileAnalyticsInterceptor> interceptor in self->_interceptors )
265- {
199+ }] waitUntilFinished ];
200+
201+ for (id <AWSMobileAnalyticsInterceptor> interceptor in self.interceptors ) {
266202 [interceptor after: response];
267203 }
268-
204+
269205 return response;
270206}
271207
272- -(NSMutableURLRequest *) buildRequest : (id <AWSMobileAnalyticsRequest>) theOriginalRequest withTimeout : (NSTimeInterval ) theTimeout
273- {
274- NSMutableURLRequest *request = [[NSMutableURLRequest alloc ] initWithURL: theOriginalRequest.url cachePolicy: NSURLRequestReloadIgnoringLocalCacheData timeoutInterval: theTimeout];
275- if (theOriginalRequest.method == GET)
276- {
208+ - (NSMutableURLRequest *)buildRequest : (id <AWSMobileAnalyticsRequest>)theOriginalRequest
209+ withTimeout : (NSTimeInterval )theTimeout {
210+ NSMutableURLRequest *request = [[NSMutableURLRequest alloc ] initWithURL: theOriginalRequest.url
211+ cachePolicy: NSURLRequestReloadIgnoringLocalCacheData
212+ timeoutInterval: theTimeout];
213+ if (theOriginalRequest.method == GET) {
277214 [request setHTTPMethod: @" GET" ];
278- }
279- else if (theOriginalRequest.method == POST)
280- {
215+ } else if (theOriginalRequest.method == POST) {
281216 [request setHTTPMethod: @" POST" ];
282217 }
283218
284219 [request setHTTPBody: theOriginalRequest.postBody];
285220 [request setAllHTTPHeaderFields: theOriginalRequest.headers];
221+
286222 return request;
287223}
288224
0 commit comments