3
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

HTTPで取得したファイルをPDFか判定

Posted at

はじめに

swiftのPDFKitを使ったPDFビューアーを作る時に、httpでダウンロードしたファイルがPDFかどうかを判定する必要がありました。PDFの判定方法とswiftでの実装を書きます。

PDFの判定

Webサーバから、HTTPでダウンロードしたコンテンツがPDFか判定するのは、以下の2種類がありました。サーバからの応答メッセージ中のHTTPヘッダを見ることで、PDFか判定できそうです。

  1. Content-Type: ブラウザ中でPDFが表示される
  2. Content-Disposition: PDFがダウンロードされる

1. Content-Type

ブラウザでPDFが表示されるパターンです。HTTPヘッダには、以下の文字列が存在しています。このヘッダが存在する時には、PDFファイルと認識できます。

Content-Type: application/pdf

2. Content-Disposition

ブラウザでPDFがダウンロードされるパターンです。HTTPヘッダには、以下の文字列が存在しています。ファイルの拡張子が.pdfの場合に、PDFファイルと認識することにします。

Content-Disposition:attachment;filename='downloaded.pdf'

SWIFTでの実装

上記のPDF判定をSWIFTで記載したコードです。以下の開発環境での動作は確認しています。

開発環境

このコードの実装環境は以下です。

  • Xcode : 11.1
  • iOS : 13.2

PDF判定コード

URLを引数に渡し、戻り値でPDFの判定をするコードです。semaphoreを使って、PDF判定が完了してから判定結果を戻り値で戻します。webサーバからの応答を待つので、Mainスレッドで使えるコードではありません。必要があれば、semaphoreをやめて、非同期で実装してください。

    private func isPdf(url: URL) -> (Bool) {
        var result: Bool = false
        var request = URLRequest(url: url)
        request.httpMethod = "HEAD"
        let semaphore = DispatchSemaphore(value: 0)
        URLSession.shared.dataTask(with: request) { (data, urlResponse, error) in
            guard let urlResponse = urlResponse as? HTTPURLResponse else {
                // レスポンスなし
                result = false
                semaphore.signal()
                return
            }
            if let contentType = urlResponse.allHeaderFields["Content-Type"] as? String {
                if contentType.contains("application/pdf") {
                    result = true
                    semaphore.signal()
                    return
                }
            }
            if let contentDisposition = urlResponse.allHeaderFields["Content-Disposition"] as? String {
                if contentDisposition.contains(".pdf") {
                    result = true
                    semaphore.signal()
                    return
                }
            }
            result = false
            semaphore.signal()
        }.resume()
        semaphore.wait()
        return result
    }

参考文献

3
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?