Skip to content

Commit

Permalink
Fix media attachments in rich notifications
Browse files Browse the repository at this point in the history
  • Loading branch information
tmolitor-stud-tu committed Oct 28, 2023
1 parent ea29888 commit 039b3a8
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 12 deletions.
16 changes: 10 additions & 6 deletions Monal/Classes/MLFiletransfer.m
Original file line number Diff line number Diff line change
Expand Up @@ -333,7 +333,7 @@ -(void) URLSession:(nonnull NSURLSession*) session downloadTask:(nonnull NSURLSe
//this allows hardlinking later on because now the mainapp owns that file while it had only read/write access before
if(!direct)
{
NSString* cacheFileTMP = [NSString stringWithFormat:@"%@.tmp", cacheFile];
NSString* cacheFileTMP = [cacheFile.stringByDeletingLastPathComponent stringByAppendingPathComponent:[NSString stringWithFormat:@"tmp.%@", cacheFile.lastPathComponent]];
DDLogInfo(@"Copying appex-created cache file '%@' to '%@' before deleting old file and renaming our copy...", cacheFile, cacheFileTMP);
[_fileManager removeItemAtPath:cacheFileTMP error:nil]; //remove tmp file if already present
[_fileManager copyItemAtPath:cacheFile toPath:cacheFileTMP error:&error];
Expand Down Expand Up @@ -485,7 +485,8 @@ +(NSDictionary*) getFileInfoForMessage:(MLMessage*) msg
MLAssert([msg.messageType isEqualToString:kMessageTypeFiletransfer], @"message not of type filetransfer!", (@{@"msg": msg}));

NSURLComponents* urlComponents = [NSURLComponents componentsWithString:msg.messageText];
NSString* filename = [[NSUUID UUID] UUIDString]; //default is a dummy filename (used when the filename can not be extracted from url)
//default is a dummy filename (used when the filename can not be extracted from url)
NSString* filename = [NSString stringWithFormat:@"%@.bin", [[NSUUID UUID] UUIDString]];
if(urlComponents != nil && urlComponents.path)
filename = [urlComponents.path lastPathComponent];
NSString* cacheFile = [self retrieveCacheFileForUrl:msg.messageText andMimeType:(msg.filetransferMimeType && ![msg.filetransferMimeType isEqualToString:@""] ? msg.filetransferMimeType : nil)];
Expand All @@ -501,12 +502,14 @@ +(NSDictionary*) getFileInfoForMessage:(MLMessage*) msg
@"needsDownloading": @YES,
@"mimeType": msg.filetransferMimeType,
@"size": msg.filetransferSize,
@"fileExtension": [filename pathExtension],
};
else
return @{
@"url": msg.messageText,
@"filename": filename,
@"needsDownloading": @YES,
@"fileExtension": [filename pathExtension],
};
}
return @{
Expand All @@ -517,6 +520,7 @@ +(NSDictionary*) getFileInfoForMessage:(MLMessage*) msg
@"size": @([[_fileManager attributesOfItemAtPath:cacheFile error:nil] fileSize]),
@"cacheId": [cacheFile lastPathComponent],
@"cacheFile": cacheFile,
@"fileExtension": [filename pathExtension],
};
}

Expand All @@ -543,7 +547,7 @@ +(MLHandler*) prepareDataUpload:(NSData*) data withFileExtension:(NSString*) fil
DDLogInfo(@"Preparing for upload of NSData object: %@", data);

//save file data to our document cache (temporary filename because the upload url is unknown yet)
NSString* tempname = [NSString stringWithFormat:@"%@.tmp", [[NSUUID UUID] UUIDString]];
NSString* tempname = [NSString stringWithFormat:@"tmp.%@", [[NSUUID UUID] UUIDString]];
NSError* error;
NSString* file = [_documentCacheDir stringByAppendingPathComponent:tempname];
DDLogDebug(@"Tempstoring data at %@", file);
Expand All @@ -569,7 +573,7 @@ +(MLHandler*) prepareFileUpload:(NSURL*) fileUrl
DDLogInfo(@"Preparing for upload of file stored at %@", [fileUrl path]);

//copy file to our document cache (temporary filename because the upload url is unknown yet)
NSString* tempname = [NSString stringWithFormat:@"%@.tmp", [[NSUUID UUID] UUIDString]];
NSString* tempname = [NSString stringWithFormat:@"tmp.%@", [[NSUUID UUID] UUIDString]];
NSError* error;
NSString* file = [_documentCacheDir stringByAppendingPathComponent:tempname];
DDLogDebug(@"Tempstoring file at %@", file);
Expand All @@ -595,7 +599,7 @@ +(MLHandler*) prepareUIImageUpload:(UIImage*) image
double imageQuality = [[HelperTools defaultsDB] doubleForKey:@"ImageUploadQuality"];

