39


20

これは以前に寄せられた質問( large-text-and-images-in-sql)ですが、主に変更されるデータ 私の場合、データは保存され、変更されることはありません。 すべてをまとめるのが賢明なようです。

静的バイナリデータをデータベースに格納しないのはなぜですか。

実行するのが賢明なことであると仮定して、そのようなデータを別々のテーブルに格納することに何か利点がありますか? (私はDBの専門家ではないことに気付き始めたかもしれませんが…)

明確にする:たぶん10人から20人のユーザーしかいないだろうが、これらはアメリカとイギリスにいるだろう。 どんな場合でもバイナリデータを転送する必要があります。

11 Answer


33


DBにデータを保存することの利点は、DBセキュリティメカニズムを利用し、メンテナンスコスト(バックアップなど)を減らすことです。 それの不利な点は、DBの負荷が増大し、接続が消費されることです(これは、接続ごとにライセンスを取得したデータベースサーバにとっては高価かもしれません)。 SQL Server 2008を使用している場合は、http://technet.microsoft.com/en-us/library/bb933993.aspx [+ FILESTREAM +]が適切な代替手段になる可能性があります。

ちなみに、Webアプリ(またはデータのストリーミングを必要とする可能性があるその他のアプリ)の場合は、通常、データをDBの外部に保存するほうが賢明です。


10


テーブルにLOBがあるときに巨大なメモリまたは帯域幅の問題、あるいはその両方を引き起こす「テーブルからのselect *」の実行に関するこれまでの話はすべて問題になりません。 返されるのは、問題のLOBへのポインタだけです。 コメントを文脈の中に入れるほどの評判はありませんが、これを見ている人々はそれが問題ではないことを知っているはずです。


9


BLOBを格納している場合の最大の欠点は、メモリ消費量です。 あなたはxからのselect *がそれぞれに45kの画像を持つ何千ものレコードに対して何をするか想像できますか?

Mehrdadが言ったようにまた利点がある。 そのため、このアプローチを採用する場合は、ほとんどのクエリでBLOBデータを使用した場合の結果が少なくなるようにデータベースを設計する必要があります。 たぶん例えばこの目的のために一対一の関係を作る。


6


原則的な観点からこの問題に対処するために、リレーショナルデータベースが(主に)構造化データを格納するためにそこにあります。 クエリ条件を作成したりデータ要素に参加したりできない場合は、おそらくデータベースに属していません。 WHERE句で画像BLOBが使用されているのがわかりませんので、データベースの外に置いてください。 一方、CLOBはクエリで使用できます。


5


私はこれがあなたの建物の用途に依存すると思います。 CMSシステムを構築していて、データの使用方法がWebブラウザ内に画像を表示することである場合、データベースに配置するのではなく、画像をディスクに保存するのが合理的かもしれません。 正直言って私は両方をするでしょう、それは至る所にファイルをコピーする必要なしにファームにサーバーを追加することを可能にします。

もう1つのユースケースは、ワークフローなどの複雑なオブジェクト、あるいは相互依存性が多いビジネスオブジェクトです。 これらの両方をバイナリまたはテキストベースのフォーマットにシリアル化し、それらをDBに保存することができます。 そうすると、DBの恩恵を受けることができます。アトミック、バックアップなど。

そもそも人々が `+ select * +`クエリを使うべきではないと思います。 2つの方法でデータを取得します。1つのメソッドはサマリー情報を返し、2つ目のメソッドはBLOBを返します。 何千もの画像を一度に返す必要があるのは、どうしても想像できません。


4


私はMySQLデータベースに画像を保存するという当初の決断を下したかなり良いサイズのOSSプロジェクトに精通していて、それが彼らがこれまで対処してきたトップ3の悪い考えの一つであることが証明されています。 (「容赦なくリファクタリングする」というのはアナタマであるという事実によって悪化していますが、それはまた別の話です。)

これが引き起こした深刻な問題の中で:

  1. 最大効率データベースサイズ(mysql)を超えています。 (画像に必要な合計スペースは、他のすべてのスペースを少なくとも2桁超えています)。

  2. 画像ファイルは「ファイル性」を失います。 日付サイズなしなど 日付として(冗長に)保存されていない限り(管理にコードが必要です)。

  3. 任意のバイトシーケンスは、保存や操作のために常にうまく処理されるわけではありません。

  4. 「外部から画像にアクセスする必要はありません」というのは危険な想定です。

  5. 脆弱性 全体の配置は不自然で手の込んだものであり、次にどこで噛み付くのかわからないので(反リファクタリングメンタリティに寄与する)。

メリット? それが当時最も抵抗の少ない道であったかもしれないことを除いて、私が考えることができるものはない。


3


データベースに画像(あるいは他のバイナリドキュメント)を保存するという考えを持っていたとしても、私がとても満足している人ではありません。 データベースはINDEXABLE、DISCRETEデータを格納するためのものです。 意味のないバイナリデータのBLOBではありません。 BLOBを使ってバイナリデータを直接扱ったことがあれば、これは既に知っています。

ファイルシステムにファイルへの参照を保存する必要があります。 そのベストプラクティスはファイル名であり、絶対(または相対)パスではありません。


2


添付ファイルはGoogleのシステムに保存されていますが、添付ファイルを変更することはできません。そのため、同じページに "保存され、変更されることはありません"と表示されます。データベースに格納することを_not_に決めました。 これは、単純さとバックアップ/リカバリ時間という2つの理由で行われました。

単純さが優先:私たちの場合、これらの添付ファイルはエンドユーザーのブラウザからアップロードされます。そしてそれらをSQLパイプの下にストリーミングするよりも(DBサーバー上の)ディレクトリに書き込む方が簡単です。 それらのレコードはDBにありますが、DBには添付ファイルに関するメタ情報と、ディスク上のファイルの名前(この場合はguid)が含まれているだけです。

バックアップ/リカバリの面では:これらのBLOBは、おそらくデータベースの中で最も大きな部分の1つになるでしょう。 あなたがフルバックアップを実行するときはいつでも、あなたはその時決して変わることができないことを知っていてもあなたは何度も何度もこれらのビットをコピーすることになるでしょう。 私たちにとっては、(はるかに)小さなバックアップを作成し、バックアップとしてセカンダリサーバーに添付ファイルのディレクトリのxcopyを実行する方がはるかに簡単に見えます。


1


まさにこれがLOBやCLOBなのでしょうか。 設計された?

CLOBを使用して、主要航空会社システムのクレジットカードカード取引の大量の暗号化を保存しました。

しかし、メモリ消費はあなたの最大の原因です。

HTH

乾杯、


1


いくつかのデータベース(例えば。 Postgresql)は自動的にフィールドを圧縮します。おそらく、dbから直接それらを読む方が速いでしょう。 また、プログラムはすべてのフィールドと画像を一気に読み取ることができます。