2016-09-01 43 views
6

在以前的CakePHP版本中,您可以暫時更改與Table::bindModel('SomeModel');的關聯,但我無法弄清楚如何在v3中執行此操作。如何在CakePHP v3中動態刪除關聯

我想臨時禁用Table類中定義的hasMany關聯,因爲當我運行在該表存在之前寫入的較舊遷移時會導致錯誤。我不完全理解遷移問題,但當我在Table類中註釋掉關聯時,它立即消失。

class AgenciesTable extends Table 
{ 
    public function initialize(array $config) 
    { 
     parent::initialize($config); 

     $this->table('agencies'); 
     $this->displayField('full_name'); 
     $this->primaryKey('id'); 
     $this->addBehavior('Timestamp'); 

     $this->hasMany('Routes'); 

enter image description here

+1

這只是一個猜測,但我認爲它沒有在cake3中實現。原因可能是,在find()調用中「包含」表之前,cake實際上並沒有調用關係。因此,如果沒有包含路由的find()調用,ake將不檢查該表是否存在。 – arilia

回答

1

這裏的問題是,使用遷移時,你應該依賴於實際的模型類。這可能會導致剛遇到的問題。

而是直接使用TableRegistry或Table對象並創建一個沒有任何依賴關係的表對象。直接在該對象上加載你需要的關聯。

$agencies = new Table(['table' => 'agencies', /*...*/]); 
$agencies->belongsTo('Whatever'); 
/* Do your data manipulation */ 

這樣,無論您對AgenciesTable類進行了哪些其他更改,遷移都可以正常工作。這是恕我直言,它是在遷移中的正確方式。

我認爲,即使您沒有通過調用$this->hasMany('Routes');來明確創建關聯,您最終也會得到相同的錯誤,因爲預先加載器仍然會嘗試查找匹配的表類並動態加載它。這也是爲什麼沒有「無法」方法的原因。

此外,你沒有顯示你的實際查詢代碼...所以我假設你調用一個自定義的查找或方法調用查詢:: contains()的地方。只寫一個沒有包含的新查詢?

$agencies->find()->contain(['One', 'Two'])->where([/*...*/])->all(); 

如果你有一個大的查詢這可能是一個好主意,把它分解成多個自定義的發現,因爲它們可以組合:

$agencies->find('withoutMyContain')->all(); 
$agencies->find('withoutMyContain')->find('withMyContain')->all(); 

Custom Finder Methods

+0

謝謝!我們只是從您烘烤遷移時獲得的樣板代碼中獲取錯誤。沒有額外的幻想。我認爲你的解決方法是行之有效的。但我想知道原始問題是否是一個錯誤。似乎是一種非常普遍的情況來創建遷移,然後在某個時候後來引入一個新的關聯......這本身不應該打破早先的遷移權利? – emersonthis