Version: current

      1 <?php
      2 /**
      3  * This is a class used to represent key->value pairs generated from database queries.
      4  * The query isn't actually executed until you need it.
      5  *
      6  * @package sapphire
      7  * @subpackage model
      8  */
      9 class SQLMap extends Object implements IteratorAggregate {
     10     /**
     11      * The query used to generate the map.
     12      * @var SQLQuery
     13      */
     14     protected $query;
     15     protected $keyField, $titleField;
     16
     17     /**
     18      * Construct a SQLMap.
     19      * @param SQLQuery $query The query to generate this map. THis isn't executed until it's needed.
     20      */
     21     public function __construct(SQLQuery $query, $keyField = "ID", $titleField = "Title") {
     22         if(!$query) {
     23             user_error('SQLMap constructed with null query.', E_USER_ERROR);
     24         }
     25
     26         $this->query = $query;
     27         $this->keyField = $keyField;
     28         $this->titleField = $titleField;
     29
     30         parent::__construct();
     31     }
     32
     33     /**
     34      * Get the name of an item.
     35      * @param string|int $id The id of the item.
     36      * @return string
     37      */
     38     public function getItem($id) {
     39         if($id) {
     40             $baseTable = reset($this->query->from);
     41             $this->query->where[] = "$baseTable.ID = $id";
     42             $record = $this->query->execute()->first();
     43             if($record) {
     44                 $className = $record['ClassName'];
     45                 $obj = new $className($record);
     46                 return $obj->Title;
     47             }
     48         }
     49     }
     50
     51     public function getIterator() {
     52         $this->genItems();
     53         return new SQLMap_Iterator($this->items->getIterator(), $this->keyField, $this->titleField);
     54     }
     55
     56     /**
     57      * Get the items in this class.
     58      * @return DataObjectSet
     59      */
     60     public function getItems() {
     61         $this->genItems();
     62         return $this->items;
     63     }
     64
     65     /**
     66      * Generate the items in this map. This is used by
     67      * getItems() if the items have not been generated already.
     68      */
     69     protected function genItems() {
     70         if(!isset($this->items)) {
     71             $this->items = new DataObjectSet();
     72             $items = $this->query->execute();
     73
     74             foreach($items as $item) {
     75                 $className = isset($item['RecordClassName'])  ? $item['RecordClassName'] :  $item['ClassName'];
     76
     77                 if(!$className) {
     78                     user_error('SQLMap query could not retrieve className', E_USER_ERROR);
     79                 }
     80
     81                 $this->items->push(new $className($item));
     82             }
     83         }
     84     }
     85 }
     86
     87 /**
     88  * @package sapphire
     89  * @subpackage model
     90  */
     91 class SQLMap_Iterator extends Object implements Iterator {
     92     protected $items;
     93     protected $keyField, $titleField;
     94
     95     function __construct(Iterator $items, $keyField, $titleField) {
     96         $this->items = $items;
     97         $this->keyField = $keyField;
     98         $this->titleField = $titleField;
     99     }
    100
    101
    102     /*
    103      * Iterator functions - necessary for foreach to work
    104      */
    105     public function rewind() {
    106         return $this->items->rewind() ? $this->items->rewind()->{$this->titleField} : null;
    107     }
    108
    109     public function current() {
    110         return $this->items->current()->{$this->titleField};
    111     }
    112
    113     public function key() {
    114         return $this->items->current()->{$this->keyField};
    115     }
    116
    117     public function next() {
    118         $next = $this->items->next();
    119         return isset($next->{$this->titleField}) ? $next->{$this->titleField} : null;
    120     }
    121
    122     public function valid() {
    123         return $this->items->valid();
    124     }
    125 }
    126
    127 ?>

[Raise a SilverStripe Framework issue/bug](https://github.com/silverstripe/silverstripe-framework/issues/new)
- [Raise a SilverStripe CMS issue/bug](https://github.com/silverstripe/silverstripe-cms/issues/new)
- Please use the Silverstripe Forums to ask development related questions. -