ユニバーサルデータコンテナ

過去5年間、私はほとんどの場合、最大の柔軟性、拡張性、適応性のアイデアに基づいたMagentoベースのアプリケーションを扱ってきました。 Magentoのeコマースでの人気と、サードパーティの拡張モジュールの数は、このプラットフォームとそこに実装されたアイデアがその逆よりも成功していることを示しています。 多数のオブジェクトは、Magentoのユニバーサルデータコンテナ(Magento 1のVarien_ObjectおよびMagento 2の\ Magento \ Framework \ DataObject )の概念に基づいています。 私はそのような普遍的なコンテナと同様の類似点を見つけます そして最後に-1930年代にハワードエイケンによって開発されたハーバードコンピュータアーキテクチャを使用します。

「ユニバーサルデータコンテナ」とは何ですか?

これは通常の連想配列であり、各キーが他の連想配列を含むいくつかのデータに対応するマップです。 したがって、コンテナには、1つのエントリポイントがあり、閉じたループがないデータツリーが含まれます(非常に望ましい状態)。 次のようなもの:
$customer = ['Id' => 21, 'Name' => 'Janis Zarinsh']; $order = ['Id' => 32, 'Amount' => 43.32, 'Currency' => 'EUR']; $data = []; $data['Customer'] = $customer; $data['SaleOrder'] = $order;
      
      



ツリーの「リーフ」またはツリーの一部(サブツリー)は、「by」でアドレス指定されます-ゴールまでのすべてのキーをリストすることにより:
  $orderId = $data['SaleOrder']['Id'];
      
      



マジックメソッドを使用するPHPでは、次の形式で同じものを実装できます。
  $customer = new DataObject(['Id' => 21, 'Name' => 'Janis Zarinsh']); $order = new DataObject(['Id' => 32, 'Amount' => 43.32]); $order->setCurrency('EUR'); $data = new DataObject(); $data->setCustomer($customer); $data->setSaleOrder($order);
      
      



より馴染みのある形式でのアドレス指定(* nixのファイルパスとして):
  $orderId = $data->getData('/SaleOrder/Id');
      
      



その結果、何が得られますか? データを転送するためのコンテナ。 JavaのPOJOに類似したオブジェクトの開発者によるPHPの記述は、IDEの自動補完を使用できるように、アクセサー(get / setメソッド)に注釈を付けることになります。 @propertyアノテーションでも同じことができますが、さらに短くなります( get、 setを使用してDataObjectの異なる実装が必要になります)が、私にとっては次のように便利です。
 /** * @method array getBaseCalcData() * @method void setBaseCalcData(array $data) * @method array getDependentCalcData() * @method void setDependentCalcData(array $data) */ class GetForDependentCalc extends DataObject {}
      
      



このオブジェクトの作成者として、私は自分の目的で使用するプロパティを特定しました。 ユニバーサルコンテナは、使用するデータをあるデータプロセッサから別のデータプロセッサに転送し(たとえば、サービスの1つから別のサービスに)、輸送中に他のデータが追加されても(たとえば、完全に記述された拡張子によって)別の開発者によって)。 さらに、ユニバーサルコンテナを「教える」ことで、そこに格納されているデータをJSONなどの形式に自動的に変換し、このデータをサーバー側からブラウザに転送できます。 また、コンテナは、データとともに、サーバー側のコードのサードパーティ拡張によって準備され、クライアント側のコードのサードパーティ拡張によって使用されるデータを変換します。どういうわけか、ユニバーサルデータコンテナは、オブジェクト指向のパラダイムと矛盾し、アプリケーション内のクリーンなデータオブジェクトとオブジェクトを分離しますハンドラー。 しかし、これはむしろ矛盾ではなく、POJOのようなOOPを使用する境界的なケースです。 ユニバーサルデータコンテナは、RDBMSと同様にOOPと共存できます。結局、RDBMSは一種の「ユニバーサルデータコンテナ」でもあります。 理論的には、任意のデータベースを連想配列に配置できます(ハンドラーではなくデータについて話している場合-トリガー/プロシージャ/関数)。

「動物園でこのチューニングが必要なのはなぜですか?」

拡張性

