web-dev-qa-db-ja.com

PDFファイルが正しいかどうかを検出(ヘッダーPDF)

多くのPDFファイルを管理するWindows .NETアプリケーションがあります。ファイルの一部が破損しています。

2つの問題:私は私の不完全な英語で説明しようとします...申し訳ありません

1.)

PDFファイルが正しいかどうかをどのように検出できますか?

PDFのヘッダーを読み、それが正しいかどうかを検出したい。

var okPDF = PDFCorrect(@ "C:\ temp\pdfile1.pdf");

2.)

ファイルのバイト[](バイト配列)がPDFファイルかどうか)を知る方法.

たとえば、Zipファイルの場合、最初の4バイトを調べて、それらがローカルヘッダーの署名と一致するかどうかを確認できます。

50 4b 03 04

if(buffer [0] == 0x50 && buffer [1] == 0x4b && buffer [2] == 0x03 && buffer [3] == 0x04)

Longにロードする場合、これは(0x04034b50)です。デビッド・ピアソン

PDFファイルについても同じです。

byte [] dataPDF = ...

var okPDF = PDFCorrect(dataPDF);

.NETのサンプルソースコードはありますか?

21
Kiquenet

1)残念ながら、pdfファイルが破損しているかどうかを簡単に判断する方法はありません。通常、問題のあるファイルには正しいヘッダーがあるため、破損の実際の理由は異なります。 PDFファイルは、事実上PDFオブジェクトのダンプです。ファイルには、ファイルの先頭からの各オブジェクトの正確なバイトオフセット位置を示す参照テーブルが含まれています。そのため、破損した可能性のあるファイルのオフセットが壊れているか、一部のオブジェクトが欠落している可能性があります。

ファイルが破損していると判断する最良の方法は、専用のPDFライブラリを使用することです。 .NETには、このようなライブラリの無料版と商用版の両方がたくさんあります。そのようなライブラリの1つを使用してPDFファイルをロードしてみてください。 iTextSharpが良い選択です。

2)PDF参照に従って、PDFファイルのヘッダーは通常、%PDF-1.Xの形式になっています(Xは0から7までの数値です)。また、PDFファイルの99%にそのようなヘッダーがあります。しかし、Acrobat Viewerが受け入れる他の種類のヘッダーもあり、ヘッダーがないことはPDFビューアにとって実際の問題ではありません。したがって、ヘッダーがない場合は、ファイルを破損したものとして扱わないでください。例えば。ヘッダーは、ファイルの最初の1024バイト内のどこかに表示されるか、%!PS-Adobe-N.n PDF-M.mの形式になります。

参考までに、私は Docotic PDFライブラリ の開発者です。

18
Vitaliy Shibaev

私はヘッダーをチェックしますPDFこのように:

 public bool IsPDFHeader(string fileName)
    {
        byte[] buffer = null;
        FileStream fs = new FileStream(fileName, FileMode.Open, FileAccess.Read);
        BinaryReader br = new BinaryReader(fs);
        long numBytes = new FileInfo(fileName).Length;
        //buffer = br.ReadBytes((int)numBytes);
        buffer = br.ReadBytes(5);

        var enc = new ASCIIEncoding();
        var header = enc.GetString(buffer);

        //%PDF−1.0
        // If you are loading it into a long, this is (0x04034b50).
        if (buffer[0] == 0x25 && buffer[1] == 0x50
            && buffer[2] == 0x44 && buffer[3] == 0x46)
        {
            return header.StartsWith("%PDF-");
        }
        return false;

    }
36
Kiquenet

PDFファイルの最初の行は、ファイルが準拠するPDF仕様のバージョンを識別するヘッダーです%PDF-1.0%PDF-1.1%PDF-1.2%PDF-1.3%PDF-1.4など.

これを確認するには、ファイルの先頭から数バイトを読み取り、PDF file。 PDF reference を参照してください。 =詳しくはアドビから。

あなたに代わって.NETの例はありません(今から何年も触れていません)が、たとえそうであっても、ファイルの完全な有効なコンテンツを確認できるかどうかはわかりません。ヘッダーは大丈夫かもしれませんが、ファイルの残りは台無しになるかもしれません(あなたが言ったように、いくつかのファイルは壊れています)。

