代码之家  ›  专栏  ›  技术社区  ›  mensch

在数据源中实现CakePHP find()操作

  •  0
  • mensch  · 技术社区  · 14 年前

    我在CakePHP应用程序中实现了一个自定义数据源,我实现了一个数据源的基本函数( read() , listSources() , describe() ). 数据源使用Xml作为输入,我很想在Xml上使用find('neighbors'),并想知道Cake是否“自动”实现了这个特性(因为 读取() 函数在那里),或者如果我需要以某种方式扩展数据源。我还没有找到具体的例子,所以我希望so社区能够提供帮助。

    下面是当前的数据源实现。

    <?php
    App::import('Core', 'Xml');
    
    class AppdataSource extends DataSource {
      protected $_schema = array(
      'apps' => array(
       'id' => array(
        'type' => 'integer',
        'null' => true,
        'key' => 'primary',
        'length' => 11,
       ),
       'type' => array(
        'type' => 'string',
        'null' => true,
        'length' => 140
       ),
       'title' => array(
        'type' => 'string',
        'null' => true,
        'length' => 255
       ),
       'subtitle' => array(
        'type' => 'string',
        'null' => true,
        'length' => 255
       ),
       'body' => array(
        'type' => 'text',
        'null' => true,
       ),
       'date' => array(
        'type' => 'date',
        'null' => true,
       ),
      )
     );
    
      public function listSources() {
      return array('apps');
     }
    
      public function describe($model) {
      return $this->_schema['apps'];
     }
    
      function calculate(&$model, $func, $params = array()) {
       return '__'.$func;
      }
    
      function __getPage($items = null, $queryData = array()) {
      if (empty($queryData['limit']) ) {
       return $items;
      }
      $limit = $queryData['limit'];
      $page = $queryData['page'];
      $offset = $limit * ($page-1);
      return array_slice($items, $offset, $limit);
     }
    
      function __sortItems(&$model, $items, $order) {
      if ( empty($order) || empty($order[0]) ) {
       return $items;
      }
    
      $sorting = array();
      foreach( $order as $orderItem ) {
       if ( is_string($orderItem) ) {
        $field = $orderItem;
        $direction = 'asc';
       }
       else {
        foreach( $orderItem as $field => $direction ) {
         continue;
        }
       }
    
       $field = str_replace($model->alias.'.', '', $field);
    
       $values =  Set::extract($items, '{n}.'.$field);
       if ( in_array($field, array('lastBuildDate', 'pubDate')) ) {
        foreach($values as $i => $value) {
         $values[$i] = strtotime($value);
        }
       }
       $sorting[] = $values;
    
       switch(low($direction)) {
        case 'asc':
         $direction = SORT_ASC;
         break;
        case 'desc':
         $direction = SORT_DESC;
         break;
        default:
         trigger_error('Invalid sorting direction '. low($direction));
       }
       $sorting[] = $direction;
      }
    
      $sorting[] = &$items;
      $sorting[] = $direction;
      call_user_func_array('array_multisort', $sorting);
    
      return $items;
     }
    
      public function read($model, $queryData = array()) {
        $feedPath = 'xml/example.xml';
        $xml = new Xml($feedPath);
        $xml = $xml->toArray();
      foreach ($xml['Items']['Item'] as $record) {
        $record = array('App' => $record);
        $results[] = $record;
      }
        $results = $this->__getPage($results, $queryData);
        //Return item count
        if (Set::extract($queryData, 'fields') == '__count' ) {
         return array(array($model->alias => array('count' => count($results))));
        }
        return $results;
     }
    }
    ?>
    

    基本Xml结构:

    <items>
     <item id="1">
       <type>Type</type>
       <title>Title</title>
       <subtitle>Subtitle</subtitle>
       <date>15-12-2010</date>
       <body>Body text</body>
     </item>
    </items>
    

    编辑:

    本应仔细阅读本手册:

    就这些了 它。通过将此数据源耦合到 模特,你就可以使用 Model::find()/save()就像您希望的那样 通常,以及适当的数据 和/或用于调用这些 方法将传递给 数据源本身,您可以 决定实现哪个特性 您需要(例如Model::find options 例如“条件”解析、“限制” 甚至你自己的自定义参数)。

    1 回复  |  直到 14 年前
        1
  •  2
  •   Leo    14 年前

    我想你必须 显示 通过在数据源中定义方法来简化如何查找邻居。