Magentoは、オンラインストアを作成するためのプラットフォームとしての主な目的に加えて、その基本機能の拡張機能を作成するための環境でもあります。 非常に多くのMagentoプラグインがあります-シンプルで複雑、無料で商用です(その一部は非常に高価です)。 そして、ユニバーサルデータコンテナは、そのアーキテクチャの基本概念です。 確かに、Magentoでは、システムの他のほとんどのコンポーネント(親クラス)を構築するためのカーネルとして主に使用され、「純粋なデータ」ではありません。 それでも、Magentoは彼だけではなく、その拡張性を負っています。 このようなアプローチは、サードパーティの開発者による拡張機能の作成に対するオープン性を示唆するプラットフォームで役立ちます。

「深宇宙」

アプリケーションを統合するのは、すべてがアプリケーションを処理するということです。 原則として、データはデータベースに格納され、そこから取得され、ビジネスロジックのレイヤーによって戻され、UIレベルでユーザーフレンドリな形式で表示するために変換されます。そこでユーザーから取得され、処理および後続の格納に便利な形式に変換されます。 Webアプリケーションでは、ほとんどの場合、データは1つの「ユニバース」(ビジネスロジックのサーバーレイヤー、たとえばPHP)から別の「ユニバース」(JavaScriptのクライアントプレゼンテーションレイヤー)に転送されます。 そして、この旅では、原則として、データのみが送信されます-JSON / XML / ...の形式ですべての機能はそのまま残り、単に「他のユニバース」には適用されません。ユニバーサル「ユニバース」データコンテナ(PHP)はそのデータをトランスコード(JSONなど)を「ユニバースB」(JavaScript)に送信するか、別のトランスコード(XMLなど)に変換して「ユニバースC」(JavaのSOAPサービスなど)に送信します。 または、「B」は最初にデータを変換して「C」に送信し、次に「C」から応答を受信し、「A」に処理して送信します。必要に応じて「A」はそれ自体を「C」に変更できます。 最も重要なのは、各「ユニバース」のユニバーサルコンテナがトランスコード(JSON / XML / YAML / ...)を解析および生成し、アプリケーション自体の開発者が入れたデータ(「A」)だけでなく、そのランタイム環境に適応できることです。サービスの開発者(「C」)またはクライアント(「B」)が「パッケージ」に添付した追加データ。

柔軟なパイプライン

関数では複数の引数を指定できますが、通常は結果のみが返されます。
 function tooManyArgs($arg1, $arg2, $arg3) {}
      
      



1つの引数(および関数の結果)を使用して、プロセッサ関数への入力引数の数を制限する場合:
 function oneArgOnly($data) {}
      
      



プロセッサ関数のチェーンという形で非常に興味深い結果を得ることができます。この場合、一部の関数の出力は他の関数への入力になります。 このアプローチの実用的なアプリケーションの例は、JavaScriptのpromiseです。
 httpGet(...) .then(...) .then(...) .then(...)
      
      



PHPでは、ハンドラーパイプラインは次のようになります。
 function proc5(DataObject $arg) { $result = new DataObject(); $customer = $arg->getData('/Customer'); $order = $arg->getData('/SaleOrder'); // ... $result->setData('/Transaction', $trans); return $result; } function proc6(DataObject $arg) { $result = new DataObject(); $transaction = $arg->getData('/Transaction'); // ... $result->setData('/Balance', $balance); return $result; } $res5 = proc5($data); $res6 = proc6($res1); $amount = $res6->getData('/Balance/Amount');
      
      



同様のプロセッサ関数のセットから記述レベルでデータ処理ストリームを構築できます。
 <workflow> <step id="5"> <handler id="proc5"> <input> <map as="/Customer"> <handler>proc3</handler> <result/> </map> <map as="/SaleOrder"> <handler>proc4</handler> <result/> </map> </input> </handler> </step> <step id="6"> <handler id="proc6"> <input> <map as="/Transaction"> <handler>proc5</handler> <result/> </map> </input> </handler> </step> </workflow>
      
      



処理されたデータに応じて変更します。
 <workflow> <step id="7"> <case> <condition if="qt"> <left output="proc5">/Balance/Amount</left> <right>0</right> </condition> <then> <handler id="proc7">...</handler> </then> <else> <handler id="proc8">...</handler> </else> </case> </step> </workflow>
      
      



彼らが言うように、この技術は「昼食で百年」になるでしょうが、それは独自のニッチを持っています。

合計

私の観点からは、コードとデータを分離するためのハワード・エイケン氏の「ハーバード・アプローチ」は、ソフトウェア開発の分野における興味深いソリューションの十分な数の基礎になります。 「見てみよう!」 (c)S. S.ゴルブンコフ



All Articles