aliyun-oss-react-native

RNAliyunOSS.m 6.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. /**
  2. * RNAliyunOSS.m refactor comments
  3. */
  4. #import "RNAliyunOSS.h"
  5. #import <React/RCTLog.h>
  6. #import <React/RCTConvert.h>
  7. @import Photos;
  8. @import MobileCoreServices;
  9. @implementation RNAliyunOSS
  10. /**
  11. Will be called when this module's first listener is added.
  12. */
  13. -(void)startObserving {
  14. _hasListeners = YES;
  15. // Set up any upstream listeners or background tasks as necessary
  16. }
  17. /**Will be called when this module's last listener is removed, or on dealloc.
  18. */
  19. -(void)stopObserving {
  20. _hasListeners = NO;
  21. // Remove upstream listeners, stop unnecessary background tasks
  22. }
  23. /**
  24. Supported two events: uploadProgress, downloadProgress
  25. @return an array stored all supported events
  26. */
  27. -(NSArray<NSString *> *)supportedEvents
  28. {
  29. return @[@"uploadProgress", @"downloadProgress"];
  30. }
  31. /**
  32. Get local directory with read/write accessed
  33. @return document directory
  34. */
  35. -(NSString *)getDocumentDirectory {
  36. NSString * path = NSHomeDirectory();
  37. NSLog(@"NSHomeDirectory:%@",path);
  38. NSString * userName = NSUserName();
  39. NSString * rootPath = NSHomeDirectoryForUser(userName);
  40. NSLog(@"NSHomeDirectoryForUser:%@",rootPath);
  41. NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
  42. NSString * documentsDirectory = [paths objectAtIndex:0];
  43. return documentsDirectory;
  44. }
  45. /**
  46. Get a temporary directory inside of application's sandbox
  47. @return document directory
  48. */
  49. -(NSString*)getTemporaryDirectory {
  50. NSString *TMP_DIRECTORY = @"react-native/";
  51. NSString *filepath = [NSTemporaryDirectory() stringByAppendingString:TMP_DIRECTORY];
  52. BOOL isDir;
  53. BOOL exists = [[NSFileManager defaultManager] fileExistsAtPath:filepath isDirectory:&isDir];
  54. if (!exists) {
  55. [[NSFileManager defaultManager] createDirectoryAtPath: filepath
  56. withIntermediateDirectories:YES attributes:nil error:nil];
  57. }
  58. return filepath;
  59. }
  60. /**
  61. Setup initial configuration for initializing OSS Client
  62. @param configuration a configuration object (NSDictionary *) passed from react-native side
  63. */
  64. -(void)initConfiguration:(NSDictionary *)configuration {
  65. _clientConfiguration = [OSSClientConfiguration new];
  66. _clientConfiguration.maxRetryCount = [RCTConvert int:configuration[@"maxRetryCount"]]; //default 3
  67. _clientConfiguration.timeoutIntervalForRequest = [RCTConvert double:configuration[@"timeoutIntervalForRequest"]]; //default 30
  68. _clientConfiguration.timeoutIntervalForResource = [RCTConvert double:configuration[@"timeoutIntervalForResource"]]; //default 24 * 60 * 60
  69. }
  70. /**
  71. Begin a new uploading task
  72. Currently, support AssetLibrary, PhotoKit, and pure File for uploading
  73. Also, will convert the HEIC image to JPEG format
  74. @param filepath passed from reacit-native side, it might be a path started with 'assets-library://', 'localIdentifier://', 'file:'
  75. @param callback a block waiting to be called right after the binary data of asset is found
  76. */
  77. -(void)beginUploadingWithFilepath:(NSString *)filepath resultBlock:(void (^) (NSData *))callback {
  78. // read asset data from filepath
  79. if ([filepath hasPrefix:@"assets-library://"]) {
  80. PHAsset *asset = [PHAsset fetchAssetsWithALAssetURLs:@[filepath] options:nil].firstObject;
  81. [self convertToNSDataFromAsset:asset withHandler:callback];
  82. } else if ([filepath hasPrefix:@"localIdentifier://"]) {
  83. NSString *localIdentifier = [filepath stringByReplacingOccurrencesOfString:@"localIdentifier://" withString:@""];
  84. PHAsset *asset = [PHAsset fetchAssetsWithLocalIdentifiers:@[localIdentifier] options:nil].firstObject;
  85. [self convertToNSDataFromAsset:asset withHandler:callback];
  86. } else {
  87. filepath = [filepath stringByReplacingOccurrencesOfString:@"file://" withString:@""];
  88. NSData *data = [NSData dataWithContentsOfFile:filepath];
  89. callback(data);
  90. }
  91. }
  92. /**
  93. a helper method to do the file convertion
  94. @param asset PHAsset
  95. @param handler a callback block
  96. */
  97. -(void)convertToNSDataFromAsset:(PHAsset *)asset withHandler:(void (^) (NSData *))handler
  98. {
  99. PHImageManager *imageManager = [PHImageManager defaultManager];
  100. switch (asset.mediaType) {
  101. case PHAssetMediaTypeImage: {
  102. PHImageRequestOptions *options = [[PHImageRequestOptions alloc] init];
  103. options.networkAccessAllowed = YES;
  104. [imageManager requestImageDataForAsset:asset options:options resultHandler:^(NSData * _Nullable imageData, NSString * _Nullable dataUTI, UIImageOrientation orientation, NSDictionary * _Nullable info) {
  105. if ([dataUTI isEqualToString:(__bridge NSString *)kUTTypeJPEG]) {
  106. handler(imageData);
  107. } else {
  108. //if the image UTI is not JPEG, then do the convertion to make sure its compatibility
  109. CGImageSourceRef source = CGImageSourceCreateWithData((__bridge CFDataRef)imageData, NULL);
  110. NSDictionary *imageInfo = (__bridge NSDictionary*)CGImageSourceCopyPropertiesAtIndex(source, 0, NULL);
  111. NSDictionary *metadata = [imageInfo copy];
  112. NSMutableData *imageDataJPEG = [NSMutableData data];
  113. CGImageDestinationRef destination = CGImageDestinationCreateWithData((__bridge CFMutableDataRef)imageDataJPEG, kUTTypeJPEG, 1, NULL);
  114. CGImageDestinationAddImageFromSource(destination, source, 0, (__bridge CFDictionaryRef)metadata);
  115. CGImageDestinationFinalize(destination);
  116. handler([NSData dataWithData:imageDataJPEG]);
  117. }
  118. }];
  119. break;
  120. }
  121. case PHAssetMediaTypeVideo:{
  122. PHVideoRequestOptions *options = [[PHVideoRequestOptions alloc] init];
  123. options.networkAccessAllowed = YES;
  124. [imageManager requestExportSessionForVideo:asset options:options exportPreset:AVAssetExportPresetHighestQuality resultHandler:^(AVAssetExportSession * _Nullable exportSession, NSDictionary * _Nullable info) {
  125. //generate a temporary directory for caching the video (MP4 Only)
  126. NSString *filePath = [[self getTemporaryDirectory] stringByAppendingString:[[NSUUID UUID] UUIDString]];
  127. filePath = [filePath stringByAppendingString:@".mp4"];
  128. exportSession.shouldOptimizeForNetworkUse = YES;
  129. exportSession.outputFileType = AVFileTypeMPEG4;
  130. exportSession.outputURL = [NSURL fileURLWithPath:filePath];
  131. [exportSession exportAsynchronouslyWithCompletionHandler:^{
  132. handler([NSData dataWithContentsOfFile:filePath]);
  133. }];
  134. }];
  135. break;
  136. }
  137. default:
  138. break;
  139. }
  140. }
  141. /**
  142. Expose this native module to RN
  143. */
  144. RCT_EXPORT_MODULE()
  145. @end