diff --git a/Classes/ChatConversationView.h b/Classes/ChatConversationView.h index 32595c83c..06bb89c17 100644 --- a/Classes/ChatConversationView.h +++ b/Classes/ChatConversationView.h @@ -95,9 +95,9 @@ + (void)markAsRead:(LinphoneChatRoom *)chatRoom; + (void)autoDownload:(LinphoneChatMessage *)message; +(NSString *)getKeyFromFileType:(NSString *)fileType fileName:(NSString *)name; -+ (NSURL *)getCacheFileUrl:(NSString *)name; -+ (void)writeFileInCache:(NSData *)data name:(NSString *)name; -+ (NSData *)getCacheFileData:(NSString *)name; ++ (NSURL *)getFileUrl:(NSString *)name; ++ (void)writeFileInImagesDirectory:(NSData *)data name:(NSString *)name; ++ (NSData *)getFileData:(NSString *)name; + (void)writeMediaToGallery:(NSString *)name fileType:(NSString *)fileType; +(UIImage *)getBasicImage; +(UIImage*)drawText:(NSString*)text image:(UIImage *)image textSize:(CGFloat)textSize; @@ -121,7 +121,6 @@ - (void)showFileDownloadError; - (NSURL *)getICloudFileUrl:(NSString *)name; -- (BOOL)writeFileInICloud:(NSData *)data fileURL:(NSURL *)fileURL; - (void)removeCallBacks; @end diff --git a/Classes/ChatConversationView.m b/Classes/ChatConversationView.m index a365d68e6..bfdca00f3 100644 --- a/Classes/ChatConversationView.m +++ b/Classes/ChatConversationView.m @@ -901,7 +901,7 @@ static UICompositeViewDescription *compositeDescription = nil; } + (void)writeMediaToGallery:(NSString *)name fileType:(NSString *)fileType { - NSString *filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; + NSString *filePath = [LinphoneManager validFilePath:name]; NSFileManager *fileManager = [NSFileManager defaultManager]; if ([fileManager fileExistsAtPath:filePath]) { NSData* data = [NSData dataWithContentsOfFile:filePath]; @@ -1324,18 +1324,18 @@ void on_chat_room_conference_alert(LinphoneChatRoom *cr, const LinphoneEventLog [PhoneMainView.instance fullScreen:NO]; } -+ (NSData *)getCacheFileData: (NSString *)name { - NSString *filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; ++ (NSData *)getFileData: (NSString *)name { + NSString *filePath = [LinphoneManager validFilePath:name]; return [NSData dataWithContentsOfFile:filePath]; } -+ (NSURL *)getCacheFileUrl: (NSString *)name { - NSString *filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; ++ (NSURL *)getFileUrl: (NSString *)name { + NSString *filePath = [LinphoneManager validFilePath:name]; return [NSURL fileURLWithPath:filePath]; } -+ (void)writeFileInCache:(NSData *)data name:(NSString *)name { - NSString *filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; ++ (void)writeFileInImagesDirectory:(NSData *)data name:(NSString *)name { + NSString *filePath = [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:name]; if (name || [name isEqualToString:@""]) { LOGW(@"try to write file in %@", filePath); } @@ -1364,44 +1364,6 @@ void on_chat_room_conference_alert(LinphoneChatRoom *cr, const LinphoneEventLog return nil; } -- (BOOL)writeFileInICloud:(NSData *)data fileURL:(NSURL *)fileURL { - NSFileManager *fileManager = [NSFileManager defaultManager]; - BOOL useMyDevice = FALSE; - if (@available(iOS 11.0, *)) { - useMyDevice = TRUE; - } - - if (!useMyDevice && ![[fileManager URLForUbiquityContainerIdentifier:nil]URLByAppendingPathComponent:@"Documents"]) { - //notify : set configuration to use icloud - [[[UIAlertView alloc] initWithTitle:NSLocalizedString(@"Info", nil) message:NSLocalizedString(@"ICloud Drive is unavailable.", nil) delegate:nil cancelButtonTitle:NSLocalizedString(@"Cancel", nil) otherButtonTitles:nil, nil] show]; - return FALSE; - } - - NSString *fileName = fileURL.lastPathComponent; - if ([fileManager fileExistsAtPath:[fileURL path]] || [fileName hasPrefix:@"recording"]) { - // if it exists, replace the file. If it's a record file, copy the file - return [data writeToURL:fileURL atomically:TRUE]; - } else { - // get the url of localfile - NSString *filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:fileName]; - NSURL *localURL = nil; - if (fileName || [fileName isEqualToString:@""]) { - LOGW(@"[writeFileInICloud] try to write file in %@", filePath); - } - if ([fileManager createFileAtPath:filePath contents:data attributes:nil]) { - localURL = [NSURL fileURLWithPath:filePath]; - } - - NSError *error; - if ([[NSFileManager defaultManager] setUbiquitous:YES itemAtURL:localURL destinationURL:fileURL error:&error]) { - return TRUE; - } else { - LOGE(@"Cannot write file in Icloud file [%@]",[error localizedDescription]); - return FALSE; - } - } -} - - (void)deleteFileWithUuid:(NSUUID *)uuid { [_fileContext deleteContentWithUuid:uuid]; [self refreshImageDrawer]; diff --git a/Classes/LinphoneManager.h b/Classes/LinphoneManager.h index 318d70940..f168ada5a 100644 --- a/Classes/LinphoneManager.h +++ b/Classes/LinphoneManager.h @@ -132,6 +132,8 @@ typedef struct _LinphoneManagerSounds { + (NSString *)documentFile:(NSString *)file; + (NSString*)dataFile:(NSString*)file; + (NSString*)cacheDirectory; ++ (NSString *)imagesDirectory; ++ (NSString *)validFilePath:(NSString *)name; // migration + (NSString *)oldPreferenceFile:(NSString *)file; + (NSString *)oldDataFile:(NSString *)file; diff --git a/Classes/LinphoneManager.m b/Classes/LinphoneManager.m index 8628e2072..64bb1b296 100644 --- a/Classes/LinphoneManager.m +++ b/Classes/LinphoneManager.m @@ -252,6 +252,9 @@ struct codec_name_pref_table codec_pref_table[] = {{"speex", 8000, "speex_8k_pre [self renameDefaultSettings]; [self copyDefaultSettings]; [self overrideDefaultSettings]; + if (![self lpConfigBoolForKey:@"migration_images_done" withDefault:FALSE]) { + [self migrationAllImages]; + } [self lpConfigSetString:[LinphoneManager dataFile:@"linphone.db"] forKey:@"uri" inSection:@"storage"]; [self lpConfigSetString:[LinphoneManager dataFile:@"x3dh.c25519.sqlite3"] forKey:@"x3dh_db_path" inSection:@"lime"]; @@ -1400,7 +1403,7 @@ void popup_link_account_cb(LinphoneAccountCreator *creator, LinphoneAccountCreat /* Use the rootca from framework, which is already set*/ //linphone_core_set_root_ca(theLinphoneCore, [LinphoneManager bundleFile:@"rootca.pem"].UTF8String); - linphone_core_set_user_certificates_path(theLinphoneCore, [LinphoneManager cacheDirectory].UTF8String); + linphone_core_set_user_certificates_path(theLinphoneCore, linphone_factory_get_data_dir(linphone_factory_get(), kLinphoneMsgNotificationAppGroupId.UTF8String)); /* The core will call the linphone_iphone_configuring_status_changed callback when the remote provisioning is loaded (or skipped). @@ -1668,6 +1671,17 @@ static int comp_call_state_paused(const LinphoneCall *call, const void *param) { linphone_core_refresh_registers(theLinphoneCore); // just to make sure REGISTRATION is up to date } +- (void)migrationAllImages { + NSFileManager *fileManager = [NSFileManager defaultManager]; + NSArray *images = [fileManager contentsOfDirectoryAtPath:[LinphoneManager cacheDirectory] error:NULL]; + + for (NSString *image in images) + { + [fileManager copyItemAtPath:[[LinphoneManager cacheDirectory] stringByAppendingPathComponent:image] toPath:[[LinphoneManager imagesDirectory] stringByAppendingPathComponent:image] error:nil]; + } + [self lpConfigSetBool:TRUE forKey:@"migration_images_done"]; +} + - (void)migrateImportantFiles { if ([LinphoneManager copyFile:[LinphoneManager oldPreferenceFile:@"linphonerc"] destination:[LinphoneManager preferenceFile:@"linphonerc"] override:TRUE ignore:TRUE]) { [NSFileManager.defaultManager @@ -1845,6 +1859,22 @@ static int comp_call_state_paused(const LinphoneCall *call, const void *param) { return [fullPath stringByAppendingPathComponent:file]; } ++ (NSString *)imagesDirectory { + NSURL *basePath = [[NSFileManager defaultManager] containerURLForSecurityApplicationGroupIdentifier:kLinphoneMsgNotificationAppGroupId]; + NSString *fullPath = [[basePath path] stringByAppendingString:@"/Library/Images/"]; + if (![[NSFileManager defaultManager] fileExistsAtPath:fullPath]) { + NSError *error; + LOGW(@"Download path %@ does not exist, creating it.", fullPath); + if (![[NSFileManager defaultManager] createDirectoryAtPath:fullPath + withIntermediateDirectories:YES + attributes:nil + error:&error]) { + LOGE(@"Create download path directory error: %@", error.description); + } + } + return fullPath; +} + + (NSString *)cacheDirectory { NSURL *basePath = [[NSFileManager defaultManager] containerURLForSecurityApplicationGroupIdentifier:kLinphoneMsgNotificationAppGroupId]; NSString *fullPath = [[basePath path] stringByAppendingString:@"/Library/Caches/"]; @@ -1859,20 +1889,15 @@ static int comp_call_state_paused(const LinphoneCall *call, const void *param) { } } return fullPath; - - /*LinphoneFactory *factory = linphone_factory_get(); - NSString *cachePath = [NSString stringWithUTF8String:linphone_factory_get_download_dir(factory, kLinphoneMsgNotificationAppGroupId.UTF8String)]; - BOOL isDir = NO; - NSError *error; - // cache directory must be created if not existing - if (![[NSFileManager defaultManager] fileExistsAtPath:cachePath isDirectory:&isDir] && isDir == NO) { - [[NSFileManager defaultManager] createDirectoryAtPath:cachePath - withIntermediateDirectories:NO - attributes:nil - error:&error]; - LOGW(@"create new cache directory"); +} + ++ (NSString *)validFilePath:(NSString *)name { + NSString *filePath = [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:name]; + if ([[NSFileManager defaultManager] fileExistsAtPath:filePath]) { + return filePath; } - return cachePath;*/ + // if migration (move files of cacheDirectory to imagesDirectory) failed + return [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; } + (NSString *)oldPreferenceFile:(NSString *)file { diff --git a/Classes/LinphoneUI/UIChatBubblePhotoCell.m b/Classes/LinphoneUI/UIChatBubblePhotoCell.m index d2f99565f..d96ae3cb2 100644 --- a/Classes/LinphoneUI/UIChatBubblePhotoCell.m +++ b/Classes/LinphoneUI/UIChatBubblePhotoCell.m @@ -266,7 +266,7 @@ ms_free(cPath); [LinphoneManager setValueInMessageAppData:filePath forKey:@"encryptedfile" inMessage:self.message]; } else { - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:fileName]; + filePath = [LinphoneManager validFilePath:fileName]; } } if ([[NSFileManager defaultManager] fileExistsAtPath:filePath]) { @@ -435,7 +435,7 @@ if (!filePath) { NSString *localVideo = [LinphoneManager getMessageAppDataForKey:@"localvideo" inMessage:self.message]; NSString *localFile = [LinphoneManager getMessageAppDataForKey:@"localfile" inMessage:self.message]; - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:(localVideo?:localFile)]; + filePath = [LinphoneManager validFilePath:(localVideo?:localFile)]; } if ([[NSFileManager defaultManager] fileExistsAtPath:filePath]) { @@ -492,8 +492,8 @@ return; } NSString *name = [LinphoneManager getMessageAppDataForKey:@"localfile" inMessage:self.message]; - if([[NSFileManager defaultManager] fileExistsAtPath:[[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]]) { - [view openFileWithURL:[ChatConversationView getCacheFileUrl:name]]; + if([[NSFileManager defaultManager] fileExistsAtPath: [LinphoneManager validFilePath:name]]) { + [view openFileWithURL:[ChatConversationView getFileUrl:name]]; } else { [view openFileWithURL:[view getICloudFileUrl:name]]; } @@ -540,16 +540,16 @@ NSString *localImage = [LinphoneManager getMessageAppDataForKey:@"localimage" inMessage:self.message]; NSString *localFile = [LinphoneManager getMessageAppDataForKey:@"localfile" inMessage:self.message]; NSString *imageName = NULL; - if (localImage && [[NSFileManager defaultManager] fileExistsAtPath:[[LinphoneManager cacheDirectory] stringByAppendingPathComponent:localImage]]) { + if (localImage && [[NSFileManager defaultManager] fileExistsAtPath: [LinphoneManager validFilePath:localImage]]) { imageName = localImage; - } else if (localFile && [[NSFileManager defaultManager] fileExistsAtPath:[[LinphoneManager cacheDirectory] stringByAppendingPathComponent:localFile]]) { + } else if (localFile && [[NSFileManager defaultManager] fileExistsAtPath:[LinphoneManager validFilePath:localFile]]) { if ([localFile hasSuffix:@"JPG"] || [localFile hasSuffix:@"PNG"] || [localFile hasSuffix:@"jpg"] || [localFile hasSuffix:@"png"]) { imageName = localFile; } } if (imageName) { - NSData *data = [NSData dataWithContentsOfFile:[[LinphoneManager cacheDirectory] stringByAppendingPathComponent:imageName]]; + NSData *data = [NSData dataWithContentsOfFile:[LinphoneManager validFilePath:imageName]]; UIImage *image = [[UIImage alloc] initWithData:data]; if (image) [view setImage:image]; diff --git a/Classes/LinphoneUI/UIChatBubbleTextCell.m b/Classes/LinphoneUI/UIChatBubbleTextCell.m index 704ca72be..808cb20b1 100644 --- a/Classes/LinphoneUI/UIChatBubbleTextCell.m +++ b/Classes/LinphoneUI/UIChatBubbleTextCell.m @@ -75,7 +75,7 @@ for(NSString *path in [encrptedFilePaths allValues]) { if (![path isEqualToString:@""]) { LOGW(@"[vfs]s remove item at %@",path); - if ([path isEqualToString:[LinphoneManager cacheDirectory]]) { + if ([path isEqualToString:[LinphoneManager imagesDirectory]]) { LOGE(@"[vfs] something is wrong, can not delete the cache directory"); break; } @@ -92,7 +92,7 @@ if (![filePath isEqualToString:@""]) { NSError *error = nil; LOGW(@"[vfs] remove item at %@",filePath); - if ([filePath isEqualToString:[LinphoneManager cacheDirectory]]) { + if ([filePath isEqualToString:[LinphoneManager imagesDirectory]]) { LOGE(@"[vfs] something is wrong, can not delete the cache directory"); } else { [[NSFileManager defaultManager] removeItemAtPath:filePath error:&error]; @@ -327,7 +327,7 @@ NSString *name = [NSString stringWithUTF8String:linphone_content_get_name(content)]; NSString *filePath = [encrptedFilePaths valueForKey:name]; if (filePath == NULL) { - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; + filePath = [LinphoneManager validFilePath:name]; } [newfileContext addObject:[NSData dataWithContentsOfFile:filePath] name:name type:[NSString stringWithUTF8String:linphone_content_get_type(content)]]; } @@ -354,11 +354,11 @@ const char *text = linphone_chat_message_get_text_content(_message); NSString *str = text ? [NSString stringWithUTF8String:text] : NULL; if (localImage) { - [_chatRoomDelegate resendFile: (data?:[ChatConversationView getCacheFileData:localImage]) withName:localImage type:@"image" key:@"localimage" message:str]; + [_chatRoomDelegate resendFile: (data?:[ChatConversationView getFileData:localImage]) withName:localImage type:@"image" key:@"localimage" message:str]; } else if (localVideo) { - [_chatRoomDelegate resendFile:(data?:[ChatConversationView getCacheFileData:localVideo]) withName:localVideo type:@"video" key:@"localvideo" message:str]; + [_chatRoomDelegate resendFile:(data?:[ChatConversationView getFileData:localVideo]) withName:localVideo type:@"video" key:@"localvideo" message:str]; } else { - [_chatRoomDelegate resendFile:(data?:[ChatConversationView getCacheFileData:localFile]) withName:localFile type:@"image" key:@"localfile" message:str]; + [_chatRoomDelegate resendFile:(data?:[ChatConversationView getFileData:localFile]) withName:localFile type:@"image" key:@"localfile" message:str]; } }); } else { @@ -441,7 +441,7 @@ static const CGFloat CELL_MESSAGE_Y_MARGIN = 44; NSString *type = [NSString stringWithUTF8String:linphone_content_get_type(content)]; NSString *name = [NSString stringWithUTF8String:linphone_content_get_name(content)]; if (!filePath) { - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; + filePath = [LinphoneManager validFilePath:name]; } UIImage *image = nil; @@ -502,7 +502,7 @@ static const CGFloat CELL_MESSAGE_Y_MARGIN = 44; NSString *name = [NSString stringWithUTF8String:linphone_content_get_name(content)]; NSString *filePath=[encrptedFilePaths valueForKey:name]; if (filePath == NULL) { - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; + filePath = [LinphoneManager validFilePath:name]; } image = [UIChatBubbleTextCell getImageFromContent:content filePath:filePath]; @@ -562,7 +562,7 @@ static const CGFloat CELL_MESSAGE_Y_MARGIN = 44; CGSize originalImageSize = CGSizeMake(230, 50); if (!filePath) { - filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:fileName]; + filePath = [LinphoneManager validFilePath:fileName]; } if (localFile) { UIImage *image = nil; diff --git a/Classes/LinphoneUI/UIChatContentView.m b/Classes/LinphoneUI/UIChatContentView.m index fd24709cf..45882677f 100644 --- a/Classes/LinphoneUI/UIChatContentView.m +++ b/Classes/LinphoneUI/UIChatContentView.m @@ -48,7 +48,7 @@ } else { if (_filePath == NULL) { NSString *name = [NSString stringWithUTF8String:linphone_content_get_name(content)]; - _filePath = [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name]; + _filePath = [LinphoneManager validFilePath:name]; } UIImage *image = [UIChatBubbleTextCell getImageFromContent:content filePath:_filePath]; [self setImage:image]; @@ -67,7 +67,7 @@ -(IBAction)onDownloadClick:(id)sender { _downloadButton.enabled = NO; - linphone_content_set_file_path(_content, [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:[NSString stringWithUTF8String:linphone_content_get_name(_content)]].UTF8String); + linphone_content_set_file_path(_content, [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:[NSString stringWithUTF8String:linphone_content_get_name(_content)]].UTF8String); linphone_chat_message_download_content(_message, _content); } diff --git a/Classes/Utils/FileTransferDelegate.m b/Classes/Utils/FileTransferDelegate.m index 970288c86..d8d20670b 100644 --- a/Classes/Utils/FileTransferDelegate.m +++ b/Classes/Utils/FileTransferDelegate.m @@ -108,13 +108,13 @@ static void file_transfer_progress_indication_send(LinphoneChatMessage *message, return; } [LinphoneManager.instance.fileTransferDelegates addObject:self]; - [ChatConversationView writeFileInCache:data name:name]; + [ChatConversationView writeFileInImagesDirectory:data name:name]; LinphoneContent *content = linphone_core_create_content(linphone_chat_room_get_core(chatRoom)); linphone_content_set_type(content, [type UTF8String]); linphone_content_set_subtype(content, [subtype UTF8String]); linphone_content_set_name(content, [name UTF8String]); - linphone_content_set_file_path(content, [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name].UTF8String); + linphone_content_set_file_path(content, [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:name].UTF8String); _message = linphone_chat_room_create_file_transfer_message(chatRoom, content); BOOL isOneToOneChat = linphone_chat_room_get_capabilities(chatRoom) & LinphoneChatRoomCapabilitiesOneToOne; if (!isOneToOneChat && (_text!=nil && ![_text isEqualToString:@""])) @@ -143,13 +143,13 @@ static void file_transfer_progress_indication_send(LinphoneChatMessage *message, NSString *name = [context.namesArray objectAtIndex:i]; NSData *data = [context.datasArray objectAtIndex:i]; - [ChatConversationView writeFileInCache:data name:name]; + [ChatConversationView writeFileInImagesDirectory:data name:name]; linphone_content_set_type(content, [type UTF8String]); linphone_content_set_subtype(content, [name.pathExtension UTF8String]); linphone_content_set_name(content, [name UTF8String]); - linphone_content_set_file_path(content, [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:name].UTF8String); + linphone_content_set_file_path(content, [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:name].UTF8String); [names addObject:name]; [types addObject:type]; linphone_chat_message_add_file_content(_message, content); @@ -179,7 +179,7 @@ static void file_transfer_progress_indication_send(LinphoneChatMessage *message, } - (void)uploadFile:(NSData *)data forChatRoom:(LinphoneChatRoom *)chatRoom withName:(NSString *)name { - NSURL *url = [ChatConversationView getCacheFileUrl:name]; + NSURL *url = [ChatConversationView getFileUrl:name]; AVAsset *asset = [AVURLAsset URLAssetWithURL:url options:nil]; NSString *fileType = [[asset tracksWithMediaType:AVMediaTypeVideo] count] > 0 ? @"video" : @"file"; NSString *key = [ChatConversationView getKeyFromFileType:fileType fileName:name]; @@ -202,7 +202,7 @@ static void file_transfer_progress_indication_send(LinphoneChatMessage *message, LOGI(@"%p Downloading content in %p ", self, message); linphone_chat_message_cbs_set_file_transfer_progress_indication(linphone_chat_message_get_callbacks(_message), file_transfer_progress_indication_recv); - linphone_content_set_file_path(content, [[LinphoneManager cacheDirectory] stringByAppendingPathComponent:[NSString stringWithUTF8String:linphone_content_get_name(content)]].UTF8String); + linphone_content_set_file_path(content, [[LinphoneManager imagesDirectory] stringByAppendingPathComponent:[NSString stringWithUTF8String:linphone_content_get_name(content)]].UTF8String); linphone_chat_message_download_content(_message, content); return TRUE;