하나의 문제는 당신이 메모리에 비디오를 (매우 클 수 있음)로드하려고하는 것입니다 NSData
입니다. 대신에 영구 저장 장치에서 파일을주고받을 수 있다면 훨씬 좋습니다. 더 이상 사용되지 않는 NSURLConnection
메서드 인 sendSynchronousRequest
을 사용하는 대신 NSURLSession
다운로드 작업을 사용하여이 작업을 수행 할 수 있습니다.
NSURLSession
다운로드 작업을 사용하면 한 번에 큰 비디오를 메모리에 보관하는 것을 피할 수 있으며 대신 비디오를 영구 저장소로 직접 스트리밍합니다. (즉, 사용되지 않는 방법 NSURLConnection
의 sendSynchronousRequest
와 같은 메모리 풋 프린트 문제가되므로, NSURLSession
데이터 작업을 사용하지 마십시오.)
NSURLSession
다운로드 작업이 영구 저장 장치에 다운로드 직접 스트리밍되면, 당신은 다음 수 파일을 임시 파일로 이동 한 다음 NSData
이 아닌 파일 URL을 다시 제공하여 addResourceWithType
을 사용하십시오.
나는 잘 작동하는 듯 (그리고 확인 다른 유용한 오류 추가)했을 때 : NSURLSession
확실히 만드는 방법에 대한 더 엄격한 때문에
func downloadVideo() {
let fileManager = NSFileManager.defaultManager()
// create request
let url = NSURL(string: "http://www.sample-videos.com/video/mp4/720/big_buck_bunny_720p_10mb.mp4")!
let task = NSURLSession.sharedSession().downloadTaskWithURL(url) { location, response, error in
// make sure there weren't any fundamental networking errors
guard location != nil && error == nil else {
print(error)
return
}
// make sure there weren't and web server errors
guard let httpResponse = response as? NSHTTPURLResponse where httpResponse.statusCode == 200 else {
print(response)
return
}
// move the file to temporary folder
let fileURL = NSURL(fileURLWithPath: NSTemporaryDirectory())
.URLByAppendingPathComponent(url.lastPathComponent!)
do {
try fileManager.moveItemAtURL(location!, toURL: fileURL)
} catch {
print(error)
return
}
// now save it in our photo library
PHPhotoLibrary.sharedPhotoLibrary().performChanges({
PHAssetCreationRequest.creationRequestForAsset().addResourceWithType(.Video, fileURL: fileURL, options: nil)
}, completionHandler: { success, error in
defer {
do {
try fileManager.removeItemAtURL(fileURL)
} catch let removeError {
print(removeError)
}
}
guard success && error == nil else {
print(error)
return
}
print("SUCCESS")
})
}
task.resume()
}
참고 :
// make sure it's authorized
PHPhotoLibrary.requestAuthorization { authorizationStatus in
guard authorizationStatus == .Authorized else {
print("cannot proceed without permission")
return
}
self.downloadVideo()
}
당신은 안전하지 않은 요청을 수행하지 않으므로 info.plist
(오른쪽 클릭하고 "다른 이름으로 열기"- "소스 코드"를 선택하십시오)를 업데이트하여 파일에 추가하십시오 :
<dict>
<key>NSExceptionDomains</key>
<dict>
<key>sample-videos.com</key>
<dict>
<!--Include to allow subdomains-->
<key>NSIncludesSubdomains</key>
<true/>
<!--Include to allow HTTP requests-->
<key>NSTemporaryExceptionAllowsInsecureHTTPLoads</key>
<true/>
<!--Include to specify minimum TLS version-->
<key>NSTemporaryExceptionMinimumTLSVersion</key>
<string>TLSv1.1</string>
</dict>
</dict>
</dict>
그러나 그 모든 작업을 수행하면 비디오가 다운로드되어 내 사진 라이브러리에 성공적으로 추가되었습니다. 또한 동기화 요청 (거의 확실하게 메인 대기열에 있지 않음)을 거의 수행하지 않으므로 여기에서 모든 동기 요청 (NSURLSession
은 비동기식입니다 (performChanges
))을 제거했습니다.
출처
2016-08-03 04:33:04
Rob
'try! '를 사용하는 대신'do'-'try' -catch' 패턴을 사용하고 결과로 나오는'error' 객체를 출력하십시오. 보다 의미있는 오류 메시지를 줄 수 있습니다. – Rob
다음과 같이하면 비슷한 오류가 발생합니다. 오류 도메인 = NSCocoaErrorDomain 코드 = -1 "(null)" – user2658229
iOS 프로그래밍에 익숙하지 않으므로 계속 배우고 있습니다. 미안하지만 당신이 말하는 localizedDescription과 userInfo는 무엇입니까? 그리고 네, 응용 프로그램이 요청하고 사진 라이브러리에 대한 액세스 권한이 있습니다. – user2658229