0

私はDBテーブルをほとんど持っていません.魔女は1つのテーブルからの継承を使用して構築されています魔女は新しいテーブルを作成するための一種の「テンプレート」であり、今では一連のビジネスロジックメソッドがテンプレートから継承された列で機能し、追加の列のみが使用されますモデルのプレゼンテーションのためのパラメーターとして、ロジックには意味がありません。

目標は、すべてのテーブルに沿ってビジネス ロジック メソッドを共有することです。今では、別のクラス ウィッチを追加して CActiveRecord を拡張し、そこからすべてのモデルを拡張するか、ロジックをビヘイビアとしてパックしてモデルに追加することで実行できます。ただし、これには、すべてのテーブル/モデルに対して少なくとも「ダンプ」クラス ファイルを書き込む必要がありますが、それらのテーブルはシステム内で「ライブ」であり、システムのライフ サイクルで削除/作成されます。

パラメータ、テーブル名、またはテーブルのモデルを「オンザフライ」で作成し、それにビジネスロジックを追加する方法として、ある種の「メタモデル」ウィッチを作成する方法はありますか?

私は Yii ユーザー ボードでこの質問をしましたが、何の回答も見つかりませんでした :/ 私はこれをある種のコード チャレンジと考えているので、どんな助けや手がかりも歓迎します :)

[編集]

いくつかのサンプル: さまざまなクライアント デバイスのテーブル

  • hfc.cable_modem
  • lan.switch_port
  • lan.voip_gateway
  • (近い将来、システムに追加される「テクノロジー」が増えるため、クライアント デバイス用の新しいテーブルが追加され、それらの一部のサポートが終了する可能性があります)

すべてのテーブルはテンプレート テーブルから継承します client_device ウィッチには次のフィールドがあります。

  • クライアントID
  • service_id
  • core_device_id
  • (さらに、created、updated、updater などのタイムスタンプ可能な動作のためのいくつかのメタ列)

ビジネスロジックはIDのみで動作し、すべてのテーブルで同じであることがわかります。残りの列は、デバイスパラメーターのストレージ/プレゼンテーション情報として使用されます。

私の目標は、「メタモデル」クライアント デバイスを用意することです。魔女は、このすべてのテーブルにビジネス ロジックを適用し、すべてのテーブルに対して、モデル クラスを記述することなく、特定のフィールドへのアクセスを提供します (魔女 i'新しいテクノロジーが追加されるか、特定のテクノロジーのサポートが将来廃止されるたびに、毎回行う必要があります)

4

1 に答える 1

2

さて、私があなたを正しく理解していれば、私が行っている同様のことに基づいた提案があります:

基本の「機能」モデルがあります。ただし、機能は「テキスト」機能または「画像」機能などにすることができます。ただし、それらはすべて共通の「機能 ID」と他のいくつかの列を共有します。そこで、私は一種のEAVアプローチを取りました。単一の「機能」テーブルがあり、次に各サブタイプ (テキスト、画像など) のテーブルがあります。「機能」テーブルの列の 1 つに、サブタイプ情報が含まれています。次に、基本「フィーチャー」モデルの「afterFind()」メソッドで、サブタイプ列を調べます。サブタイプが「テキスト」の場合、作成した「テキスト」タイプの動作を添付します。この動作は、サブタイプ テーブルから変数を取得し、基本モデルの属性と同様にアクセスできるように設定します。

このようなもの:

client_device_table : (ベース テーブル)
-client_id (プライマリ キー)
-service_id
-core_device_id
-device_type (CableModemBehavior や VoipGatewayBehavior などの動作の名前)

cable_modem_table
-core_device_id
-modem_info_1
-modem_into_2

voip_gateway_table
-core_device_id
-gateway_info_1
-gateway_into_2

ClientDevice CActiveRecord モデル (基本モデル) では:

protected function afterFind() {
  parent::afterFind();
  // remember $this->device_type holds the relevant behavior i.e. CableModemBehavior
  $this->attachBehavior($this->device_type,call_user_func(array($this->device_type, 'model')));
}

そして、動作は次のようになります。

class CableModemBehavior extends CActiveRecordBehavior {
  public modem_info_1;
  public modem_info_2;
  public function attach($owner)
  {
    parent::attach($owner);
    $connection = Yii::app()->getDb();
    $command=$connection->createCommand("SELECT * 
      FROM cable_modem_table 
      WHERE core_device_id=:device_id");
    $command->bindParam(':device_id',$this->owner->core_device_id);
    $data=$command->queryRow();
    $this->modem_info_1 = $data->modem_info_1;
    $this->modem_info_2 = $data->modem_info_2;
  }
}

これはテストされていませんが、CableModemBehaviorを持つ ClientDevice モデルをサブタイプ列エントリとして取得すると、通常の ClientDevice 属性 (client_id) と同様にモデム属性 (modem_info_1) にアクセスできるようになるはずです。

ClientDevice->modem_info_1

もちろん、これ以上のこともあります。これは「検索」の場合のみです。一括属性割り当てを $_POST で機能させるには、またはリレーションを転送するために、または保存と削除などをサポートするために afterDelete、validate、および afterSave メソッドを追加するために、さらに作業を行う必要がありますが、これが役立つことを願っています。始める。

また、ビヘイビアーで基本モデルの __get および __set メソッドをオーバーライドすることで、これをより良くすることもできます。これにより、サブタイプ テーブルの列が要求された場合に、テキスト テーブルから透過的に取得し、スキーマを実行します。列名などを取得するためのルックアップ。この例で行ったようにハードコーディングするよりも優れています。yiiextリポジトリのEavBehavior とAdvancedArBehavior (または同様のもの) を調べて、より滑らかにする方法を理解することをお勧めします。各サブタイプの動作の代わりに、一般的な動作を使用して、サブタイプ テーブル名を渡すだけで済みます。(ああ、私は実際にそれが好きです)

乾杯!

于 2010-08-26T18:28:58.107 に答える