iPhone how to compress the files while upload to server? - iphone

What is the best way to compress and upload file from iPhone? Am using ASIHTTP to upload the file to my server. But am getting network error while upload the large files to server. So how to compress and upload it using ASIHTTP?
Code:
[serverUploadRequest setPostValue:withEmail_id forKey:#"mail_id"];
[serverUploadRequest setPostValue:withPassword forKey:#"pwd"];
[serverUploadRequest setPostValue:withFileName forKey:#"file_name"];
[serverUploadRequest setPostValue:withFileExtension forKey:#"file_extension"];
[serverUploadRequest setData:fileData withFileName:withFileName andContentType:#"application/octet-stream" forKey:#"userfile"];
[serverUploadRequest startSynchronous];
This is working fine but when i try to upload the large files some times am getting upload failed error. So is possible to compress and upload the file to server. Am using windows 2003 server with PHP
Thanks

Use Objective-Zip to zip the file.
For more info about its usage, visit this link

May this link useful to you
You can zip file you files before uploading to server.

easy & fast C based zip.
http://code.google.com/p/miniz/source/browse/trunk/miniz.c?r=31

Here is a simple method I used for creating a zip to upload 3 image.
-(void)zipImage:(NSString *) filename: (NSString *) file1: (NSString *) file2: (NSString *) file3{
ZipArchive *zipfile = [[ZipArchive alloc]init];
[zipfile CreateZipFile2:filename];
[zipfile addFileToZip:file1 newname:#"C1.jpg"];
[zipfile addFileToZip:file2 newname:#"C2.jpg"];
[zipfile addFileToZip:file3 newname:#"T1.jpg"];
[zipfile CloseZipFile2];
}
The zip library is miniZip ( http://code.google.com/p/ziparchive/ )
As you can see the initial call is to init the ZipArchive object, next create the zipfile, then just recursively call addFileToZip for each item you want in your file.
P.

Related

iPhone File system operation questions

I want to download files from remote to temp folder
the folder on remote like:
http://remoteserver.com/abc/def/file1.txt
http://remoteserver.com/abc/file2.png
http://remoteserver.com/abc/pla/mnb/file3.html
and the folder structure will like:
tmpefolder/abc/def/file1.txt
tmpefolder/abc/file2.png
tmpefolder/abc/pla/mnb/file3.html
And then after download, will move files to permanent folder like and keep same folder structure
permanentfolder/abc/def/file1.txt
permanentfolder/abc/file2.png
permanentfolder/abc/pla/mnb/file3.html
finally remove all files in tempfolder
So my questions are:
What the best way to download multi files from server? (Better to show ASIHTTPRequest, it is ok to show me other way)
Easy way to create the whole structure of folders? Do I have to split folder path by "/" and check every level path exist and create it?
How to copy whole temp folder content to permanent folder? Is it possible to do this with one operation like copy on OS X?
Also, like remove operation on OS X, remove temp folder with one shot?
Thank you!
1/ You'd better use AFNetwork. ASIHTTPRequest is growing old, no longer maintained. AFNetwork is more modern, and works with blocks (“hmmm, blocks”, like Homer would say). There are plenty of examples around here, just search.
Specifically, AFNetwork allows you to put download operations in a NSOperationQueue, that you can handle at your will, let's say, to download 35 files in parallel, with a maximum of 4 running downloads at the same time, and report to you when everything's done.
2, 3, 4/ Take a look at the reference for NSFileManager. All you need is there.
create .zip of all your file use following code to download .zip form server.
this will create your folder in NSTemporaryDirectory.
NSString *filePath = [NSString stringWithFormat:#"%#/FILENAME.zip",NSTemporaryDirectory()];
[[NSFileManager defaultManager] createFileAtPath:filePath contents:[NSData dataWithContentsOfURL:[NSURL URLWithString:[obj valueForKey:#"zip_path"]]] attributes:nil];
after download move folder to documentDirectory.
[[NSFileManager defaultManager] moveItemAtPath:filePath toPath:[NSHomeDirectory() stringByAppendingPathComponent:#"Documents"] error:nil];
following code is remove files form temp
[[NSFileManager defaultManager] removeItemAtPath:filePath error:nil];

How do I get QuickLook to show offline files?

Our iPad app can show Documents and save them offline when needed.
I've got a QLPreviewController subclass named DocumentViewController (named DVC from now on) for showing them.
Workflow of the app:
- The user clicks a name of a document and the DVC is pushed on to show the document.
- The DVC downloads the file offline and shows it when done.
(So the HTTP URL is downloaded, stored offline, and an offline URL is returned)
The weird thing is, is that only PDF files are working with the offline URL, and the rest crashes.. (it works with online links though)
I did some tests and when I put file:// before the offline link the app does not crash but the DVC is ging me some information about the file (like that it is a excel 97-2004 document).
So some info is transferred, but I can't figure out what the problem is.
Here are some screenshots and after that some code.
code:
Note that Document is a model class with document properties like id, name, file type and url.
//DVC QLPreviewController dataSource method for returning url
- (id <QLPreviewItem>) previewController: (QLPreviewController *) controller previewItemAtIndex: (NSInteger)index
{
[SaveHelper saveDocumentFileAndPropertyWithDocument:document];
//[SaveHelper getDocumentFileWithDocument:document]; without file://
//if I return document.documentUrl it is working with all files except iworks files)
return [SaveHelper getDocumentFileAsPathWithDocument:document]; //with file://
}
//SaveHelper methods
+ (NSString *)documentFilePathWithDocument:(Document *)document
{
return [[self documentFilePath] stringByAppendingPathComponent:[NSString stringWithFormat:#"%#%d.%#", DOCUMENT_FILE_PREFIX, document.documentId, document.documentType]];
}
+ (NSURL *)saveDocumentFileAndPropertyWithDocument:(Document *)document
{
if([self saveDocumentPropertyWithDocument:document])
{
return [self saveDocumentFileWithDocument:document];
}
return nil;
}
+ (NSURL *)saveDocumentFileWithDocument:(Document *)document
{
NSData *data = [NSData dataWithContentsOfURL:document.documentURL];
NSString *fullPath = [self documentFilePathWithDocument:document];
if([[NSKeyedArchiver archivedDataWithRootObject:data] writeToFile:fullPath atomically:YES])
{
return [NSURL fileURLWithPath:fullPath];
}
return nil;
}
+ (NSURL *)getDocumentFileWithDocument:(Document *)document
{
return [NSURL fileURLWithPath:[self documentFilePathWithDocument:document]];
}
+ (NSURL *)getDocumentFileAsPathWithDocument:(Document *)document
{
return [NSURL fileURLWithPath:[#"file://" stringByAppendingPathComponent:[[self getDocumentFileWithDocument:document] absoluteString]]];
}
If more code needed, just say.
EDIT:
When logging the URL passed trough the 'getDocumentFileAsPathWithDocument' method:
url: file:/var/mobile/Applications/xx-xx/Documents/documentFiles/file_20.pdf
url: file:/var/mobile/Applications/xx-xx/Documents/documentFiles/file_80.docx
Where the PDF file is working and the docx not
When I try to load an image(jpg) from local storage I get a black screen with this error message:
warning: Unable to read symbols for /Developer/Platforms/iPhoneOS.platform/DeviceSupport/4.3.5 (8L1)/Symbols/System/Library/Frameworks/QuickLook.framework/DisplayBundles/Image.qldisplay/Image (file not found).
warning: No copy of Image.qldisplay/Image found locally, reading from memory on remote device. This may slow down the debug session.
EDIT:
The webview does not work either with the local urls. PDF is fine but the office files gives an message "Unable to read Document, the file format is invalid". The iWorks documents give the same error as the quicklook. I think its somewhere at the save and load of the format, I savve them as a NSDATA but after that there is no hint for the iPad to see if it is for example a word document (only the extension).
You haven't posted your download code, but I believe that the problem is there. Files from Pages (.pages extension) aren't actual files, they are bundles, i.e. directories that contain files and show as a single item in Finder (look up a .pages file in Finder, right-click it and select 'Show contents'). Downloading a .pages file is actually like downloading a directory: it depends on the web server what kind of result you get but it's most likely an error page.
You could detect that it's a .pages file and try to download all of its contents manually, but you'd have to study the structure of the files to see if that's possible because it's unlikely that you can request the contents of the directory from a web server.
The results for the .ppt and .xls files look normal to me; I think it unlikely that the iPad can preview MS Office documents at all.
Edit: apologies, I just read that iOS can preview MS Office documents. Perhaps the documents get somehow corrupted during download? Have you tried to set your download location to the app's documents folder and enable iTunes file sharing? That way you can download some documents, pull them off your device and then try to open it on your PC to see if that works.
We finally found the solution!
I was right that the problem was with saving the document.
I needed to change the save method in:
+ (NSURL *)saveDocumentFileWithDocument:(Document *)document
{
NSData *data = [NSData dataWithContentsOfURL:document.documentURL options:NSDataReadingUncached error:nil];
NSString *fullPath = [self documentFilePathWithDocument:document];
if([[NSFileManager defaultManager] createFileAtPath:fullPath contents:data attributes:nil])
{
return [NSURL fileURLWithPath:fullPath];
}
//OLD CODE
// if([[NSKeyedArchiver archivedDataWithRootObject:data] writeToFile:fullPath atomically:YES])
// {
// return [NSURL fileURLWithPath:fullPath];
// }
return nil;
}
SO saving it with the filemanager and not with a keyedarchiver.
Did you check if the size of the files is the same both online and offline? It is possible that the file download wasn't complete
Try using the URL of the MS Office documents with a normal NSURL object and opening in a UIWebView. Does it work then (so we know if its the document or your class)?
Try using NSURL's fileURLWithPath: method in the getDocumentFileAsPathWithDocument: It is possible that the URL being returned is incorrect (though doesn't look like it from the logs but doesn't hurt to try)
first of all, use this code to make sure your documents are there,because i think the error cause by your documents path.
NSFileManager *fileManager=[NSFileManager defaultManager];
if([fileManager fileExistsAtPath:fullPath]){
NSLog(#"%# exsit! ",fullPath);
}else{
NSLog(#"%# not exsit! ",fullPath);
}
If any of one have same problem even though you did everything suggestions above.
(I had same problem, when I downloaded some files from google drive.)
Try this!
Put 'x' end of your file extension to be recognized as a new version of format.
(it's working only for 'doc' and 'ppt' files, not for 'xls' files)
Yes, I know this is not a appropriate way to solve this problem, but
it's worth to try it.
Believe me I tried everything!
Hope you help.

ZipArchive memory problems on iPhone for large archive

I am trying to compress multiple files into a single zip archive and I am running into low memory warning. Since the complete zip file is loaded into the memory I guess that's the problem. Is there a way by which I can manage the compression/decompression better using ZipArchive so that not all the data is in the memory at once?
Thanks!
After doing some investigation on alternatives to ZipArchive I found another project called Objective-zip that seems to be a little better than ZipArchive. Here is the link:
http://code.google.com/p/objective-zip/
The API is quite simple. One thing I ran into was that in the begging I was reading data and never releasing it so if you are adding a bunch of large files to the zip file remember to release the data. Here is a little code I used:
ZipFile *zipFile = [[ZipFile alloc] initWithFileName:archivePath mode:ZipFileModeCreate];
for(NSString *path in subpaths){
NSData *data= [[NSData alloc] initWithContentsOfFile:longPath];
ZipWriteStream *stream = [zipFile writeFileInZipWithName:path compressionLevel:ZipCompressionLevelNone];
[stream writeData:data];
[stream finishedWriting];
[data release];
}
[zipFile close];
[zipFile release];
I hope this is helpful for anyone who runs into the same issue.
An easier way to deal with this is to simply change ZipArchive's method of reading the file into the NSData. Just change the following code
data = [ NSData dataWithContentsOfFile:file ];
to
data = [ NSData dataWithContentsOfMappedFile:file ];
That will cause the OS to read the file in a memory mapped way. Basically it just uses way less memory as it reads from the file as it needs to rather than loading it all into memory at once.

Play a wav file retrieved from a database on the iPhone?

I have alot of wav files stored in sqlite3, but when I retrieve one of them, I can't play it. The retrieve code is
NSData *soundData = (NSDATA *)sqlite3_column_blob(statement, 0);
mPlayer = [[AVAudioPlayer alloc] initWithData:soundData error:&error];
The data is stored as binary and it's there when I search for it using sqlite3.
Sorry. Never mind. I just compressed the data more and it works fine now. Seems the number of files is not as important as their size afterall.

How can I read bytes from a file in iphone application, chunk by chunk?

I am trying to implement an iphone application which can read some fixed amount of bytes from a file and store in another file. this process will go on up to the end of the file. I am very new to iphone application so please help me on that . Is there any parent classes out there for this specific type of implementation?
I had a very large file which couldn't be read with NSData methods, so I used the following (per TechZen's suggestion for fine grain control).
NSFileHandle *fileHandle = [NSFileHandle fileHandleForReadingAtPath:filePath];
[fileHandle seekToFileOffset:offset];
NSData *data = [fileHandle readDataOfLength:length];
If you just want to copy the file, use NSFileManager's copy functions.
If you just want specific bytes in a file, you can load the file using NSData's file methods then you can get specific blocks of bytes and write them to file.
If you want more fine grain control, use NSFileHandler.
Edit01:
This page has examples for close to what you want. I don't have anything on hand.