【问题标题】:Database error on calling a function in another model through its controller from a controller从控制器通过其控制器调用另一个模型中的函数时出现数据库错误
【发布时间】:2015-10-09 06:32:36
【问题描述】:

在我的 CakePHP 2.3 中,我试图从用户控制器调用一个函数到一个城市控制器,而城市控制器又从城市模型调用一个函数。

用户控制器中的功能:

function get_cities(){  

    $list_cities = $this->City->get_all_cities();

}

城市控制器功能:

function get_all_cities(){

    return $get_cities = $this->City->get_all_active_cities();

}

城市模型中的功能

public function get_all_active_cities(){

        $cities=$this->find('all',array('conditions'=>array('City.status'=>1)));    
        return $cities;

    }

但我遇到了数据库错误。

错误:SQLSTATE[42000]:语法错误或访问冲突:1064 你 您的 SQL 语法有错误;检查对应的手册 您的 MySQL 服务器版本,以便在附近使用正确的语法 第 1 行的“get_all_active_cities”

我该如何解决这个问题? TIA。

【问题讨论】:

标签: php mysql cakephp runtime-error cakephp-2.3


【解决方案1】:

快速提示,如果您只对调用模型函数感兴趣,您可以在不需要调用控制器的任何控制器中注册您的模型。

例如您可以在 User 控制器中使用注册模型

$this->City = ClassRegistry::init('City');

然后调用

$this->City->get_all_active_cities()

http://api.cakephp.org/2.3/class-ClassRegistry.html#_init

相反,您也可以在您的用户控制器中使用var $uses = array('User','City'); 来实现相同的效果

还检查从 CakePHP 生成的 sql 日志生成的 sql 查询,问题更多地指向框架生成的查询。您可以通过Error: SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual进行验证

希望对您有所帮助, 干杯。

【讨论】:

    【解决方案2】:

    您还可以在 users/get_cities 方法中加载城市模型。

    像下面这样的代码

    function get_cities(){  
       $this->loadModel('City');
       $list_cities = $this->City->get_all_cities();
    }
    

    【讨论】:

      【解决方案3】:

      在第 1 行的“get_all_active_cities”附近使用正确的语法

      此错误消息表示此代码已执行:

      $modelClass->get_all_active_cities();
      

      然而模型类没有有那个方法,而是作为查询传递给mysql,因为that's how unhandled methods are implemented

      要么方法名有错别字,要么$modelClass不是你认为的类

      如果您像这样更改控制器代码:

      function get_cities(){  
          debug(get_class($this->City)); //
          die;
      }
      

      然后看到“AppModel”,那么您的模型类根本没有被使用 - 典型的原因是:

      • 模型文件名不正确
      • 模型文件在错误的文件夹中

      这不是编写模型代码的正常方式

      拥有一个名为get_all_active_cities 的方法只是一个简单的查找并没有真正的帮助。它没有封装复杂性,也没有让代码的作用更清晰,可以说它使代码更难阅读,因为它隐藏了一些如此简单的东西。考虑简单地使用等效查找:

      function get_cities(){  
          $params = [
              'conditions'=>[
                  'City.status'=>1
              ]
          ];
          $list_cities = $this->City->find('all',$params);
          ...
      }
      

      另一种选择是创建一个finder method,以便查找逻辑与标准查找器完全相同,即

      function get_cities(){  
          $list_cities = $this->City->find('allActive');
          ...
      }
      

      与:

      class Article extends AppModel {
          public $findMethods = array('allAcctive' =>  true);
      
          protected function _findAllActive($state, $query, $results = array()) {
              if ($state === 'before') {
                  $query['conditions'][$this->alias . '.status'] = 1;
                  return $query;
              }
              return $results;
          }
      }
      

      这里的好处是上述查找器的使用方式与其他查找器方法完全相同。

      如果这是适用于所有查找的条件,还可以考虑使用 a behavior with a beforeFind callback 始终为您应用该条件。

      【讨论】:

        【解决方案4】:

        $this->loadModel('City'); 您可以在需要的地方直接使用来自城市的数据。希望对你有帮助

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2017-04-23
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多