fs.stat(filename, function(error, stat) {
if (error) { throw error; }
res.writeHead(200, {
'Content-Type' : 'application/zip',
'Content-Length' : stat.size
});
});
Node.js 檔和 iOS 專案筆者放在 GitHub/iOS_unzip。接下來就是 iOS 的部分了,筆者採用的 Zip/Unzip 套件為 ZipArchive 提供的第三方套件。下載後會看到如下的資料夾內容。
接下來開啟 Single View Application。如下,命名為 UnzipDemo
把 ZipArchive 的檔案全加到 UnzipDemo 裡。如下
在 ZipArchive 的文件有提到,要在存案加入 libz.dylib。如下
加入之後會看到如下圖,才是正確的
加入之後,我們立馬 Compile 執行看看,卻看到如下的 Error
原來是 ZipArchive 這個專案有用到 dealloc 等 ARC 開啟時不允許的關鍵字,因為引入的檔案不多,直接把某幾個 file 設定會不支援 ARC 就好了,如下設定。
現在 Compile 就可以成功執行了。
接者來看到功能面,新增一個 UIButton 和連結一個 IBAction 如下圖
在 ViewController.m 新增如下程式碼,先來把 Server 的 developer.zip 下載到 Mac 某個資料夾。在這邊的例子,是用 GET 連結 http://127.0.0.1:8800/data?fileName=developer.zip 然後存到 /Users/chronoer/developer/developer.zip ,先做這樣的測試。
#define SERVER @"http://127.0.0.1:8800/data"
@interface ViewController (){
NSString * fileName;
}
@property (strong) NSMutableData * tmpData;
@end
@implementation ViewController
@synthesize tmpData;
- (IBAction)downZip:(id)sender {
fileName = @"developer.zip";
NSURL * fileURL = [NSURL URLWithString:[SERVER stringByAppendingFormat:@"?fileName=%@", fileName]];
NSURLRequest * urlRequest = [NSURLRequest requestWithURL:fileURL];
[NSURLConnection connectionWithRequest:urlRequest delegate:self];
}
-(void) connection:(NSURLConnection *)connection didReceiveData:(NSData *)data{
[self.tmpData appendData:data];
}
-(void) connectionDidFinishLoading:(NSURLConnection *)connection{
NSString * filePath = [[self fakeDoc] stringByAppendingFormat:@"/%@"fileName];
[[NSFileManager defaultManager] createFileAtPath:filePath contents:self.tmpData attributes:nil];
}
-(NSString *) fakeDoc{
return @"/Users/chronoer/developer";
}
首先有一個 ivar fileName 用來設定要抓取的 zip 檔名,還有一個 tmpData,要去收集從 Server 來的 binary 的片段。在 downZip: 這個 IBAction 我們看到用 NSURLConnection 去連結 http://127.0.0.1:8800/data?fileName=developer.zip 然後指定 delegate 為 self,所以接下來至少要實作
-(void) connection:(NSURLConnection *)connection didReceiveData:(NSData *)data{
[self.tmpData appendData:data];
}
和
-(void) connectionDidFinishLoading:(NSURLConnection *)connection{
NSString * filePath = [[self fakeDoc] stringByAppendingFormat:@"/%@", fileName];
[[NSFileManager defaultManager] createFileAtPath:filePath contents:self.tmpData attributes:nil];
}
這兩個 delegate method。其中
[self.tmpData appendData:data];
就是把每個 zip file 小片斷收集到 tmpData,而整個檔案都收集完整就會呼叫 connectionDidFinishLoading: ,如下我們就把 self.tmpData 的完整資料存在 /Users/chronoer/developer/developer.zip。
NSString * filePath = [[self fakeDoc] stringByAppendingFormat:@"/%@", fileName];
[[NSFileManager defaultManager] createFileAtPath:filePath contents:self.tmpData attributes:nil];
developer.zip 要預先放在 server 的資料夾,然後 /Users/chronoer/developer 這個目錄也要存在。最後就是 unzip 的部分了,在 ViewController.m import 如下
#import "ZipArchive.h"
然後新增一個 method 為 unzipFile
-(void) unzipFile:(NSString * ) zipFilePath{
ZipArchive *zipArchive = [[ZipArchive alloc] init];
[zipArchive UnzipOpenFile:zipFilePath ];
[zipArchive UnzipFileTo:[self fakeDoc] overWrite:YES];
[zipArchive UnzipCloseFile];
}
非常單純的 4 個步驟,先 alloc ZipArchive 的物件,然後指定要開啟的 zip 檔,用
[zipArchive UnzipOpenFile:zipFilePath ];
再來就是把這個 zip 檔解壓縮到指定的目錄底下,並設定為 overWrite
[zipArchive UnzipFileTo:[self fakeDoc] overWrite:YES];
結束就是關掉和這個 zip 相關連結,
[zipArchive UnzipCloseFile];
好啦,今天教學到這,咱們下次見。
沒有留言:
張貼留言