FIRMessagingExtensionHelper.m 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. /*
  2. * Copyright 2019 Google
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. #import "FirebaseMessaging/Sources/Public/FirebaseMessaging/FIRMessagingExtensionHelper.h"
  17. #import "FirebaseMessaging/Sources/FIRMessagingCode.h"
  18. #import "FirebaseMessaging/Sources/FIRMessagingLogger.h"
  19. static NSString *const kPayloadOptionsName = @"fcm_options";
  20. static NSString *const kPayloadOptionsImageURLName = @"image";
  21. static NSString *const kNoExtension = @"";
  22. static NSString *const kImagePathPrefix = @"image/";
  23. @interface FIRMessagingExtensionHelper ()
  24. @property(nonatomic, strong) void (^contentHandler)(UNNotificationContent *contentToDeliver);
  25. @property(nonatomic, strong) UNMutableNotificationContent *bestAttemptContent;
  26. @end
  27. @implementation FIRMessagingExtensionHelper
  28. - (void)populateNotificationContent:(UNMutableNotificationContent *)content
  29. withContentHandler:(void (^)(UNNotificationContent *_Nonnull))contentHandler {
  30. self.contentHandler = [contentHandler copy];
  31. self.bestAttemptContent = content;
  32. // The `userInfo` property isn't available on newer versions of tvOS.
  33. #if TARGET_OS_IOS || TARGET_OS_OSX || TARGET_OS_WATCH
  34. NSString *currentImageURL = content.userInfo[kPayloadOptionsName][kPayloadOptionsImageURLName];
  35. if (!currentImageURL) {
  36. [self deliverNotification];
  37. return;
  38. }
  39. NSURL *attachmentURL = [NSURL URLWithString:currentImageURL];
  40. if (attachmentURL) {
  41. [self loadAttachmentForURL:attachmentURL
  42. completionHandler:^(UNNotificationAttachment *attachment) {
  43. if (attachment != nil) {
  44. self.bestAttemptContent.attachments = @[ attachment ];
  45. }
  46. [self deliverNotification];
  47. }];
  48. } else {
  49. FIRMessagingLoggerError(kFIRMessagingServiceExtensionImageInvalidURL,
  50. @"The Image URL provided is invalid %@.", currentImageURL);
  51. [self deliverNotification];
  52. }
  53. #else
  54. [self deliverNotification];
  55. #endif
  56. }
  57. #if TARGET_OS_IOS || TARGET_OS_OSX || TARGET_OS_WATCH
  58. - (NSString *)fileExtensionForResponse:(NSURLResponse *)response {
  59. NSString *suggestedPathExtension = [response.suggestedFilename pathExtension];
  60. if (suggestedPathExtension.length > 0) {
  61. return [NSString stringWithFormat:@".%@", suggestedPathExtension];
  62. }
  63. if ([response.MIMEType containsString:kImagePathPrefix]) {
  64. return [response.MIMEType stringByReplacingOccurrencesOfString:kImagePathPrefix
  65. withString:@"."];
  66. }
  67. return kNoExtension;
  68. }
  69. - (void)loadAttachmentForURL:(NSURL *)attachmentURL
  70. completionHandler:(void (^)(UNNotificationAttachment *))completionHandler {
  71. __block UNNotificationAttachment *attachment = nil;
  72. NSURLSession *session = [NSURLSession
  73. sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
  74. [[session
  75. downloadTaskWithURL:attachmentURL
  76. completionHandler:^(NSURL *temporaryFileLocation, NSURLResponse *response, NSError *error) {
  77. if (error != nil) {
  78. FIRMessagingLoggerError(kFIRMessagingServiceExtensionImageNotDownloaded,
  79. @"Failed to download image given URL %@, error: %@\n",
  80. attachmentURL, error);
  81. completionHandler(attachment);
  82. return;
  83. }
  84. NSFileManager *fileManager = [NSFileManager defaultManager];
  85. NSString *fileExtension = [self fileExtensionForResponse:response];
  86. NSURL *localURL = [NSURL
  87. fileURLWithPath:[temporaryFileLocation.path stringByAppendingString:fileExtension]];
  88. [fileManager moveItemAtURL:temporaryFileLocation toURL:localURL error:&error];
  89. if (error) {
  90. FIRMessagingLoggerError(
  91. kFIRMessagingServiceExtensionLocalFileNotCreated,
  92. @"Failed to move the image file to local location: %@, error: %@\n", localURL,
  93. error);
  94. completionHandler(attachment);
  95. return;
  96. }
  97. attachment = [UNNotificationAttachment attachmentWithIdentifier:@""
  98. URL:localURL
  99. options:nil
  100. error:&error];
  101. if (error) {
  102. FIRMessagingLoggerError(kFIRMessagingServiceExtensionImageNotAttached,
  103. @"Failed to create attachment with URL %@, error: %@\n",
  104. localURL, error);
  105. completionHandler(attachment);
  106. return;
  107. }
  108. completionHandler(attachment);
  109. }] resume];
  110. }
  111. #endif
  112. - (void)deliverNotification {
  113. if (self.contentHandler) {
  114. self.contentHandler(self.bestAttemptContent);
  115. }
  116. }
  117. @end