2017-08-13 6 views
0
require 'yaml' 
class Person 
    attr_accessor :name, :age 
end 
fred = Person.new 
fred.name = "Fred Bloggs" 
fred.age = 45 
laura = Person.new 
laura.name = "Laura Smith" 

laura.age = 23 
test_data = [ fred, laura ] 
puts test_data.to_yaml 

#YAML 
- !ruby/object:Person 
    age: 45 
    name: Fred Bloggs 
- !ruby/object:Person 
    name: Laura Smith 
    age: 23 

これは、私が読んでいる本からのYAML直列化の例です。私は、YAML構文を保存/送信するための通常のルビコードとは異なるものを理解するのに問題があります。それが "バイナリシリアル化"のようにバイナリに変換される場合、それはより高速に送信できるように私には意味をなさないでしょう。シリアライゼーションのポイントがオブジェクトの状態を整理してストリームにすることであるならば、なぜそれを元の順序と構文のストリームにしないのですか?JSON構文またはYAML構文を "有線経由で"送信できるのはなぜですか?

+5

"* YAMLの構文は通常のルビコードと何が違うのですか*" - 目的は**データ**を送信することであり、**コード**ではありません。 –

答えて

0

バイナリシリアル化が高速かどうかという疑問について:はい、そうです。あなたがスピードを心配しているなら、YAMLはあなたが望むツールではありません - あなたはCap'n Protoのような他のツールに目を向けるべきです。 YAMLは人間が読めるように設計されています。

なぜRubyコードの代わりにYAMLを送信するのですか?さて、まずはセキュリティ。一方のエンドから他方のエンドにRubyコードが送信され、そこでコードが評価されると、不正な第三者がこのストリームにメッセージを挿入する方法を見つけた場合、これが脆弱になる可能性があります。任意のコードが実行される可能性があります。

実際に任意のRubyコードを送信しないと仮定しましょう。代わりに、送信したいデータに評価される単一の式であるサブセットを送信したいとします。ちなみに、これはJSONが存在するようになった方法です:オブジェクト値を評価するJavaScriptのサブセットとして。

JSONはすでに存在しているため、JSON¹に欠けている機能を追加しない限り、Ruby上でいくつかのシリアライズ言語をベースにしたホイールの発明には何の意味もありません。完全なパーサとエミッタを記述する必要があります(前述のように、攻撃者は任意のコードを実行できるため、Ruby実装を単純に使用することはできません)。また、JSONは広範なプログラミング言語とエコシステムで既にサポートされているため、プラットフォーム間の互換性を重視する場合には理想的なデータ交換形式です。

これで、YAMLがJSONに加えて提供している問題が解決されました。 YAMLの構文は、JSONのYMMVよりはるかに読みやすいと主張する人もいます。しかし、YAMLには、JSONよりも優れた機能がいくつかあります。

  • YAMLには、タイプ付きの注釈コンテンツ用の拡張可能なタグ付けシステムがあります。あなたのコードからの例:!ruby/object:Person。これにより、異なる型の値が発生する可能性のあるデータ構造内のフィールドがある場合、受信側はどのタイプを非直列化に使用するかをすぐに知ることができます。 JSONでは、その決定を行うために型推論(式の値から型を推論する)が必要であり、常に可能ではありません。
  • データ構造にはサイクル(リングリスト、強く接続されたグラフなど)が含まれる場合があります。これらは直列化が困難です。 YAMLにはアンカーとエイリアスが組み込まれており、以前に開始したノードを参照して循環構造を示すことができます。 JSONにはそのようなことはありません。私は、Rubyに似た機能を追加することなく、この機能をRubyベースの直列化言語に含めることは難しいと考えています。
  • 最後に、これはタイトルの質問の答えですが、YAMLはストリーミング用に設計されています(JSONははるかに少ない程度です)。 YAMLストリームには、任意の数の文書を含めることができます。これにより、ストリームを開いたままにして、受信側で新しいデータを待つことが可能になります。対照的に、JSONは、入力が1つのオブジェクトの後に終了することを期待しています。

これは、YAML(またはJSON)が唯一の方法であることを意味するものではありません。データにサイクルや異質なフィールドを持たないでください。アンカー/エイリアスやタグは必要ありません!人が読めるシリアライゼーションは必要ありませんか?あなたはバイナリ形式で行くことができます!JSONとYAMLは、その機能セットが多くのアプリケーションの要件を十分に反映しているため、成功しています。アプリケーションに適したツールであるかどうかは、あなたが決めるまでです。


1確かにいくつかの理由でそれを行うプロジェクトがあります。私が作ろうとしている点は、一般的に、適切な(デ)シリアライゼーションを実装することは複雑な作業であり、通常はそこにあるものを使いたいということです。

{ 
    "type": "myType", 
    "value": ... 
} 

しかし、それは直列化はかなり冗長になるだろう:すべてのノードがこのような構造を持つようにあなたは、もちろん、あなたのJSONスキーマを拡張することができます²

+0

この次の質問で私のリーグから抜け出しましたが、セキュリティが問題であれば、人間が読める逐次化メソッドは簡単にリバースエンジニアリングできませんでしたか?しかし、良い説明が私のために多くをクリアしました –

+1

リバースエンジニアリングは、あなたが*「セキュリティで保護されていない」*システムセキュリティに対する有効なアプローチを考慮しない限り、セキュリティ上の問題ではありません。 – flyx

+1

比較のために:HTMLもプレーンテキスト形式ですが、現在では通常、TLS( - > HTTPS)を介して送信されるため、第三者が読むことも変更することもできません。あなたはYAMLで全く同じことをすることができます。 – flyx

関連する問題