8
user159088

正常に動作するPDFは、最初の9バイトが%PDF-1.xと改行(xは0..8)で始まります。 1.xは、PDFファイル形式のバージョンを提供することになっています。 2行目は、アプリケーション(エディタ)がPDFを非ASCIIテキストファイルタイプとして識別できるようにするためのバイナリバイトです。

ただし、このタグはまったく信頼できません。 PDF-1.7の機能を使用しているがPDF-1.4であると主張しているアプリケーションが数多くあり、無効なエラーメッセージを吐き出すように一部の視聴者を誤解させています。 (これらのPDFに最も類似しているのは、ファイルの上位から下位への誤った管理されたPDFバージョンの変換の結果です。)

PDFには「ヘッダー」などのセクションはありません(%PDF-1.xの最初の9バイトは、「ヘッダー」の意味ですか?)。 PDF内にメタデータを保持するための構造が埋め込まれている場合があり、Author、CreationDate、ModDate、Titleなどの情報を提供します。

PDFの破損を確実にチェックするための私の方法

レンダリングすること以外に、PDFの妥当性と破損がないことを確認する方法はありません。

私にとって個人的にそのような妥当性をチェックするための「安く」そしてかなり信頼できる方法は Ghostscript を使用することです。

ただし、これを高速かつ自動的に実行する必要があります。また、この方法をプログラムで、またはスクリプトによるアプローチを使用して、多くのPDFをチェックしたいとします。

ここにトリックがあります:

  • Ghostscriptでファイルをディスプレイまたは実際の(イメージ)ファイルにレンダリングしないでください。
  • 代わりにGhostscriptのnullpageデバイスを使用してください。

次にコマンドラインの例を示します。

gswin32c.exe ^
    -o nul ^
    -sDEVICE=nullpage ^
    -r36x36 ^
    "c:/path to /input.pdf"

この例はWindows用です。 Unixでは、gswin32c.exeおよび-o /dev/nullの代わりにgsを使用してください。

-o nul -sDEVICE=nullpageを使用すると、レンダリング結果は出力されません。ただし、Ghostscriptによるinput.pdfの処理のすべてのstderrおよびstdout出力は、引き続きコンソールに表示されます。 -r36x36は、解像度を36 dpiに設定してチェックを高速化します。

%errorlevel%(Linuxでは$?)は、破損していないファイルの場合は0になります。破損したファイルの場合は0ではありません。また、stdoutに表示される警告またはエラーメッセージは、input.pdfの問題を特定するのに役立ちます。

PDFファイルの破損を確認する方法は、なんとかしてレンダリングする以外にありません...


更新:一方、%PDF-1.0、%PDF-1.1、%PDF-1.2、%PDF-1.3、%PDF-1.4、%PDFだけではありません-1.5、%PDF-1.6、%PDF-1.7、および%PDF-1.8は、有効なバージョンインジケーターですだけでなく、%PDF-2.0。

7
Kurt Pfeifle

ヘッダーの確認は注意が必要です。上記のコードの一部は、すべてのPDFが%PDFで始まるわけではないため、単に機能しません。ビューアで正しく開くPDFには、BOMマーカーで始まるものと、このように始まるものがあります。

------------ e56a47d13b73819f84d36ee6a94183 Content-Disposition:form-data; name = "par" ...など

したがって、「%PDF」のチェックは機能しません。

1
Joost Aarts

iTextSharp を使用してファイルを開いて解析しようとすることもできます(たとえば、テキストをテキストから抽出してみます)が、おそらくやり過ぎです。また、商用ライセンスを購入しない限り、それは GNU Affero GPL であることにも注意してください。

1
Rup

私がしていることは:

1.拡張機能を検証する

2。PDFファイルを開き、ヘッダー(最初の行)を読み取り、次の文字列が含まれているかどうかを確認します: "%PDF-"

3.ファイルに複数の「/ページ」を検索してページ数を指定する文字列が含まれているかどうかを確認します(PDFファイルには常に少なくとも1ページが必要です)

以前に提案したように、ライブラリを使用してファイルを読み取ることもできます。 Reading PDF iTextSharpを使用したファイル

0
Artur Kędzior