Merge pull request #2261 from dreampiggy/feature_request_modifier_and_response
Feature request modifier and response
This commit is contained in:
commit
2cb03773db
|
@ -453,6 +453,18 @@
|
|||
32EB6D90206D132E005CAEF6 /* SDAnimatedImageRep.m in Sources */ = {isa = PBXBuildFile; fileRef = 320224BA203979BA00E9F285 /* SDAnimatedImageRep.m */; };
|
||||
32EB6D91206D132E005CAEF6 /* SDAnimatedImageRep.m in Sources */ = {isa = PBXBuildFile; fileRef = 320224BA203979BA00E9F285 /* SDAnimatedImageRep.m */; };
|
||||
32EB6D92206D132E005CAEF6 /* SDAnimatedImageRep.m in Sources */ = {isa = PBXBuildFile; fileRef = 320224BA203979BA00E9F285 /* SDAnimatedImageRep.m */; };
|
||||
32F21B5120788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5220788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5320788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5420788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5520788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5620788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F21B5720788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F21B5820788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F21B5920788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F21B5A20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F21B5B20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F21B5C20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */ = {isa = PBXBuildFile; fileRef = 32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */; };
|
||||
32F7C06F2030114C00873181 /* SDWebImageTransformer.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F7C06D2030114C00873181 /* SDWebImageTransformer.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F7C0702030114C00873181 /* SDWebImageTransformer.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F7C06D2030114C00873181 /* SDWebImageTransformer.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
32F7C0712030114C00873181 /* SDWebImageTransformer.h in Headers */ = {isa = PBXBuildFile; fileRef = 32F7C06D2030114C00873181 /* SDWebImageTransformer.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
|
@ -1490,6 +1502,8 @@
|
|||
32C0FDE02013426C001B8F2D /* SDWebImageIndicator.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = SDWebImageIndicator.m; sourceTree = "<group>"; };
|
||||
32CF1C051FA496B000004BD1 /* SDWebImageCoderHelper.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SDWebImageCoderHelper.h; sourceTree = "<group>"; };
|
||||
32CF1C061FA496B000004BD1 /* SDWebImageCoderHelper.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = SDWebImageCoderHelper.m; sourceTree = "<group>"; };
|
||||
32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SDWebImageDownloaderRequestModifier.h; sourceTree = "<group>"; };
|
||||
32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = SDWebImageDownloaderRequestModifier.m; sourceTree = "<group>"; };
|
||||
32F7C06D2030114C00873181 /* SDWebImageTransformer.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SDWebImageTransformer.h; sourceTree = "<group>"; };
|
||||
32F7C06E2030114C00873181 /* SDWebImageTransformer.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = SDWebImageTransformer.m; sourceTree = "<group>"; };
|
||||
32F7C07C2030719600873181 /* UIImage+Transform.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "UIImage+Transform.m"; sourceTree = "<group>"; };
|
||||
|
@ -1984,6 +1998,8 @@
|
|||
530E49E416460AE2002868E7 /* SDWebImageDownloaderOperation.m */,
|
||||
32B9B535206ED4230026769D /* SDWebImageDownloaderConfig.h */,
|
||||
32B9B536206ED4230026769D /* SDWebImageDownloaderConfig.m */,
|
||||
32F21B4F20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h */,
|
||||
32F21B5020788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m */,
|
||||
);
|
||||
name = Downloader;
|
||||
sourceTree = "<group>";
|
||||
|
@ -2196,6 +2212,7 @@
|
|||
323F8BE71F38EF770092B609 /* vp8li_enc.h in Headers */,
|
||||
329A185C1FFF5DFD008C9A2F /* UIImage+WebCache.h in Headers */,
|
||||
4369C27A1D9807EC007E863A /* UIView+WebCache.h in Headers */,
|
||||
32F21B5420788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
80377DCC1F2F66A700F89830 /* lossless_common.h in Headers */,
|
||||
321E60971F38E8ED00405457 /* SDWebImageImageIOCoder.h in Headers */,
|
||||
43A918671D8308FE00B3925F /* SDImageCacheConfig.h in Headers */,
|
||||
|
@ -2332,6 +2349,7 @@
|
|||
80377C191F2F666300F89830 /* endian_inl_utils.h in Headers */,
|
||||
321E60A31F38E8F600405457 /* SDWebImageGIFCoder.h in Headers */,
|
||||
4314D17C1D0E0E3B004B36C9 /* UIImage+WebP.h in Headers */,
|
||||
32F21B5220788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
4369C2781D9807EC007E863A /* UIView+WebCache.h in Headers */,
|
||||
80377D621F2F66A700F89830 /* yuv.h in Headers */,
|
||||
80377D341F2F66A700F89830 /* dsp.h in Headers */,
|
||||
|
@ -2427,6 +2445,7 @@
|
|||
43A62A1E1D0E0A800089D7DD /* format_constants.h in Headers */,
|
||||
80377E111F2F66A800F89830 /* lossless_common.h in Headers */,
|
||||
431BB6F61D06D2C1006A3455 /* UIImage+MultiFormat.h in Headers */,
|
||||
32F21B5520788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
807A122C1F89636300EC2A9B /* SDWebImageCodersManager.h in Headers */,
|
||||
323F8BFA1F38EF770092B609 /* animi.h in Headers */,
|
||||
431BB6F91D06D2C1006A3455 /* UIImage+GIF.h in Headers */,
|
||||
|
@ -2460,6 +2479,7 @@
|
|||
4397D2BD1D0DDD8C00BB2784 /* types.h in Headers */,
|
||||
4397D2C01D0DDD8C00BB2784 /* SDWebImage.h in Headers */,
|
||||
4397D2C11D0DDD8C00BB2784 /* format_constants.h in Headers */,
|
||||
32F21B5620788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
80377C8D1F2F666400F89830 /* random_utils.h in Headers */,
|
||||
4397D2C31D0DDD8C00BB2784 /* SDWebImageManager.h in Headers */,
|
||||
323F8B551F38EF770092B609 /* backward_references_enc.h in Headers */,
|
||||
|
@ -2551,6 +2571,7 @@
|
|||
323F8BE61F38EF770092B609 /* vp8li_enc.h in Headers */,
|
||||
329A185B1FFF5DFD008C9A2F /* UIImage+WebCache.h in Headers */,
|
||||
4369C2791D9807EC007E863A /* UIView+WebCache.h in Headers */,
|
||||
32F21B5320788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
80377D871F2F66A700F89830 /* lossless_common.h in Headers */,
|
||||
321E60961F38E8ED00405457 /* SDWebImageImageIOCoder.h in Headers */,
|
||||
4A2CAE041AB4BB5400B6BC39 /* SDWebImage.h in Headers */,
|
||||
|
@ -2663,6 +2684,7 @@
|
|||
5376131A155AD0D5005750A4 /* SDWebImageDownloader.h in Headers */,
|
||||
4369C2771D9807EC007E863A /* UIView+WebCache.h in Headers */,
|
||||
80377CEF1F2F66A100F89830 /* dsp.h in Headers */,
|
||||
32F21B5120788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.h in Headers */,
|
||||
80377C011F2F665300F89830 /* filters_utils.h in Headers */,
|
||||
5376131C155AD0D5005750A4 /* SDWebImageManager.h in Headers */,
|
||||
438096741CDFC09C00DC626B /* UIImage+WebP.h in Headers */,
|
||||
|
@ -2977,6 +2999,7 @@
|
|||
80377DEB1F2F66A700F89830 /* yuv.c in Sources */,
|
||||
3237F9E920161AE000A88143 /* NSImage+Additions.m in Sources */,
|
||||
32C0FDEA2013426C001B8F2D /* SDWebImageIndicator.m in Sources */,
|
||||
32F21B5A20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
00733A551BC4880000A5A117 /* SDWebImageDownloader.m in Sources */,
|
||||
80377EB71F2F66D400F89830 /* alpha_dec.c in Sources */,
|
||||
80377DC61F2F66A700F89830 /* enc.c in Sources */,
|
||||
|
@ -3165,6 +3188,7 @@
|
|||
80377D5F1F2F66A700F89830 /* yuv_mips32.c in Sources */,
|
||||
80377D3C1F2F66A700F89830 /* enc.c in Sources */,
|
||||
4314D13B1D0E0E3B004B36C9 /* UIButton+WebCache.m in Sources */,
|
||||
32F21B5820788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
321E60C51F38E91700405457 /* UIImage+ForceDecode.m in Sources */,
|
||||
80377D461F2F66A700F89830 /* lossless_enc_neon.c in Sources */,
|
||||
80377E9B1F2F66D400F89830 /* frame_dec.c in Sources */,
|
||||
|
@ -3321,6 +3345,7 @@
|
|||
80377E2E1F2F66A800F89830 /* yuv_mips32.c in Sources */,
|
||||
80377E0B1F2F66A800F89830 /* enc.c in Sources */,
|
||||
431BB6AC1D06D2C1006A3455 /* SDWebImageCompat.m in Sources */,
|
||||
32F21B5B20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
80377E151F2F66A800F89830 /* lossless_enc_neon.c in Sources */,
|
||||
321E60C81F38E91700405457 /* UIImage+ForceDecode.m in Sources */,
|
||||
80377C721F2F666400F89830 /* random_utils.c in Sources */,
|
||||
|
@ -3475,6 +3500,7 @@
|
|||
323F8BF51F38EF770092B609 /* anim_encode.c in Sources */,
|
||||
80377E381F2F66A800F89830 /* argb_sse2.c in Sources */,
|
||||
323F8B9B1F38EF770092B609 /* near_lossless_enc.c in Sources */,
|
||||
32F21B5C20788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
80377E3B1F2F66A800F89830 /* cost_mips_dsp_r2.c in Sources */,
|
||||
4397D29B1D0DDD8C00BB2784 /* SDWebImageDownloader.m in Sources */,
|
||||
80377E711F2F66A800F89830 /* upsampling.c in Sources */,
|
||||
|
@ -3607,6 +3633,7 @@
|
|||
43CE757A1CFE9427006C64D0 /* FLAnimatedImage.m in Sources */,
|
||||
3237F9E820161AE000A88143 /* NSImage+Additions.m in Sources */,
|
||||
32C0FDE92013426C001B8F2D /* SDWebImageIndicator.m in Sources */,
|
||||
32F21B5920788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
80377D811F2F66A700F89830 /* enc.c in Sources */,
|
||||
80377EA71F2F66D400F89830 /* alpha_dec.c in Sources */,
|
||||
80377D8F1F2F66A700F89830 /* lossless_mips_dsp_r2.c in Sources */,
|
||||
|
@ -3767,6 +3794,7 @@
|
|||
80377CF71F2F66A100F89830 /* enc.c in Sources */,
|
||||
3237F9EB20161AE000A88143 /* NSImage+Additions.m in Sources */,
|
||||
32C0FDE72013426C001B8F2D /* SDWebImageIndicator.m in Sources */,
|
||||
32F21B5720788D8C0036B1D5 /* SDWebImageDownloaderRequestModifier.m in Sources */,
|
||||
80377E871F2F66D000F89830 /* alpha_dec.c in Sources */,
|
||||
80377D051F2F66A100F89830 /* lossless_mips_dsp_r2.c in Sources */,
|
||||
80377C0A1F2F665300F89830 /* random_utils.c in Sources */,
|
||||
|
|
|
@ -199,3 +199,8 @@ FOUNDATION_EXPORT SDWebImageContextOption _Nonnull const SDWebImageContextImageS
|
|||
This can be used to improve animated images rendering performance (especially memory usage on big animated images) with `SDAnimatedImageView` (Class).
|
||||
*/
|
||||
FOUNDATION_EXPORT SDWebImageContextOption _Nonnull const SDWebImageContextAnimatedImageClass;
|
||||
|
||||
/**
|
||||
A id<SDWebImageDownloaderRequestModifier> instance to modify the image download request. It's used for downloader to modify the original request from URL and options. If you provide one, it will ignore the `requestModifier` in downloader and use provided one instead. (id<SDWebImageDownloaderRequestModifier>)
|
||||
*/
|
||||
FOUNDATION_EXPORT SDWebImageContextOption _Nonnull const SDWebImageContextDownloadRequestModifier;
|
||||
|
|
|
@ -122,3 +122,4 @@ SDWebImageContextOption const SDWebImageContextCustomManager = @"customManager";
|
|||
SDWebImageContextOption const SDWebImageContextCustomTransformer = @"customTransformer";
|
||||
SDWebImageContextOption const SDWebImageContextImageScaleFactor = @"imageScaleFactor";
|
||||
SDWebImageContextOption const SDWebImageContextAnimatedImageClass = @"animatedImageClass";
|
||||
SDWebImageContextOption const SDWebImageContextDownloadRequestModifier = @"downloadRequestModifier";
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
#import "SDWebImageDefine.h"
|
||||
#import "SDWebImageOperation.h"
|
||||
#import "SDWebImageDownloaderConfig.h"
|
||||
#import "SDWebImageDownloaderRequestModifier.h"
|
||||
|
||||
typedef NS_OPTIONS(NSUInteger, SDWebImageDownloaderOptions) {
|
||||
/**
|
||||
|
@ -81,11 +82,6 @@ typedef void(^SDWebImageDownloaderProgressBlock)(NSInteger receivedSize, NSInteg
|
|||
|
||||
typedef void(^SDWebImageDownloaderCompletedBlock)(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, BOOL finished);
|
||||
|
||||
typedef NSDictionary<NSString *, NSString *> SDHTTPHeadersDictionary;
|
||||
typedef NSMutableDictionary<NSString *, NSString *> SDHTTPHeadersMutableDictionary;
|
||||
|
||||
typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterBlock)(NSURL * _Nullable url, SDHTTPHeadersDictionary * _Nullable headers);
|
||||
|
||||
/**
|
||||
* A token associated with each download. Can be used to cancel a download
|
||||
*/
|
||||
|
@ -101,6 +97,16 @@ typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterB
|
|||
*/
|
||||
@property (nonatomic, strong, nullable, readonly) NSURL *url;
|
||||
|
||||
/**
|
||||
The download's request.
|
||||
*/
|
||||
@property (nonatomic, copy, nullable, readonly) NSURLRequest *request;
|
||||
|
||||
/**
|
||||
The download's response.
|
||||
*/
|
||||
@property (nonatomic, copy, nullable, readonly) NSURLResponse *response;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
|
@ -116,12 +122,12 @@ typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterB
|
|||
@property (nonatomic, copy, readonly, nonnull) SDWebImageDownloaderConfig *config;
|
||||
|
||||
/**
|
||||
* Set filter to pick headers for downloading image HTTP request.
|
||||
*
|
||||
* This block will be invoked for each downloading image request, returned
|
||||
* NSDictionary will be used as headers in corresponding HTTP request.
|
||||
* Set the request modifier to modify the original download request before image load.
|
||||
* This request modifier method will be called for each downloading image request. Return the original request means no modication. Return nil will cancel the download request.
|
||||
* Defaults to nil, means does not modify the original download request.
|
||||
* @note If you want to modify single request, consider using `SDWebImageContextDownloadRequestModifier` context option.
|
||||
*/
|
||||
@property (nonatomic, copy, nullable) SDWebImageDownloaderHeadersFilterBlock headersFilter;
|
||||
@property (nonatomic, strong, nullable) id<SDWebImageDownloaderRequestModifier> requestModifier;
|
||||
|
||||
/**
|
||||
* The configuration in use by the internal NSURLSession. If you want to provide a custom sessionConfiguration, use `SDWebImageDownloaderConfig.sessionConfiguration` and create a new downloader instance.
|
||||
|
@ -188,7 +194,7 @@ typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterB
|
|||
* before to be called a last time with the full image and finished argument
|
||||
* set to YES. In case of error, the finished argument is always YES.
|
||||
*
|
||||
* @return A token (SDWebImageDownloadToken) that can be passed to -cancel: to cancel this operation
|
||||
* @return A token (SDWebImageDownloadToken) that can be used to cancel this operation
|
||||
*/
|
||||
- (nullable SDWebImageDownloadToken *)downloadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageDownloaderOptions)options
|
||||
|
@ -209,7 +215,7 @@ typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterB
|
|||
* @note the progress block is executed on a background queue
|
||||
* @param completedBlock A block called once the download is completed.
|
||||
*
|
||||
* @return A token (SDWebImageDownloadToken) that can be passed to -cancel: to cancel this operation
|
||||
* @return A token (SDWebImageDownloadToken) that can be used to cancel this operation
|
||||
*/
|
||||
- (nullable SDWebImageDownloadToken *)downloadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageDownloaderOptions)options
|
||||
|
@ -217,13 +223,6 @@ typedef SDHTTPHeadersDictionary * _Nullable (^SDWebImageDownloaderHeadersFilterB
|
|||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nullable SDWebImageDownloaderCompletedBlock)completedBlock;
|
||||
|
||||
/**
|
||||
* Cancels a download that was previously queued using -downloadImageWithURL:options:progress:completed:
|
||||
*
|
||||
* @param token The token received from -downloadImageWithURL:options:progress:completed: that should be canceled.
|
||||
*/
|
||||
- (void)cancel:(nullable SDWebImageDownloadToken *)token;
|
||||
|
||||
/**
|
||||
* Cancels all download operations in the queue
|
||||
*/
|
||||
|
|
|
@ -18,6 +18,8 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
@interface SDWebImageDownloadToken ()
|
||||
|
||||
@property (nonatomic, strong, nullable, readwrite) NSURL *url;
|
||||
@property (nonatomic, copy, nullable, readwrite) NSURLRequest *request;
|
||||
@property (nonatomic, copy, nullable, readwrite) NSURLResponse *response;
|
||||
@property (nonatomic, strong, nullable, readwrite) id downloadOperationCancelToken;
|
||||
@property (nonatomic, weak, nullable) NSOperation<SDWebImageDownloaderOperation> *downloadOperation;
|
||||
@property (nonatomic, weak, nullable) SDWebImageDownloader *downloader;
|
||||
|
@ -25,15 +27,13 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
|
||||
@end
|
||||
|
||||
|
||||
@interface SDWebImageDownloader () <NSURLSessionTaskDelegate, NSURLSessionDataDelegate>
|
||||
|
||||
@property (strong, nonatomic, nonnull) NSOperationQueue *downloadQueue;
|
||||
@property (weak, nonatomic, nullable) NSOperation *lastAddedOperation;
|
||||
@property (strong, nonatomic, nonnull) NSMutableDictionary<NSURL *, NSOperation<SDWebImageDownloaderOperation> *> *URLOperations;
|
||||
@property (strong, nonatomic, nullable) SDHTTPHeadersMutableDictionary *HTTPHeaders;
|
||||
@property (copy, atomic, nullable) NSDictionary<NSString *, NSString *> *HTTPHeaders; // Since modify this value is rare, use immutable object can enhance performance. But should mark as atomic to keep thread-safe
|
||||
@property (strong, nonatomic, nonnull) dispatch_semaphore_t operationsLock; // a lock to keep the access to `URLOperations` thread-safe
|
||||
@property (strong, nonatomic, nonnull) dispatch_semaphore_t headersLock; // a lock to keep the access to `HTTPHeaders` thread-safe
|
||||
|
||||
// The session in which data tasks will run
|
||||
@property (strong, nonatomic) NSURLSession *session;
|
||||
|
@ -91,12 +91,11 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
_downloadQueue.name = @"com.hackemist.SDWebImageDownloader";
|
||||
_URLOperations = [NSMutableDictionary new];
|
||||
#ifdef SD_WEBP
|
||||
_HTTPHeaders = [@{@"Accept": @"image/webp,image/*;q=0.8"} mutableCopy];
|
||||
_HTTPHeaders = @{@"Accept": @"image/webp,image/*;q=0.8"};
|
||||
#else
|
||||
_HTTPHeaders = [@{@"Accept": @"image/*;q=0.8"} mutableCopy];
|
||||
_HTTPHeaders = @{@"Accept": @"image/*;q=0.8"};
|
||||
#endif
|
||||
_operationsLock = dispatch_semaphore_create(1);
|
||||
_headersLock = dispatch_semaphore_create(1);
|
||||
NSURLSessionConfiguration *sessionConfiguration = _config.sessionConfiguration;
|
||||
if (!sessionConfiguration) {
|
||||
sessionConfiguration = [NSURLSessionConfiguration defaultSessionConfiguration];
|
||||
|
@ -133,27 +132,20 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
}
|
||||
|
||||
- (void)setValue:(nullable NSString *)value forHTTPHeaderField:(nullable NSString *)field {
|
||||
LOCK(self.headersLock);
|
||||
NSMutableDictionary *mutableHTTPHeaders = [self.HTTPHeaders mutableCopy];
|
||||
if (value) {
|
||||
self.HTTPHeaders[field] = value;
|
||||
[mutableHTTPHeaders setObject:value forKey:field];
|
||||
} else {
|
||||
[self.HTTPHeaders removeObjectForKey:field];
|
||||
[mutableHTTPHeaders removeObjectForKey:field];
|
||||
}
|
||||
UNLOCK(self.headersLock);
|
||||
self.HTTPHeaders = [mutableHTTPHeaders copy];
|
||||
}
|
||||
|
||||
- (nullable NSString *)valueForHTTPHeaderField:(nullable NSString *)field {
|
||||
if (!field) {
|
||||
return nil;
|
||||
}
|
||||
return [[self allHTTPHeaderFields] objectForKey:field];
|
||||
}
|
||||
|
||||
- (nonnull SDHTTPHeadersDictionary *)allHTTPHeaderFields {
|
||||
LOCK(self.headersLock);
|
||||
SDHTTPHeadersDictionary *allHTTPHeaderFields = [self.HTTPHeaders copy];
|
||||
UNLOCK(self.headersLock);
|
||||
return allHTTPHeaderFields;
|
||||
return [self.HTTPHeaders objectForKey:field];
|
||||
}
|
||||
|
||||
- (nullable SDWebImageDownloadToken *)downloadImageWithURL:(NSURL *)url options:(SDWebImageDownloaderOptions)options progress:(SDWebImageDownloaderProgressBlock)progressBlock completed:(SDWebImageDownloaderCompletedBlock)completedBlock {
|
||||
|
@ -176,17 +168,28 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
|
||||
// In order to prevent from potential duplicate caching (NSURLCache + SDImageCache) we disable the cache for image requests if told otherwise
|
||||
NSURLRequestCachePolicy cachePolicy = options & SDWebImageDownloaderUseNSURLCache ? NSURLRequestUseProtocolCachePolicy : NSURLRequestReloadIgnoringLocalCacheData;
|
||||
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url
|
||||
cachePolicy:cachePolicy
|
||||
timeoutInterval:timeoutInterval];
|
||||
|
||||
request.HTTPShouldHandleCookies = (options & SDWebImageDownloaderHandleCookies);
|
||||
request.HTTPShouldUsePipelining = YES;
|
||||
if (sself.headersFilter) {
|
||||
request.allHTTPHeaderFields = sself.headersFilter(url, [sself allHTTPHeaderFields]);
|
||||
NSMutableURLRequest *mutableRequest = [[NSMutableURLRequest alloc] initWithURL:url cachePolicy:cachePolicy timeoutInterval:timeoutInterval];
|
||||
mutableRequest.HTTPShouldHandleCookies = (options & SDWebImageDownloaderHandleCookies);
|
||||
mutableRequest.HTTPShouldUsePipelining = YES;
|
||||
mutableRequest.allHTTPHeaderFields = sself.HTTPHeaders;
|
||||
id<SDWebImageDownloaderRequestModifier> requestModifier;
|
||||
if ([context valueForKey:SDWebImageContextDownloadRequestModifier]) {
|
||||
requestModifier = [context valueForKey:SDWebImageContextDownloadRequestModifier];
|
||||
} else {
|
||||
requestModifier = self.requestModifier;
|
||||
}
|
||||
else {
|
||||
request.allHTTPHeaderFields = [sself allHTTPHeaderFields];
|
||||
|
||||
NSURLRequest *request;
|
||||
if (requestModifier) {
|
||||
NSURLRequest *modifiedRequest = [requestModifier modifiedRequestWithRequest:[mutableRequest copy]];
|
||||
// If modified request is nil, early return
|
||||
if (!modifiedRequest) {
|
||||
return nil;
|
||||
} else {
|
||||
request = [modifiedRequest copy];
|
||||
}
|
||||
} else {
|
||||
request = [mutableRequest copy];
|
||||
}
|
||||
Class operationClass = sself.config.operationClass;
|
||||
if (operationClass && [operationClass isSubclassOfClass:[NSOperation class]] && [operationClass conformsToProtocol:@protocol(SDWebImageDownloaderOperation)]) {
|
||||
|
@ -241,8 +244,9 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
createCallback:(NSOperation<SDWebImageDownloaderOperation> *(^)(void))createCallback {
|
||||
// The URL will be used as the key to the callbacks dictionary so it cannot be nil. If it is nil immediately call the completed block with no image or data.
|
||||
if (url == nil) {
|
||||
if (completedBlock != nil) {
|
||||
completedBlock(nil, nil, nil, NO);
|
||||
if (completedBlock) {
|
||||
NSError *error = [NSError errorWithDomain:SDWebImageErrorDomain code:-1 userInfo:@{NSLocalizedDescriptionKey : @"Trying to download a nil url"}];
|
||||
completedBlock(nil, nil, error, YES);
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
@ -251,6 +255,14 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
NSOperation<SDWebImageDownloaderOperation> *operation = [self.URLOperations objectForKey:url];
|
||||
if (!operation) {
|
||||
operation = createCallback();
|
||||
if (!operation) {
|
||||
UNLOCK(self.operationsLock);
|
||||
if (completedBlock) {
|
||||
NSError *error = [NSError errorWithDomain:SDWebImageErrorDomain code:-1 userInfo:@{NSLocalizedDescriptionKey : @"Downloader operation is nil"}];
|
||||
completedBlock(nil, nil, error, YES);
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
__weak typeof(self) wself = self;
|
||||
operation.completionBlock = ^{
|
||||
__strong typeof(wself) sself = wself;
|
||||
|
@ -273,6 +285,7 @@ static void * SDWebImageDownloaderContext = &SDWebImageDownloaderContext;
|
|||
SDWebImageDownloadToken *token = [SDWebImageDownloadToken new];
|
||||
token.downloadOperation = operation;
|
||||
token.url = url;
|
||||
token.request = operation.request;
|
||||
token.downloadOperationCancelToken = downloadOperationCancelToken;
|
||||
token.downloader = self;
|
||||
|
||||
|
@ -412,6 +425,25 @@ didReceiveResponse:(NSURLResponse *)response
|
|||
|
||||
@implementation SDWebImageDownloadToken
|
||||
|
||||
- (void)dealloc {
|
||||
[[NSNotificationCenter defaultCenter] removeObserver:self name:SDWebImageDownloadReceiveResponseNotification object:nil];
|
||||
}
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (self) {
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(downloadReceiveResponse:) name:SDWebImageDownloadReceiveResponseNotification object:nil];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)downloadReceiveResponse:(NSNotification *)notification {
|
||||
NSOperation<SDWebImageDownloaderOperation> *downloadOperation = notification.object;
|
||||
if (downloadOperation && downloadOperation == self.downloadOperation) {
|
||||
self.response = downloadOperation.response;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)cancel {
|
||||
@synchronized (self) {
|
||||
if (self.isCancelled) {
|
||||
|
|
|
@ -93,11 +93,6 @@ FOUNDATION_EXPORT NSString * _Nonnull const SDWebImageDownloadFinishNotification
|
|||
*/
|
||||
@property (copy, nonatomic, readonly, nullable) SDWebImageContext *context;
|
||||
|
||||
/**
|
||||
* The expected size of data.
|
||||
*/
|
||||
@property (assign, nonatomic, readonly) NSInteger expectedSize;
|
||||
|
||||
/**
|
||||
* Initializes a `SDWebImageDownloaderOperation` object
|
||||
*
|
||||
|
|
|
@ -46,7 +46,7 @@ typedef NSMutableDictionary<NSString *, id> SDCallbacksDictionary;
|
|||
@property (strong, nonatomic, nullable) NSMutableData *imageData;
|
||||
@property (copy, nonatomic, nullable) NSData *cachedData; // for `SDWebImageDownloaderIgnoreCachedResponse`
|
||||
@property (copy, nonatomic, nullable) NSString *cacheKey;
|
||||
@property (assign, nonatomic, readwrite) NSInteger expectedSize;
|
||||
@property (assign, nonatomic, readwrite) long long expectedSize;
|
||||
@property (strong, nonatomic, nullable, readwrite) NSURLResponse *response;
|
||||
|
||||
// This is weak because it is injected by whoever manages this session. If this gets nil-ed out, we won't be able to run
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
/*
|
||||
* This file is part of the SDWebImage package.
|
||||
* (c) Olivier Poitrey <rs@dailymotion.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import "SDWebImageCompat.h"
|
||||
|
||||
typedef NSURLRequest * _Nullable (^SDWebImageDownloaderRequestModifierBlock)(NSURLRequest * _Nonnull request);
|
||||
|
||||
@protocol SDWebImageDownloaderRequestModifier <NSObject>
|
||||
|
||||
- (nullable NSURLRequest *)modifiedRequestWithRequest:(nonnull NSURLRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
@interface SDWebImageDownloaderRequestModifier : NSObject <SDWebImageDownloaderRequestModifier>
|
||||
|
||||
- (nonnull instancetype)initWithBlock:(nonnull SDWebImageDownloaderRequestModifierBlock)block;
|
||||
+ (nonnull instancetype)requestModifierWithBlock:(nonnull SDWebImageDownloaderRequestModifierBlock)block;
|
||||
|
||||
@end
|
|
@ -0,0 +1,39 @@
|
|||
/*
|
||||
* This file is part of the SDWebImage package.
|
||||
* (c) Olivier Poitrey <rs@dailymotion.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
#import "SDWebImageDownloaderRequestModifier.h"
|
||||
|
||||
@interface SDWebImageDownloaderRequestModifier ()
|
||||
|
||||
@property (nonatomic, copy, nonnull) SDWebImageDownloaderRequestModifierBlock block;
|
||||
|
||||
@end
|
||||
|
||||
@implementation SDWebImageDownloaderRequestModifier
|
||||
|
||||
- (instancetype)initWithBlock:(SDWebImageDownloaderRequestModifierBlock)block {
|
||||
self = [super init];
|
||||
if (self) {
|
||||
self.block = block;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
+ (instancetype)requestModifierWithBlock:(SDWebImageDownloaderRequestModifierBlock)block {
|
||||
SDWebImageDownloaderRequestModifier *requestModifier = [[SDWebImageDownloaderRequestModifier alloc] initWithBlock:block];
|
||||
return requestModifier;
|
||||
}
|
||||
|
||||
- (NSURLRequest *)modifiedRequestWithRequest:(NSURLRequest *)request {
|
||||
if (!self.block) {
|
||||
return nil;
|
||||
}
|
||||
return self.block(request);
|
||||
}
|
||||
|
||||
@end
|
|
@ -20,6 +20,26 @@ typedef NSString * _Nullable(^SDWebImageCacheKeyFilterBlock)(NSURL * _Nullable u
|
|||
|
||||
typedef NSData * _Nullable(^SDWebImageCacheSerializerBlock)(UIImage * _Nonnull image, NSData * _Nullable data, NSURL * _Nullable imageURL);
|
||||
|
||||
// A combined operation representing the cache and download operation. You can it to cancel the load process.
|
||||
@interface SDWebImageCombinedOperation : NSObject <SDWebImageOperation>
|
||||
|
||||
/**
|
||||
Cancel the current operation, including cache and download process
|
||||
*/
|
||||
- (void)cancel;
|
||||
|
||||
/**
|
||||
The cache operation used for image cache query
|
||||
*/
|
||||
@property (strong, nonatomic, nullable, readonly) id<SDWebImageOperation> cacheOperation;
|
||||
|
||||
/**
|
||||
The download operation if the image is download from the network
|
||||
*/
|
||||
@property (strong, nonatomic, nullable, readonly) id<SDWebImageOperation> downloadOperation;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@class SDWebImageManager;
|
||||
|
||||
|
@ -173,12 +193,12 @@ SDWebImageManager.sharedManager.cacheKeyFilter = ^(NSURL * _Nullable url) {
|
|||
*
|
||||
* The last parameter is the original image URL
|
||||
*
|
||||
* @return Returns an NSObject conforming to SDWebImageOperation. Should be an instance of SDWebImageDownloaderOperation
|
||||
* @return Returns an instance of SDWebImageCombinedOperation, which you can cancel the loading process.
|
||||
*/
|
||||
- (nullable id <SDWebImageOperation>)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock;
|
||||
- (nullable SDWebImageCombinedOperation *)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock;
|
||||
|
||||
/**
|
||||
* Downloads the image at the given URL if not present in cache or return the cached version otherwise.
|
||||
|
@ -190,13 +210,13 @@ SDWebImageManager.sharedManager.cacheKeyFilter = ^(NSURL * _Nullable url) {
|
|||
* @note the progress block is executed on a background queue
|
||||
* @param completedBlock A block called when operation has been completed.
|
||||
*
|
||||
* @return Returns an NSObject conforming to SDWebImageOperation. Should be an instance of SDWebImageDownloaderOperation
|
||||
* @return Returns an instance of SDWebImageCombinedOperation, which you can cancel the loading process.
|
||||
*/
|
||||
- (nullable id <SDWebImageOperation>)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
context:(nullable SDWebImageContext *)context
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock;
|
||||
- (nullable SDWebImageCombinedOperation *)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
context:(nullable SDWebImageContext *)context
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock;
|
||||
|
||||
/**
|
||||
* Saves image to cache for given URL
|
||||
|
|
|
@ -11,11 +11,11 @@
|
|||
#import "UIImage+WebCache.h"
|
||||
#import "SDAnimatedImage.h"
|
||||
|
||||
@interface SDWebImageCombinedOperation : NSObject <SDWebImageOperation>
|
||||
@interface SDWebImageCombinedOperation ()
|
||||
|
||||
@property (assign, nonatomic, getter = isCancelled) BOOL cancelled;
|
||||
@property (strong, nonatomic, nullable) SDWebImageDownloadToken *downloadToken;
|
||||
@property (strong, nonatomic, nullable) NSOperation *cacheOperation;
|
||||
@property (strong, nonatomic, readwrite, nullable) id<SDWebImageOperation> downloadOperation;
|
||||
@property (strong, nonatomic, readwrite, nullable) id<SDWebImageOperation> cacheOperation;
|
||||
@property (weak, nonatomic, nullable) SDWebImageManager *manager;
|
||||
|
||||
@end
|
||||
|
@ -108,15 +108,15 @@
|
|||
}];
|
||||
}
|
||||
|
||||
- (id<SDWebImageOperation>)loadImageWithURL:(NSURL *)url options:(SDWebImageOptions)options progress:(SDWebImageDownloaderProgressBlock)progressBlock completed:(SDInternalCompletionBlock)completedBlock {
|
||||
- (SDWebImageCombinedOperation *)loadImageWithURL:(NSURL *)url options:(SDWebImageOptions)options progress:(SDWebImageDownloaderProgressBlock)progressBlock completed:(SDInternalCompletionBlock)completedBlock {
|
||||
return [self loadImageWithURL:url options:options context:nil progress:progressBlock completed:completedBlock];
|
||||
}
|
||||
|
||||
- (id<SDWebImageOperation>)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
context:(nullable SDWebImageContext *)context
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock {
|
||||
- (SDWebImageCombinedOperation *)loadImageWithURL:(nullable NSURL *)url
|
||||
options:(SDWebImageOptions)options
|
||||
context:(nullable SDWebImageContext *)context
|
||||
progress:(nullable SDWebImageDownloaderProgressBlock)progressBlock
|
||||
completed:(nonnull SDInternalCompletionBlock)completedBlock {
|
||||
// Invoking this method without a completedBlock is pointless
|
||||
NSAssert(completedBlock != nil, @"If you mean to prefetch the image, use -[SDWebImagePrefetcher prefetchURLs] instead");
|
||||
|
||||
|
@ -216,7 +216,7 @@
|
|||
|
||||
// `SDWebImageCombinedOperation` -> `SDWebImageDownloadToken` -> `downloadOperationCancelToken`, which is a `SDCallbacksDictionary` and retain the completed block below, so we need weak-strong again to avoid retain cycle
|
||||
__weak typeof(strongOperation) weakSubOperation = strongOperation;
|
||||
strongOperation.downloadToken = [self.imageDownloader downloadImageWithURL:url options:downloaderOptions context:context progress:progressBlock completed:^(UIImage *downloadedImage, NSData *downloadedData, NSError *error, BOOL finished) {
|
||||
strongOperation.downloadOperation = [self.imageDownloader downloadImageWithURL:url options:downloaderOptions context:context progress:progressBlock completed:^(UIImage *downloadedImage, NSData *downloadedData, NSError *error, BOOL finished) {
|
||||
__strong typeof(weakSubOperation) strongSubOperation = weakSubOperation;
|
||||
if (!strongSubOperation || strongSubOperation.isCancelled) {
|
||||
// Do nothing if the operation was cancelled
|
||||
|
@ -372,13 +372,17 @@
|
|||
|
||||
- (void)cancel {
|
||||
@synchronized(self) {
|
||||
if (self.isCancelled) {
|
||||
return;
|
||||
}
|
||||
self.cancelled = YES;
|
||||
if (self.cacheOperation) {
|
||||
[self.cacheOperation cancel];
|
||||
self.cacheOperation = nil;
|
||||
}
|
||||
if (self.downloadToken) {
|
||||
[self.manager.imageDownloader cancel:self.downloadToken];
|
||||
if (self.downloadOperation) {
|
||||
[self.downloadOperation cancel];
|
||||
self.downloadOperation = nil;
|
||||
}
|
||||
[self.manager safelyRemoveOperationFromRunning:self];
|
||||
}
|
||||
|
|
|
@ -16,6 +16,14 @@
|
|||
// All the stored operations are weak, so it will be dalloced after image loading finished. If you need to store operations, use your own class to keep a strong reference for them.
|
||||
@interface UIView (WebCacheOperation)
|
||||
|
||||
/**
|
||||
* Get the image load operation for key
|
||||
*
|
||||
* @param key key for identifying the operations
|
||||
* @return the image load operation
|
||||
*/
|
||||
- (nullable id<SDWebImageOperation>)sd_imageLoadOperationForKey:(nullable NSString *)key;
|
||||
|
||||
/**
|
||||
* Set the image load operation (storage in a UIView based weak map table)
|
||||
*
|
||||
|
|
|
@ -32,6 +32,15 @@ typedef NSMapTable<NSString *, id<SDWebImageOperation>> SDOperationsDictionary;
|
|||
}
|
||||
}
|
||||
|
||||
- (nullable id<SDWebImageOperation>)sd_imageLoadOperationForKey:(nullable NSString *)key {
|
||||
id<SDWebImageOperation> operation;
|
||||
SDOperationsDictionary *operationDictionary = [self sd_operationDictionary];
|
||||
@synchronized (self) {
|
||||
operation = [operationDictionary objectForKey:key];
|
||||
}
|
||||
return operation;
|
||||
}
|
||||
|
||||
- (void)sd_setImageLoadOperation:(nullable id<SDWebImageOperation>)operation forKey:(nullable NSString *)key {
|
||||
if (key) {
|
||||
[self sd_cancelImageLoadOperationWithKey:key];
|
||||
|
|
|
@ -109,10 +109,10 @@
|
|||
- (void)test07ThatAddProgressCallbackCompletedBlockWithNilURLCallsTheCompletionBlockWithNils {
|
||||
XCTestExpectation *expectation = [self expectationWithDescription:@"Completion is called with nils"];
|
||||
[[SDWebImageDownloader sharedDownloader] addProgressCallback:nil completedBlock:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, BOOL finished) {
|
||||
if (!image && !data && !error) {
|
||||
if (!image && !data && error) {
|
||||
[expectation fulfill];
|
||||
} else {
|
||||
XCTFail(@"All params should be nil");
|
||||
XCTFail(@"All params except error should be nil");
|
||||
}
|
||||
} forURL:nil createCallback:nil];
|
||||
[self waitForExpectationsWithTimeout:0.5 handler:nil];
|
||||
|
@ -174,7 +174,7 @@
|
|||
}];
|
||||
expect([SDWebImageDownloader sharedDownloader].currentDownloadCount).to.equal(1);
|
||||
|
||||
[[SDWebImageDownloader sharedDownloader] cancel:token];
|
||||
[token cancel];
|
||||
|
||||
// doesn't cancel immediately - since it uses dispatch async
|
||||
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, kMinDelayNanosecond), dispatch_get_main_queue(), ^{
|
||||
|
@ -298,7 +298,7 @@
|
|||
}];
|
||||
expect(token2).toNot.beNil();
|
||||
|
||||
[[SDWebImageDownloader sharedDownloader] cancel:token1];
|
||||
[token1 cancel];
|
||||
|
||||
[self waitForExpectationsWithCommonTimeout];
|
||||
}
|
||||
|
@ -323,7 +323,7 @@
|
|||
}];
|
||||
expect(token1).toNot.beNil();
|
||||
|
||||
[[SDWebImageDownloader sharedDownloader] cancel:token1];
|
||||
[token1 cancel];
|
||||
|
||||
SDWebImageDownloadToken *token2 = [[SDWebImageDownloader sharedDownloader]
|
||||
downloadImageWithURL:imageURL
|
||||
|
@ -369,4 +369,49 @@
|
|||
}
|
||||
#endif
|
||||
|
||||
- (void)test23ThatDownloadRequestModifierWorks {
|
||||
XCTestExpectation *expectation = [self expectationWithDescription:@"Download request modifier not works"];
|
||||
SDWebImageDownloader *downloader = [[SDWebImageDownloader alloc] init];
|
||||
SDWebImageDownloaderRequestModifier *requestModifier = [SDWebImageDownloaderRequestModifier requestModifierWithBlock:^NSURLRequest * _Nullable(NSURLRequest * _Nonnull request) {
|
||||
if ([request.URL.absoluteString isEqualToString:kTestPNGURL]) {
|
||||
// Test that return a modified request
|
||||
NSMutableURLRequest *mutableRequest = [request mutableCopy];
|
||||
[mutableRequest setValue:@"Bar" forHTTPHeaderField:@"Foo"];
|
||||
NSURLComponents *components = [NSURLComponents componentsWithURL:mutableRequest.URL resolvingAgainstBaseURL:NO];
|
||||
components.query = @"text=Hello+World";
|
||||
mutableRequest.URL = components.URL;
|
||||
return mutableRequest;
|
||||
} else if ([request.URL.absoluteString isEqualToString:kTestJpegURL]) {
|
||||
// Test that return nil request will treat as error
|
||||
return nil;
|
||||
} else {
|
||||
return request;
|
||||
}
|
||||
}];
|
||||
downloader.requestModifier = requestModifier;
|
||||
|
||||
__block BOOL firstCheck = NO;
|
||||
__block BOOL secondCheck = NO;
|
||||
|
||||
[downloader downloadImageWithURL:[NSURL URLWithString:kTestJpegURL] options:0 progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, BOOL finished) {
|
||||
// Except error
|
||||
expect(error).notTo.beNil();
|
||||
firstCheck = YES;
|
||||
if (firstCheck && secondCheck) {
|
||||
[expectation fulfill];
|
||||
}
|
||||
}];
|
||||
|
||||
[downloader downloadImageWithURL:[NSURL URLWithString:kTestPNGURL] options:0 progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, BOOL finished) {
|
||||
// Expect not error
|
||||
expect(error).to.beNil();
|
||||
secondCheck = YES;
|
||||
if (firstCheck && secondCheck) {
|
||||
[expectation fulfill];
|
||||
}
|
||||
}];
|
||||
|
||||
[self waitForExpectationsWithCommonTimeout];
|
||||
}
|
||||
|
||||
@end
|
||||
|
|
|
@ -29,6 +29,7 @@ FOUNDATION_EXPORT const unsigned char WebImageVersionString[];
|
|||
#import <SDWebImage/UIImageView+HighlightedWebCache.h>
|
||||
#import <SDWebImage/SDWebImageDownloaderConfig.h>
|
||||
#import <SDWebImage/SDWebImageDownloaderOperation.h>
|
||||
#import <SDWebImage/SDWebImageDownloaderRequestModifier.h>
|
||||
#import <SDWebImage/UIButton+WebCache.h>
|
||||
#import <SDWebImage/SDWebImagePrefetcher.h>
|
||||
#import <SDWebImage/UIView+WebCacheOperation.h>
|
||||
|
|
Loading…
Reference in New Issue