//copy file to our document cache (temporary filename because the upload url is unknown yet)
NSString* tempname = [NSString stringWithFormat:@"%@.tmp", [[NSUUID UUID] UUIDString]];
NSString* tempname = [NSString stringWithFormat:@"tmp.%@", [[NSUUID UUID] UUIDString]];
NSError* error;
NSString* file = [_documentCacheDir stringByAppendingPathComponent:tempname];
DDLogDebug(@"Tempstoring jpeg encoded file having quality %f at %@", imageQuality, file);
Expand Down Expand Up @@ -640,7 +644,7 @@ +(void) doStartupCleanup
//delete leftover tmp files older than 1 day
NSDate* now = [NSDate date];
NSArray* directoryContents = [_fileManager contentsOfDirectoryAtPath:_documentCacheDir error:nil];
NSPredicate* filter = [NSPredicate predicateWithFormat:@"self ENDSWITH '.tmp'"];
NSPredicate* filter = [NSPredicate predicateWithFormat:@"self BEGINSWITH 'tmp.'"];
for(NSString* file in [directoryContents filteredArrayUsingPredicate:filter])
{
NSURL* fileUrl = [NSURL fileURLWithPath:file];
Expand Down
23 changes: 17 additions & 6 deletions Monal/Classes/MLNotificationManager.m
Original file line number Diff line number Diff line change
Expand Up @@ -790,17 +790,28 @@ -(void) showLegacyNotificationForMessage:(MLMessage*) message withSound:(BOOL) s
-(UNNotificationAttachment* _Nullable) createNotificationAttachmentForFileInfo:(NSDictionary*) info havingTypeHint:(UTType*) typeHint
{
NSError* error;
//use ".tmp" extension to make sure this file will be garbage collected if the ios notification attachment should leave it behind
NSString* notificationImage = [[[HelperTools getContainerURLForPathComponents:@[@"documentCache"]] path] stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.tmp", info[@"cacheId"]]];
DDLogVerbose(@"Preparing for notification attachment: hardlinking downloaded file from '%@' to '%@'..", info[@"cacheFile"], notificationImage);
error = [HelperTools hardLinkOrCopyFile:info[@"cacheFile"] to:notificationImage];
NSString* notificationAttachment = [[HelperTools getContainerURLForPathComponents:@[@"documentCache"]] path];
//use "tmp." prefix to make sure this file will be garbage collected should the ios notification attachment implementation leave it behind
NSString* attachmentBasename = [NSString stringWithFormat:@"tmp.%@", info[@"cacheId"]];
//using stringByAppendingPathExtensionForType: does not produce playable audio notifications for audios sent by conversations,
//but seems to work for other types
//--> use info[@"fileExtension"] for audio files and stringByAppendingPathExtensionForType: for all other types
if([typeHint conformsToType:UTTypeAudio])
notificationAttachment = [notificationAttachment stringByAppendingPathComponent:[attachmentBasename stringByAppendingPathExtension:info[@"fileExtension"]]];
else
notificationAttachment = [notificationAttachment stringByAppendingPathComponent:[attachmentBasename stringByAppendingPathExtensionForType:typeHint]];
DDLogVerbose(@"Preparing for notification attachment(%@): hardlinking downloaded file from '%@' to '%@'..", typeHint, info[@"cacheFile"], notificationAttachment);
error = [HelperTools hardLinkOrCopyFile:info[@"cacheFile"] to:notificationAttachment];
if(error)
{
DDLogError(@"Could not hardlink cache file to notification image temp file!");
return nil;
}
[HelperTools configureFileProtectionFor:notificationImage];
return [UNNotificationAttachment attachmentWithIdentifier:info[@"cacheId"] URL:[NSURL fileURLWithPath:notificationImage] options:@{UNNotificationAttachmentOptionsTypeHintKey:typeHint} error:&error];
[HelperTools configureFileProtectionFor:notificationAttachment];
UNNotificationAttachment* attachment = [UNNotificationAttachment attachmentWithIdentifier:info[@"cacheId"] URL:[NSURL fileURLWithPath:notificationAttachment] options:@{UNNotificationAttachmentOptionsTypeHintKey:typeHint} error:&error];
if(error != nil)
DDLogError(@"Could not create UNNotificationAttachment: %@", error);
return attachment;
}

-(void) dealloc
Expand Down

0 comments on commit 039b3a8

Please sign in to comment.