質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Swift

Swiftは、アップルのiOSおよびOS Xのためのプログラミング言語で、Objective-CやObjective-C++と共存することが意図されています

Q&A

解決済

1回答

2259閲覧

mp4ファイルが保存できない

退会済みユーザー

退会済みユーザー

総合スコア0

Swift

Swiftは、アップルのiOSおよびOS Xのためのプログラミング言語で、Objective-CやObjective-C++と共存することが意図されています

0グッド

0クリップ

投稿2022/10/09 08:16

編集2022/10/10 05:27

前提

mp4ファイルをアルバムに保存しようとすると失敗します

実現したいこと

https://hogehoge.com/movie/21838381818.mp4 から動画をダウンロードしてiPhoneのアルバムに保存したいです

アルバムへの保存の流れも知りたいです

発生している問題・エラーメッセージ

Optional(Error Domain=PHPhotosErrorDomain Code=3302 "(null)") Optional("The operation couldn’t be completed. (PHPhotosErrorDomain error 3302.)")

該当のソースコード

swift

1 import Photos 2 3class ViewController: UIViewController, WKUIDelegate, WKNavigationDelegate { 4 5// 保存 6 @IBAction func saveMovie(_ sender: Any) { 7 8 let url = URL(string: self.url!) 9 10 let request = URLRequest(url: url!) 11 12 let task = URLSession.shared.dataTask(with: request) { (data, response, error) in 13 14 if(data == nil){ 15 print("ダウンロード失敗") 16 return 17 } 18 19 if data!.count == 0 { 20 print("中身がない") 21 22 } else { 23 print("ダウンロード開始") 24 25 //ドキュメントフォルダのパス 26 let path = NSSearchPathForDirectoriesInDomains( 27 .documentDirectory, 28 .userDomainMask, true).last! 29 30 //ファイルのパス 31 let documentDirectoryURL = path 32 33 do { 34 //アプリ内に保存 35 try data?.write(to: URL(fileURLWithPath: documentDirectoryURL)) 36 print("documentDirectoryURLは") 37 print(documentDirectoryURL) 38 39 PHPhotoLibrary.shared().performChanges( 40 { 41 PHAssetChangeRequest.creationRequestForAssetFromVideo(atFileURL: URL(string: documentDirectoryURL)!) 42 }, 43 completionHandler: { (success, err) in 44 if success == true { 45 print("保存成功!") 46 } else { 47 print("保存失敗! \(err) \(err?.localizedDescription)") 48 } 49 }) 50 } catch { 51 print(error.localizedDescription) 52 } 53 } 54 } 55 task.resume() 56 } 57} 58
// 出力結果 ダウンロード開始 documentDirectoryURLは /Users/apple/Library/Developer/CoreSimulator/Devices/AE..../data/Containers/Data/Application/98.../Documents

試したこと①

info.plstは設定済みです
イメージ説明

試したこと②

do { try ...} catch {error.localizedDescription} 追記

// 出力結果② The file “Documents” couldn’t be saved in the folder "22-....-.....”.

補足情報(FW/ツールのバージョンなど)

Xcode 13.4

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2022/10/09 10:01

https://stackoverflow.com/questions/61044285/save-video-in-photo-library-swift リンク先などを見ると流れはOKっぽいのでしょうかね。 気になったのは次のコードです。 `try? data?.write(to: URL(fileURLWithPath: documentDirectoryURL))` tryの部分でエラーをオプショナルな値に変換するのではなく、 エラーの場合はどのようなエラーが発生しているのか把握するために do-catchステートメントで処理してみたらいかがでしょうか。
退会済みユーザー

退会済みユーザー

2022/10/10 05:25

コメントありがとうございます。 do { try...} catch { print(error.localizedDescription)} でやると `The file “Documents” couldn’t be saved in the folder “22...-....”.` と出るのでファイル名の重複が原因かもしれません
guest

回答1

0

ベストアンサー

コメントありがとうございます。

リンク先のコードも読んでみると良いと思います。

let dataPath = documentsDirectory.stringByAppendingPathComponent("/videoFileName.mp4")
https://stackoverflow.com/questions/61044285/save-video-in-photo-library-swift

Documentsはディレクトリですので、
stringByAppendingPathComponentでファイルを指定する形になっているみたいです。

追記です。

コメントありがとうございます。
サンプルコードも含めて追記します。

他の青アプリで当該URL(...mp4)をダウンロードしたり保存することは可能です。

こちらはmp4ファイル自体は問題なさそうなのですね。
関係しているかわからないので念の為の確認ですが、ファイルサイズはどれくらいでしょうか?

ちょっとわからなくなってきました、、

一度に全ての問題を対処しようとすると混乱してしまいますので、
1つずつゆっくり確認すると良いと思います。

処理の流れは次のような感じになりますので、
上から順番に、それぞれのポイントで正しく処理ができているか
確認してみると良いと思います。

  1. mp4ファイルダウンロード
  2. ドキュメントディレクトリに保存する([Product]-[Run]するたびにアプリのディレクトリが変わる?ため注意)
  3. 写真アプリに保存する

ちょっと細かい実装は違いますが、
手元の環境(Xcode 14.0)で再現確認したコードも記載しておきます。

swift

1 func action() { 2 Task { 3 // ダウンロード 4 let url = URL(string: "http://localhost:1313/test.mp4")! 5 let (data, response) = try await URLSession.shared.data(from: url) 6 guard let httpResponse = response as? HTTPURLResponse, 7 httpResponse.statusCode == 200 else { 8 print("response: \(response)") 9 return 10 } 11 // ドキュメントディレクトリに保存する 12 let urlDocumentDirectory = try! FileManager.default.url(for: .documentDirectory, in: .userDomainMask, appropriateFor: nil, create: false) 13 let urlFilePath = urlDocumentDirectory.appendingPathComponent("download.mp4") 14 print(urlFilePath) 15 try! data.write(to: urlFilePath) 16 // 写真アプリに保存する 17 PHPhotoLibrary.shared().performChanges { 18 PHAssetChangeRequest.creationRequestForAssetFromVideo(atFileURL: urlFilePath) 19 } completionHandler: { success, error in 20 if let error = error { 21 print("error: \(error)") 22 return 23 } 24 print("success: \(success)") 25 } 26 } 27 }

投稿2022/10/10 05:31

編集2022/10/12 05:06
退会済みユーザー

退会済みユーザー

総合スコア0

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2022/10/10 06:20

リンク先の `solution` のコードをアレンジしてみましたが ・アプリ内への保存→成功 ・iPhoneのアルバムへの保存→失敗 でした。
退会済みユーザー

退会済みユーザー

2022/10/10 06:54

コメントありがとうございます。 > ・iPhoneのアルバムへの保存→失敗 エラーは何か出力されていますでしょうか? 最初にアクセスする際に許可設定をしますが、写真への許可はされた状態になっていますでしょうか? 設定ープライバシーとセキュリティー写真ーアプリの名前ー「写真の追加のみ or すべての写真」
退会済みユーザー

退会済みユーザー

2022/10/10 09:43

・エラーは何も出ていないです。 ・許可等は質問内容でも画像を添付しています。 (間違えていたらご指摘ください)
退会済みユーザー

退会済みユーザー

2022/10/10 09:49

コメントありがとうございます。 エラーは出力されていないのですね・・ 「・iPhoneのアルバムへの保存→失敗」というのは、写真アプリに保存されていないということで判断されたのでしょうか? (その場合、何かしらエラーが出力されるような気もしますよね・・) > ・許可等は質問内容でも画像を添付しています。 Info.plistは開発者側で設定する内容だと思います。 それとは別に、アプリの利用者側が設定する内容が次のものになります。 設定ープライバシーとセキュリティー写真ーアプリの名前ー「写真の追加のみ or すべての写真」 開発者側が許可を求めるように設定しておいても、利用者が許可しなければ写真アプリにアクセスすることができない仕組みになっていると思います。
退会済みユーザー

退会済みユーザー

2022/10/10 13:43

> (その場合、何かしらエラーが出力されるような気もしますよね・・) 少しコード修正して現在は以下のエラーが出ます。 ・Optional(Error Domain=PHPhotosErrorDomain Code=3302 "(null)") Optional("The operation couldn’t be completed. (PHPhotosErrorDomain error 3302.)") or ・Optional("The operation couldn’t be completed. (PHPhotosErrorDomain error -1.)") > 開発者側が許可を求めるように設定しておいても、利用者が許可しなければ写真アプリにアクセスすることができない仕組みになっていると思います。 こちら実機、シュミレーター共に表示されたアラートで許可を選択しております 設定ープライバシーとセキュリティー写真ーアプリの名前ー「写真の追加のみ or すべての写真」で確認しても『写真の追加のみ』がちゃんとtrueになっております その他 ・実機のストレージを確認(十分余裕がありました) ・ファイルパスに余分な文字列がないか確認しましたがありませんでした 投稿した内容の実装を探してみても意外と見当たらなくて非常に困っています..
退会済みユーザー

退会済みユーザー

2022/10/10 14:07

> 少しコード修正して現在は以下のエラーが出ます。 また少し後退してしまったようですね。 おそらくドキュメントディレクトリにファイルが正しく保存できていないように見えます。 > 『写真の追加のみ』がちゃんとtrueになっております こちらは大丈夫そうですね。 > 投稿した内容の実装を探してみても意外と見当たらなくて非常に困っています.. https://stackoverflow.com/questions/61044285/save-video-in-photo-library-swift このリンク先のコードを少し修正して手元の環境(Xcode 14.0)で再現確認してみたところ、ちゃんと写真アプリに取り込めたのですけどね・・ > ・エラーは何も出ていないです。 3つ前のコメントのこの状況につきまして、そもそも対象のmp4ファイルは、開発中のアプリを通さずに(AirDropなどで)写真アプリに取り込むことが可能なものでしょうか?
退会済みユーザー

退会済みユーザー

2022/10/12 04:35

返信遅くなりました。 > おそらくドキュメントディレクトリにファイルが正しく保存できていないように見えます。 https://qiita.com/t_punch/items/edab6f323e823be4f527 の内容で確認するとドキュメントにはファイルが1つも存在しなかったです > 開発中のアプリを通さずに(AirDropなどで)写真アプリに取り込むことが可能なものでしょうか? はい。 他の青アプリで当該URL(...mp4)をダウンロードしたり保存することは可能です。 ちょっとわからなくなってきました、、
退会済みユーザー

退会済みユーザー

2022/10/14 05:32

ありがとうございます。 ただまだ一部の動画が `error: Error Domain=PHPhotosErrorDomain Code=3302 "(null)"` を吐きます。 もう少し調べてわからなくなったら再度質問投稿いたします。 回答していただきありがとうございます。
退会済みユーザー

退会済みユーザー

2022/10/17 14:08

(保存できないファイルも保存できるようになりました。稀にmp4ファイルが含まれないURLが混在するケースがある事が判明しました。API側の問題でした。それらを解消する処理を追加することで無事全てダウンロードできるようになりしました。回答していただお陰で処理が進みました。ありがとうございます。)
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問