开发者

[OSX Core Foundation]How can I asynchronously upload a file though HTTP and get a callback called while sending bytes of the stream?

开发者 https://www.devze.com 2023-01-28 03:32 出处:网络
on MacOSX, wit开发者_如何学Goh Core Foundation, I want to upload a large file (several hundreds of megabytes) to a remote server through a REST API.

on MacOSX, wit开发者_如何学Goh Core Foundation, I want to upload a large file (several hundreds of megabytes) to a remote server through a REST API. Since the file is big and I also need to give the user some feedback, I want to implement a resume upload feature and gives the user feedback on the number of bytes written.

I first followed the Apple Guide for CFNetwork programming: http://developer.apple.com/library/ios/#documentation/Networking/Conceptual/CFNetwork/CFFTPTasks/CFFTPTasks.html#//apple_ref/doc/uid/TP30001132-CH9-SW1 But the asynchronous upload of file is for FTP only.

I tried to use CFReadStreamCreateForHTTPRequest butI only got callbacks on response. I tried with CFReadStreamCreateForHTTPStreamedRequest and I set a delegate on the ReadStreamRef body parameter but it is never called even though I open the stream before actually scheduling it on the runloop.

If somebody has some tips about how to do it, it would be great. Thanks a lot!

-- Rémy


I got an answer here: http://lists.apple.com/archives/macnetworkprog/2010/Dec/msg00000.html.

CFReadStreamCreateForHTTPStreamedRequest is the good function to use.

For upload feedback, I use a timer scheduled on the runloop when creating the request:

CFRunLoopTimerCreate(kCFAllocatorDefault, 0, 10.0, 0, 0, ...);

For resume, there are two steps.

Seek the local content stream at the good offset

Once the local content stream created (but not yet opened), I can seek in it using

CFReadStreamSetProperty(content_stream, kCFStreamPropertyFileCurrentOffset, uploaded_length);

Configure http headers

I don't have webdav style remote server, so I use HTTP Range headers to inform the server about which part of the file I want to upload. This step depends on what the remote server expects.

CFHTTPMessageSetHeaderFieldValue(request_headers, CFSTR("Range"), content_range_value);

Hope this will help.

0

精彩评论

暂无评论...
验证码 换一张
取 消