No Description

GTMSessionUploadFetcher.h 8.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175
  1. /* Copyright 2014 Google Inc. All rights reserved.
  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. */
  15. // GTMSessionUploadFetcher implements Google's resumable upload protocol.
  16. //
  17. // This subclass of GTMSessionFetcher simulates the series of fetches
  18. // needed for chunked upload as a single fetch operation.
  19. //
  20. // Protocol document: TBD
  21. //
  22. // To the client, the only fetcher that exists is this class; the subsidiary
  23. // fetchers needed for uploading chunks are not visible (though the most recent
  24. // chunk fetcher may be accessed via the -activeFetcher or -chunkFetcher methods, and
  25. // -responseHeaders and -statusCode reflect results from the most recent chunk
  26. // fetcher.)
  27. //
  28. // Chunk fetchers are discarded as soon as they have completed.
  29. //
  30. // The protocol also allows for a cancellation notification request to be sent to the
  31. // server to allow discarding of the currently uploaded data and this will be sent
  32. // automatically upon calling stopFetching if the upload has already started.
  33. //
  34. // Note: Unlike the fetcher superclass, the methods of GTMSessionUploadFetcher should
  35. // only be used from the main thread until further work is done to make this subclass
  36. // thread-safe.
  37. #import "GTMSessionFetcher.h"
  38. #import "GTMSessionFetcherService.h"
  39. GTM_ASSUME_NONNULL_BEGIN
  40. // The value to use for file size parameters when the file size is not yet known.
  41. extern int64_t const kGTMSessionUploadFetcherUnknownFileSize;
  42. // Unless an application knows it needs a smaller chunk size, it should use the standard
  43. // chunk size, which sends the entire file as a single chunk to minimize upload overhead.
  44. // Setting an explicit chunk size that comfortably fits in memory is advisable for large
  45. // uploads.
  46. extern int64_t const kGTMSessionUploadFetcherStandardChunkSize;
  47. // When uploading requires data buffer allocations (such as uploading from an NSData or
  48. // an NSFileHandle) this is the maximum buffer size that will be created by the fetcher.
  49. extern int64_t const kGTMSessionUploadFetcherMaximumDemandBufferSize;
  50. // Notification that the upload location URL was provided by the server.
  51. extern NSString *const kGTMSessionFetcherUploadLocationObtainedNotification;
  52. // Block to provide data during uploads.
  53. //
  54. // Response data may be allocated with dataWithBytesNoCopy:length:freeWhenDone: for efficiency,
  55. // and released after the response block returns.
  56. //
  57. // If the length of the file being uploaded is unknown or already set, send
  58. // kGTMSessionUploadFetcherUnknownFileSize for |fullUploadLength|. Otherwise, set |fullUploadLength|
  59. // to its proper value.
  60. //
  61. // Pass nil as the data (and optionally an NSError) for a failure.
  62. typedef void (^GTMSessionUploadFetcherDataProviderResponse)(NSData * GTM_NULLABLE_TYPE data,
  63. int64_t fullUploadLength,
  64. NSError * GTM_NULLABLE_TYPE error);
  65. // Do not call the response with an NSData object with less data than the requested length unless
  66. // you are passing the fullUploadLength to the fetcher for the first time and it is the last chunk
  67. // of data in the file being uploaded.
  68. typedef void (^GTMSessionUploadFetcherDataProvider)(int64_t offset, int64_t length,
  69. GTMSessionUploadFetcherDataProviderResponse response);
  70. // Block to be notified about the final status of the cancellation request started in stopFetching.
  71. //
  72. // |fetcher| will be the cancel request that was sent to the server, or nil if stopFetching is not
  73. // going to send a cancel request. If |fetcher| is provided, the other parameters correspond to the
  74. // completion handler of the cancellation request fetcher.
  75. typedef void (^GTMSessionUploadFetcherCancellationHandler)(
  76. GTMSessionFetcher * GTM_NULLABLE_TYPE fetcher,
  77. NSData * GTM_NULLABLE_TYPE data,
  78. NSError * GTM_NULLABLE_TYPE error);
  79. @interface GTMSessionUploadFetcher : GTMSessionFetcher
  80. // Create an upload fetcher specifying either the request or the resume location URL,
  81. // then set an upload data source using one of these:
  82. //
  83. // setUploadFileURL:
  84. // setUploadDataLength:provider:
  85. // setUploadFileHandle:
  86. // setUploadData:
  87. + (instancetype)uploadFetcherWithRequest:(NSURLRequest *)request
  88. uploadMIMEType:(NSString *)uploadMIMEType
  89. chunkSize:(int64_t)chunkSize
  90. fetcherService:(GTM_NULLABLE GTMSessionFetcherService *)fetcherServiceOrNil;
  91. // Allows cellular access.
  92. + (instancetype)uploadFetcherWithLocation:(NSURL * GTM_NULLABLE_TYPE)uploadLocationURL
  93. uploadMIMEType:(NSString *)uploadMIMEType
  94. chunkSize:(int64_t)chunkSize
  95. fetcherService:(GTM_NULLABLE GTMSessionFetcherService *)fetcherServiceOrNil;
  96. + (instancetype)uploadFetcherWithLocation:(NSURL *GTM_NULLABLE_TYPE)uploadLocationURL
  97. uploadMIMEType:(NSString *)uploadMIMEType
  98. chunkSize:(int64_t)chunkSize
  99. allowsCellularAccess:(BOOL)allowsCellularAccess
  100. fetcherService:(GTM_NULLABLE GTMSessionFetcherService *)fetcherServiceOrNil;
  101. // Allows dataProviders for files of unknown length. Pass kGTMSessionUploadFetcherUnknownFileSize as
  102. // |fullLength| if the length is unknown.
  103. - (void)setUploadDataLength:(int64_t)fullLength
  104. provider:(GTM_NULLABLE GTMSessionUploadFetcherDataProvider)block;
  105. + (NSArray *)uploadFetchersForBackgroundSessions;
  106. + (GTM_NULLABLE instancetype)uploadFetcherForSessionIdentifier:(NSString *)sessionIdentifier;
  107. - (void)pauseFetching;
  108. - (void)resumeFetching;
  109. - (BOOL)isPaused;
  110. @property(atomic, strong, GTM_NULLABLE) NSURL *uploadLocationURL;
  111. @property(atomic, strong, GTM_NULLABLE) NSData *uploadData;
  112. @property(atomic, strong, GTM_NULLABLE) NSURL *uploadFileURL;
  113. @property(atomic, strong, GTM_NULLABLE) NSFileHandle *uploadFileHandle;
  114. @property(atomic, copy, readonly, GTM_NULLABLE) GTMSessionUploadFetcherDataProvider uploadDataProvider;
  115. @property(atomic, copy) NSString *uploadMIMEType;
  116. @property(atomic, assign) int64_t chunkSize;
  117. @property(atomic, readonly, assign) int64_t currentOffset;
  118. // Reflects the original NSURLRequest's @c allowCellularAccess property.
  119. @property(atomic, readonly, assign) BOOL allowsCellularAccess;
  120. // The fetcher for the current data chunk, if any
  121. @property(atomic, strong, GTM_NULLABLE) GTMSessionFetcher *chunkFetcher;
  122. // The active fetcher is the current chunk fetcher, or the upload fetcher itself
  123. // if no chunk fetcher has yet been created.
  124. @property(atomic, readonly) GTMSessionFetcher *activeFetcher;
  125. // The last request made by an active fetcher. Useful for testing.
  126. @property(atomic, readonly, GTM_NULLABLE) NSURLRequest *lastChunkRequest;
  127. // The status code from the most recently-completed fetch.
  128. @property(atomic, assign) NSInteger statusCode;
  129. // Invoked as part of the stop fetching process. Invoked immediately if there is no upload in
  130. // progress, otherwise invoked with the results of the attempt to notify the server that the
  131. // upload will not continue.
  132. //
  133. // Unlike other callbacks, since this is related specifically to the stopFetching flow it is not
  134. // cleared by stopFetching. It will instead clear itself after it is invoked or if the completion
  135. // has occured before stopFetching is called.
  136. @property(atomic, copy, GTM_NULLABLE) GTMSessionUploadFetcherCancellationHandler
  137. cancellationHandler;
  138. // Exposed for testing only.
  139. @property(atomic, readonly, GTM_NULLABLE) dispatch_queue_t delegateCallbackQueue;
  140. @property(atomic, readonly, GTM_NULLABLE) GTMSessionFetcherCompletionHandler delegateCompletionHandler;
  141. @end
  142. @interface GTMSessionFetcher (GTMSessionUploadFetcherMethods)
  143. @property(readonly, GTM_NULLABLE) GTMSessionUploadFetcher *parentUploadFetcher;
  144. @end
  145. GTM_ASSUME_NONNULL_END