]> git.mxchange.org Git - friendica.git/blob - src/BaseModel.php
Fix missing notifications:
[friendica.git] / src / BaseModel.php
1 <?php
2
3 namespace Friendica;
4
5 use Friendica\Database\Database;
6 use Friendica\Network\HTTPException;
7 use Psr\Log\LoggerInterface;
8
9 /**
10  * The Model classes inheriting from this abstract class are meant to represent a single database record.
11  * The associated table name has to be provided in the child class, and the table is expected to have a unique `id` field.
12  *
13  * @property int id
14  */
15 abstract class BaseModel
16 {
17         /** @var Database */
18         protected $dba;
19         /** @var LoggerInterface */
20         protected $logger;
21
22         /**
23          * Model record abstraction.
24          * Child classes never have to interact directly with it.
25          * Please use the magic getter instead.
26          *
27          * @var array
28          */
29         private $data = [];
30
31         /**
32          * Used to limit/avoid updates if no data was changed.
33          *
34          * @var array
35          */
36     private $originalData = [];
37
38         /**
39          * @param Database        $dba
40          * @param LoggerInterface $logger
41          * @param array           $data   Table row attributes
42          */
43         public function __construct(Database $dba, LoggerInterface $logger, array $data = [])
44         {
45                 $this->dba = $dba;
46                 $this->logger = $logger;
47                 $this->data = $data;
48                 $this->originalData = $data;
49         }
50
51         /**
52          * Maps a data array (original/current) to a known field list of the chosen model
53          *
54          * This is useful to filter out additional attributes, which aren't part of the db-table (like readonly cached fields)
55          *
56          * @param array $data The data array to map to db-fields
57          *
58          * @return array the mapped data array
59          */
60         protected function mapFields(array $data)
61         {
62                 return $data;
63         }
64
65         public function getOriginalData()
66         {
67                 return $this->mapFields($this->originalData);
68         }
69
70         public function resetOriginalData()
71         {
72                 $this->originalData = $this->data;
73         }
74
75         /**
76          * Performance-improved model creation in a loop
77          *
78          * @param BaseModel $prototype
79          * @param array     $data
80          * @return BaseModel
81          */
82         public static function createFromPrototype(BaseModel $prototype, array $data)
83         {
84                 $model = clone $prototype;
85                 $model->data = $data;
86                 $model->originalData = $data;
87
88                 return $model;
89         }
90
91         /**
92          * Magic isset method. Returns true if the field exists, either in the data prperty array or in any of the local properties.
93          * Used by array_column() on an array of objects.
94          *
95          * @param $name
96          * @return bool
97          */
98         public function __isset($name)
99         {
100                 return in_array($name, array_merge(array_keys($this->data), array_keys(get_object_vars($this))));
101         }
102
103         /**
104          * Magic getter. This allows to retrieve model fields with the following syntax:
105          * - $model->field (outside of class)
106          * - $this->field (inside of class)
107          *
108          * @param $name
109          * @return mixed
110          * @throws HTTPException\InternalServerErrorException
111          */
112         public function __get($name)
113         {
114                 $this->checkValid();
115
116                 if (!array_key_exists($name, $this->data)) {
117                         throw new HTTPException\InternalServerErrorException('Field ' . $name . ' not found in ' . static::class);
118                 }
119
120                 return $this->data[$name];
121         }
122
123         /**
124          * @param string $name
125          * @param mixed $value
126          */
127         public function __set($name, $value)
128         {
129                 $this->data[$name] = $value;
130         }
131
132         public function toArray()
133         {
134                 return $this->mapFields($this->data);
135         }
136
137         protected function checkValid()
138         {
139                 if (empty($this->data['id'])) {
140                         throw new HTTPException\InternalServerErrorException(static::class . ' record uninitialized');
141                 }
142         }
143 }