4141static NSString *const kFDLAnalyticsDataMediumKey = @" utmMedium" ;
4242static NSString *const kFDLAnalyticsDataCampaignKey = @" utmCampaign" ;
4343static NSString *const kHeaderIosBundleIdentifier = @" X-Ios-Bundle-Identifier" ;
44+ static NSString *const kGenericErrorDomain = @" com.firebase.dynamicLinks" ;
4445
4546typedef NSDictionary *_Nullable (^FIRDLNetworkingParserBlock)(
4647 NSString *requestURLString,
@@ -67,7 +68,7 @@ void FIRMakeHTTPRequest(NSURLRequest *request, FIRNetworkRequestCompletionHandle
6768 [session dataTaskWithRequest: request
6869 completionHandler: ^(NSData *_Nullable data, NSURLResponse *_Nullable response,
6970 NSError *_Nullable error) {
70- completion (data, error);
71+ completion (data, response, error);
7172 }];
7273 [dataTask resume ];
7374}
@@ -91,6 +92,41 @@ - (instancetype)initWithAPIKey:(NSString *)APIKey URLScheme:(NSString *)URLSchem
9192 return self;
9293}
9394
95+ + (nullable NSError *)extractErrorForShortLink : (NSURL *)url
96+ data : (NSData *)data
97+ response : (NSURLResponse *)response
98+ error : (nullable NSError *)error {
99+ if (error) {
100+ return error;
101+ }
102+
103+ NSInteger statusCode = [(NSHTTPURLResponse *)response statusCode ];
104+ NSError *customError = nil ;
105+
106+ if (![response isKindOfClass: [NSHTTPURLResponse class ]]) {
107+ customError =
108+ [NSError errorWithDomain: kGenericErrorDomain
109+ code: 0
110+ userInfo: @{@" message" : @" Response should be of type NSHTTPURLResponse." }];
111+ } else if ((statusCode < 200 || statusCode >= 300 ) && data) {
112+ NSDictionary *result = [NSJSONSerialization JSONObjectWithData: data options: 0 error: nil ];
113+ if ([result isKindOfClass: [NSDictionary class ]] && [result objectForKey: @" error" ]) {
114+ id err = [result objectForKey: @" error" ];
115+ customError = [NSError errorWithDomain: kGenericErrorDomain code: statusCode userInfo: err];
116+ } else {
117+ customError = [NSError
118+ errorWithDomain: kGenericErrorDomain
119+ code: 0
120+ userInfo: @{
121+ @" message" :
122+ [NSString stringWithFormat: @" Failed to resolve link: %@ " , url.absoluteString]
123+ }];
124+ }
125+ }
126+
127+ return customError;
128+ }
129+
94130#pragma mark - Public interface
95131
96132- (void )resolveShortLink : (NSURL *)url
@@ -108,34 +144,39 @@ - (void)resolveShortLink:(NSURL *)url
108144 @" sdk_version" : FDLSDKVersion
109145 };
110146
111- FIRNetworkRequestCompletionHandler resolveLinkCallback = ^(NSData *data, NSError *error) {
112- NSURL *resolvedURL;
113-
114- if (!error && data) {
115- NSDictionary *result = [NSJSONSerialization JSONObjectWithData: data options: 0 error: nil ];
116- if ([result isKindOfClass: [NSDictionary class ]]) {
117- id invitationIDObject = [result objectForKey: @" invitationId" ];
118-
119- NSString *invitationIDString;
120- if ([invitationIDObject isKindOfClass: [NSDictionary class ]]) {
121- NSDictionary *invitationIDDictionary = invitationIDObject;
122- invitationIDString = invitationIDDictionary[@" id" ];
123- } else if ([invitationIDObject isKindOfClass: [NSString class ]]) {
124- invitationIDString = invitationIDObject;
147+ FIRNetworkRequestCompletionHandler resolveLinkCallback =
148+ ^(NSData *data, NSURLResponse *response, NSError *error) {
149+ NSURL *resolvedURL = nil ;
150+ NSError *extractedError = [FIRDynamicLinkNetworking extractErrorForShortLink: url
151+ data: data
152+ response: response
153+ error: error];
154+
155+ if (!extractedError && data) {
156+ NSDictionary *result = [NSJSONSerialization JSONObjectWithData: data options: 0 error: nil ];
157+ if ([result isKindOfClass: [NSDictionary class ]]) {
158+ id invitationIDObject = [result objectForKey: @" invitationId" ];
159+
160+ NSString *invitationIDString;
161+ if ([invitationIDObject isKindOfClass: [NSDictionary class ]]) {
162+ NSDictionary *invitationIDDictionary = invitationIDObject;
163+ invitationIDString = invitationIDDictionary[@" id" ];
164+ } else if ([invitationIDObject isKindOfClass: [NSString class ]]) {
165+ invitationIDString = invitationIDObject;
166+ }
167+
168+ NSString *deepLinkString = result[kFDLResolvedLinkDeepLinkURLKey ];
169+ NSString *minAppVersion = result[kFDLResolvedLinkMinAppVersionKey ];
170+ NSString *utmSource = result[kFDLAnalyticsDataSourceKey ];
171+ NSString *utmMedium = result[kFDLAnalyticsDataMediumKey ];
172+ NSString *utmCampaign = result[kFDLAnalyticsDataCampaignKey ];
173+ resolvedURL = FIRDLDeepLinkURLWithInviteID (invitationIDString, deepLinkString,
174+ utmSource, utmMedium, utmCampaign, NO , nil ,
175+ minAppVersion, self->_URLScheme , nil );
176+ }
125177 }
126-
127- NSString *deepLinkString = result[kFDLResolvedLinkDeepLinkURLKey ];
128- NSString *minAppVersion = result[kFDLResolvedLinkMinAppVersionKey ];
129- NSString *utmSource = result[kFDLAnalyticsDataSourceKey ];
130- NSString *utmMedium = result[kFDLAnalyticsDataMediumKey ];
131- NSString *utmCampaign = result[kFDLAnalyticsDataCampaignKey ];
132- resolvedURL = FIRDLDeepLinkURLWithInviteID (invitationIDString, deepLinkString, utmSource,
133- utmMedium, utmCampaign, NO , nil , minAppVersion,
134- self->_URLScheme , nil );
135- }
136- }
137- handler (resolvedURL, error);
138- };
178+ handler (resolvedURL, extractedError);
179+ };
139180
140181 NSString *requestURLString =
141182 [NSString stringWithFormat: @" %@ /reopenAttribution%@ " , kiOSReopenRestBaseUrl,
@@ -242,13 +283,14 @@ - (void)convertInvitation:(NSString *)invitationID
242283 }
243284 };
244285
245- FIRNetworkRequestCompletionHandler convertInvitationCallback = ^(NSData *data, NSError *error) {
246- if (handler) {
247- dispatch_async (dispatch_get_main_queue (), ^{
248- handler (error);
249- });
250- }
251- };
286+ FIRNetworkRequestCompletionHandler convertInvitationCallback =
287+ ^(NSData *data, NSURLResponse *response, NSError *error) {
288+ if (handler) {
289+ dispatch_async (dispatch_get_main_queue (), ^{
290+ handler (error);
291+ });
292+ }
293+ };
252294
253295 NSString *requestURL = [NSString stringWithFormat: @" %@ /convertInvitation%@ " , kApiaryRestBaseUrl ,
254296 FIRDynamicLinkAPIKeyParameter (_APIKey)];
@@ -270,7 +312,7 @@ - (void)sendRequestWithBaseURLString:(NSString *)baseURL
270312 stringWithFormat: @" %@ /%@%@ " , baseURL, endpointPath, FIRDynamicLinkAPIKeyParameter (_APIKey)];
271313
272314 FIRNetworkRequestCompletionHandler completeInvitationByDeviceCallback =
273- ^(NSData *data, NSError *error) {
315+ ^(NSData *data, NSURLResponse *response, NSError *error) {
274316 if (error || !data) {
275317 dispatch_async (dispatch_get_main_queue (), ^{
276318 handler (nil , nil , error);
0 commit comments