2009-08-09 3 views
1

レコードが保存された後に動作するためには、リファクタリングしたいサンプルコードがあります。現在は、レコードが最初にレンダリングされた後で動作します(afterFilterを使用)。それは、私がレイアウトで望むビューをレンダリングし、それをファイルに保存することです。Model :: afterSave()のController :: render()をCakePHPで使用していますか?

function afterFilter() { 
    parent::afterFilter(); 
    if($this->params['pass'][0] == 'contact') { 
     $surrenderOuput = $this->surrender($this->params['pass'][0]); 
     $path = WWW_ROOT . 'cache' . DS . $this->params['pass'][0] . DS . 'index.html'; 
     $file = new File($path, true); 
     $file->write($surrenderOuput); 
     $file->close(); 
    } 
} 
function surrender($action = null, $layout = null, $file = null) { 
    $this->beforeRender(); 

    $viewClass = $this->view; 
    if ($this->view != 'View') { 
     if (strpos($viewClass, '.') !== false) { 
      list($plugin, $viewClass) = explode('.', $viewClass); 
     } 
     $viewClass = $viewClass . 'View'; 
     App::import('View', $this->view); 
    } 

    $this->Component->beforeRender($this); 

    $this->params['models'] = $this->modelNames; 

    if (Configure::read() > 2) { 
     $this->set('cakeDebug', $this); 
    } 

    $View =& new $viewClass($this); 

    if (!empty($this->modelNames)) { 
     $models = array(); 
     foreach ($this->modelNames as $currentModel) { 
      if (isset($this->$currentModel) && is_a($this->$currentModel, 'Model')) { 
       $models[] = Inflector::underscore($currentModel); 
      } 
      $isValidModel = (
       isset($this->$currentModel) && is_a($this->$currentModel, 'Model') && 
       !empty($this->$currentModel->validationErrors) 
      ); 
      if ($isValidModel) { 
       $View->validationErrors[Inflector::camelize($currentModel)] =& 
        $this->$currentModel->validationErrors; 
      } 
     } 
     $models = array_diff(ClassRegistry::keys(), $models); 
     foreach ($models as $currentModel) { 
      if (ClassRegistry::isKeySet($currentModel)) { 
       $currentObject =& ClassRegistry::getObject($currentModel); 
       if (is_a($currentObject, 'Model') && !empty($currentObject->validationErrors)) { 
        $View->validationErrors[Inflector::camelize($currentModel)] =& 
         $currentObject->validationErrors; 
       } 
      } 
     } 
    } 

    $this->autoRender = false; 
    $output = $View->render($action, $layout, $file); 

    return $output; 
} 

だから私は基本的にレイアウトを表示し、それを出力として返してファイルに保存しています。すばらしいです。モデルで同様のことをする方法はありますか?

+0

私はそれを一緒にハッキングするいくつかの方法があると確信していますが、それはMVC構造の大きな違反になり、ほぼ確実に副作用があります。なぜあなたはレコードを保存するたびに特定のビューをレンダリングしたいのですか? – deceze

+0

そのビューをファイルとしてキャッシュするためです。ホスト(Godaddy)は、mysqlに関する限り、ひどいパフォーマンスを持っています。 –

答えて

2

モデルのafterSave()にメンバ変数を設定し、コントローラのafterFilter()でその値をチェックすることを検討してください。

+0

私はModel :: afterSave()を使用して動作を終了しました。これを行う方法を理解するのに時間がかかりましたが、Controller :: render()を使用するのは方法ではありません。 Controller :: requestAction()を呼び出し、beforeFilterでチェックされたレイアウトを自動レンダリングするパラメタを渡すと、私の問題が解決されたようです。ありがとう:) –

0

モデルからビューをレンダリングする方法を検索する際にこのスレッドが見つかりました。私の場合は、モデルのカスタムメソッドを呼んでいるので、これはafterSave()のために動作しない場合がありますが、あなたは、カスタムメソッドを呼び出している場合は、このようにそれを行うことができます。

コントローラー:

$this->Model->myFunc($this); 

モデルこのスレッドに出くわす他の誰かを助け

public function myFunc($object) { 
$object->render(); 
} 

うまくいけば。

関連する問題