FIRStorageTokenAuthorizer.m 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. // Copyright 2017 Google
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. #import "FirebaseStorage/Sources/FIRStorageTokenAuthorizer.h"
  15. #import "FirebaseStorage/Sources/Public/FirebaseStorage/FIRStorage.h"
  16. #import "FirebaseStorage/Sources/Public/FirebaseStorage/FIRStorageConstants.h"
  17. #import "FirebaseStorage/Sources/FIRStorageConstants_Private.h"
  18. #import "FirebaseStorage/Sources/FIRStorageErrors.h"
  19. #import "FirebaseCore/Sources/Private/FirebaseCoreInternal.h"
  20. #import "Interop/Auth/Public/FIRAuthInterop.h"
  21. @implementation FIRStorageTokenAuthorizer {
  22. @private
  23. /// Google App ID to pass along with each request.
  24. NSString *_googleAppID;
  25. /// Auth provider.
  26. id<FIRAuthInterop> _auth;
  27. }
  28. @synthesize fetcherService = _fetcherService;
  29. - (instancetype)initWithGoogleAppID:(NSString *)googleAppID
  30. fetcherService:(GTMSessionFetcherService *)service
  31. authProvider:(nullable id<FIRAuthInterop>)auth {
  32. self = [super init];
  33. if (self) {
  34. _googleAppID = googleAppID;
  35. _fetcherService = service;
  36. _auth = auth;
  37. }
  38. return self;
  39. }
  40. #pragma mark - GTMFetcherAuthorizationProtocol methods
  41. - (void)authorizeRequest:(NSMutableURLRequest *)request
  42. delegate:(id)delegate
  43. didFinishSelector:(SEL)sel {
  44. // Set version header on each request
  45. NSString *versionString = [NSString stringWithFormat:@"ios/%@", FIRFirebaseVersion()];
  46. [request setValue:versionString forHTTPHeaderField:@"x-firebase-storage-version"];
  47. // Set GMP ID on each request
  48. [request setValue:_googleAppID forHTTPHeaderField:@"x-firebase-gmpid"];
  49. if (delegate && sel) {
  50. id selfParam = self;
  51. NSMethodSignature *sig = [delegate methodSignatureForSelector:sel];
  52. NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:sig];
  53. [invocation setSelector:sel];
  54. [invocation setTarget:delegate];
  55. [invocation setArgument:&selfParam atIndex:2];
  56. [invocation setArgument:&request atIndex:3];
  57. dispatch_queue_t callbackQueue = self.fetcherService.callbackQueue;
  58. if (!callbackQueue) {
  59. callbackQueue = dispatch_get_main_queue();
  60. }
  61. [invocation retainArguments];
  62. if (_auth) {
  63. [_auth getTokenForcingRefresh:NO
  64. withCallback:^(NSString *_Nullable token, NSError *_Nullable error) {
  65. if (error) {
  66. NSMutableDictionary *errorDictionary =
  67. [NSMutableDictionary dictionaryWithDictionary:error.userInfo];
  68. errorDictionary[kFIRStorageResponseErrorDomain] = error.domain;
  69. errorDictionary[kFIRStorageResponseErrorCode] = @(error.code);
  70. NSError *tokenError =
  71. [FIRStorageErrors errorWithCode:FIRStorageErrorCodeUnauthenticated
  72. infoDictionary:errorDictionary];
  73. [invocation setArgument:&tokenError atIndex:4];
  74. } else if (token) {
  75. NSString *firebaseToken =
  76. [NSString stringWithFormat:kFIRStorageAuthTokenFormat, token];
  77. [request setValue:firebaseToken forHTTPHeaderField:@"Authorization"];
  78. }
  79. dispatch_async(callbackQueue, ^{
  80. [invocation invoke];
  81. });
  82. }];
  83. } else {
  84. dispatch_async(callbackQueue, ^{
  85. [invocation invoke];
  86. });
  87. }
  88. }
  89. }
  90. // Note that stopAuthorization, isAuthorizingRequest, and userEmail
  91. // aren't relevant with the Firebase App/Auth implementation of tokens,
  92. // and thus aren't implemented. Token refresh is handled transparently
  93. // for us, and we don't allow the auth request to be stopped.
  94. // Auth is also not required so the world doesn't stop.
  95. - (void)stopAuthorization {
  96. // Noop
  97. }
  98. - (void)stopAuthorizationForRequest:(NSURLRequest *)request {
  99. // Noop
  100. }
  101. - (BOOL)isAuthorizingRequest:(NSURLRequest *)request {
  102. return NO;
  103. }
  104. - (BOOL)isAuthorizedRequest:(NSURLRequest *)request {
  105. NSString *authHeader = request.allHTTPHeaderFields[@"Authorization"];
  106. BOOL isFirebaseToken = [authHeader hasPrefix:@"Firebase"];
  107. return isFirebaseToken;
  108. }
  109. - (NSString *)userEmail {
  110. // Noop
  111. return nil;
  112. }
  113. @end