]> git.sur5r.net Git - bacula/bacula/blob - gui/baculum/framework/Data/ActiveRecord/Relations/TActiveRecordBelongsTo.php
baculum: New Baculum API and Baculum Web
[bacula/bacula] / gui / baculum / framework / Data / ActiveRecord / Relations / TActiveRecordBelongsTo.php
1 <?php
2 /**
3  * TActiveRecordBelongsTo class file.
4  *
5  * @author Wei Zhuo <weizhuo[at]gmail[dot]com>
6  * @link https://github.com/pradosoft/prado
7  * @copyright Copyright &copy; 2005-2016 The PRADO Group
8  * @license https://github.com/pradosoft/prado/blob/master/COPYRIGHT
9  * @version $Id$
10  * @package System.Data.ActiveRecord.Relations
11  */
12
13 /**
14  * Loads base active record relationship class.
15  */
16 Prado::using('System.Data.ActiveRecord.Relations.TActiveRecordRelation');
17
18 /**
19  * Implements the foreign key relationship (TActiveRecord::BELONGS_TO) between
20  * the source objects and the related foreign object. Consider the
21  * <b>entity</b> relationship between a Team and a Player.
22  * <code>
23  * +------+            +--------+
24  * | Team | 1 <----- * | Player |
25  * +------+            +--------+
26  * </code>
27  * Where one team may have 0 or more players and each player belongs to only
28  * one team. We may model Team-Player <b>object</b> relationship as active record as follows.
29  * <code>
30  * class TeamRecord extends TActiveRecord
31  * {
32  *     // see TActiveRecordHasMany for detailed definition.
33  * }
34  * class PlayerRecord extends TActiveRecord
35  * {
36  *     const TABLE='player';
37  *     public $player_id; //primary key
38  *     public $team_name; //foreign key player.team_name <-> team.name
39  *         public $age;
40  *     public $team; //foreign object TeamRecord
41  *
42  *     public static $RELATIONS = array
43  *     (
44  *                      'team' => array(self::BELONGS_TO, 'TeamRecord')
45  *     );
46  *
47  *         public static function finder($className=__CLASS__)
48  *         {
49  *                 return parent::finder($className);
50  *         }
51  * }
52  * </code>
53  * The static <tt>$RELATIONS</tt> property of PlayerRecord defines that the
54  * property <tt>$team</tt> belongs to a <tt>TeamRecord</tt>.
55  *
56  * The team object may be fetched as follows.
57  * <code>
58  * $players = PlayerRecord::finder()->with_team()->findAll();
59  * </code>
60  * The method <tt>with_xxx()</tt> (where <tt>xxx</tt> is the relationship property
61  * name, in this case, <tt>team</tt>) fetchs the corresponding TeamRecords using
62  * a second query (not by using a join). The <tt>with_xxx()</tt> accepts the same
63  * arguments as other finder methods of TActiveRecord, e.g.
64  * <tt>with_team('location = ?', 'Madrid')</tt>.
65  *
66  * @author Wei Zhuo <weizho[at]gmail[dot]com>
67  * @version $Id$
68  * @package System.Data.ActiveRecord.Relations
69  * @since 3.1
70  */
71 class TActiveRecordBelongsTo extends TActiveRecordRelation
72 {
73         /**
74          * Get the foreign key index values from the results and make calls to the
75          * database to find the corresponding foreign objects.
76          * @param array original results.
77          */
78         protected function collectForeignObjects(&$results)
79         {
80                 $fkeys = $this->getRelationForeignKeys();
81
82                 $properties = array_keys($fkeys);
83                 $fields = array_values($fkeys);
84                 $indexValues = $this->getIndexValues($properties, $results);
85                 $fkObjects = $this->findForeignObjects($fields, $indexValues);
86                 $this->populateResult($results,$properties,$fkObjects,$fields);
87         }
88
89         /**
90          * @return array foreign key field names as key and object properties as value.
91          * @since 3.1.2
92          */
93         public function getRelationForeignKeys()
94         {
95                 $fkObject = $this->getContext()->getForeignRecordFinder();
96                 return $this->findForeignKeys($this->getSourceRecord(),$fkObject);
97         }
98
99         /**
100          * Sets the foreign objects to the given property on the source object.
101          * @param TActiveRecord source object.
102          * @param array foreign objects.
103          */
104         protected function setObjectProperty($source, $properties, &$collections)
105         {
106                 $hash = $this->getObjectHash($source, $properties);
107                 $prop = $this->getContext()->getProperty();
108                 if(isset($collections[$hash]) && count($collections[$hash]) > 0)
109                 {
110                         if(count($collections[$hash]) > 1)
111                                 throw new TActiveRecordException('ar_belongs_to_multiple_result');
112                         $source->$prop=$collections[$hash][0];
113                 }
114                 else
115                         $source->$prop=null;
116         }
117
118         /**
119          * Updates the source object first.
120          * @return boolean true if all update are success (including if no update was required), false otherwise .
121          */
122         public function updateAssociatedRecords()
123         {
124                 $obj = $this->getContext()->getSourceRecord();
125                 $fkObject = $obj->getColumnValue($this->getContext()->getProperty());
126                 if($fkObject!==null)
127                 {
128                         $fkObject->save();
129                         $source = $this->getSourceRecord();
130                         $fkeys = $this->findForeignKeys($source, $fkObject);
131                         foreach($fkeys as $srcKey => $fKey)
132                                 $source->setColumnValue($srcKey, $fkObject->getColumnValue($fKey));
133                         return true;
134                 }
135                 return false;
136         }
137 }
138