/
class.entry.php
335 lines (284 loc) · 11.4 KB
/
class.entry.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
<?php
/**
* @package toolkit
*/
/**
* An entry is a combination of data that is stored in several Fields
* typically contained in one Section. Entries are created by the
* Authors of Symphony and hold all the content for the website.
* Entries are typically created from the Symphony backend, but
* can also be created using Events from the Frontend.
*/
Class Entry {
/**
* An associative array of basic metadata/settings for this Entry
* @var array
*/
protected $_fields = array();
/**
* An associative array of the data for each of the Fields that make up
* this Entry. The key is the Field ID, and the value is typically an array
* @var array
*/
protected $_data = array();
/**
* An ISO 8601 representation of when this Entry was created
* eg. `2004-02-12T15:19:21+00:00`
* @deprecated Since Symphony 2.3.1, use $entry->get('creation_date') instead
* @var string
*/
public $creationDate = null;
/**
* Entries have some basic metadata settings such as the Entry ID, the Author ID
* who created it and the Section that the Entry sits in. This function will set a
* setting to a value overwriting any existing value for this setting
*
* @param string $setting
* the setting key.
* @param mixed $value
* the value of the setting.
*/
public function set($setting, $value){
$this->_fields[$setting] = $value;
}
/**
* Accessor to the a setting by name. If no setting is provided all the
* settings of this Entry instance are returned.
*
* @param string $setting (optional)
* the name of the setting to access the value for. This is optional and
* defaults to null in which case all settings are returned.
* @return null|mixed|array
* the value of the setting if there is one, all settings if the input setting
* was omitted or null if the setting was supplied but there is no value
* for that setting.
*/
public function get($setting = null){
if(is_null($setting)) return $this->_fields;
if (!isset($this->_fields[$setting])) return null;
return $this->_fields[$setting];
}
/**
* Creates the initial entry row in tbl_entries and returns the resulting
* Entry ID using `getInsertID()`.
*
* @see toolkit.MySQL#getInsertID()
* @return integer
*/
public function assignEntryId() {
$fields = $this->get();
$fields['creation_date'] = $fields['modification_date'] = DateTimeObj::get('Y-m-d H:i:s');
$fields['creation_date_gmt'] = $fields['modification_date_gmt'] = DateTimeObj::getGMT('Y-m-d H:i:s');
$fields['author_id'] = is_null($this->get('author_id')) ? '1' : $this->get('author_id'); // Author_id cannot be null
Symphony::Database()->insert($fields, 'tbl_entries');
if (!$entry_id = Symphony::Database()->getInsertID()) return null;
$this->set('id', $entry_id);
return $entry_id;
}
/**
* Set the data for a Field in this Entry, given the Field ID and it's data
*
* @param integer $field_id
* The ID of the Field this data is for
* @param mixed $data
* Often an array
*/
public function setData($field_id, $data){
$this->_data[$field_id] = $data;
}
/**
* When an entry is saved from a form (either Frontend/Backend) this
* function will find all the fields in this set and loop over them, setting
* the data to each of the fields for processing. If any errors occur during
* this, `_ENTRY_FIELD_ERROR_` is returned, and an array is available with
* the errors.
*
* @param array $data
* An associative array of the data for this entry where they key is the
* Field's handle for this Section and the value is the data from the form
* @param array $errors
* An associative array of errors, by reference. The key is the `field_id`, the value
* is the message text. Defaults to an empty array
* @param boolean $simulate
* If $simulate is given as true, a dry run of this function will occur, where
* regardless of errors, an Entry will not be saved in the database. Defaults to
* false
* @param boolean $ignore_missing_fields
* This parameter allows Entries to be updated, rather than replaced. This is
* useful if the input form only contains a couple of the fields for this Entry.
* Defaults to false, which will set Fields to their default values if they are not
* provided in the $data
* @return integer
* Either `__ENTRY_OK__` or `__ENTRY_FIELD_ERROR__`
*/
public function setDataFromPost($data, &$errors = null, $simulate = false, $ignore_missing_fields = false){
$status = __ENTRY_OK__;
// Entry has no ID, create it:
if (!$this->get('id') && $simulate == false) {
$entry_id = $this->assignEntryId();
if (is_null($entry_id)) return __ENTRY_FIELD_ERROR__;
}
$section = SectionManager::fetch($this->get('section_id'));
$schema = $section->fetchFieldsSchema();
foreach($schema as $info){
$result = null;
$message = null;
$field = FieldManager::fetch($info['id']);
if($ignore_missing_fields && !isset($data[$field->get('element_name')])) continue;
$result = $field->processRawFieldData(
(isset($data[$info['element_name']]) ? $data[$info['element_name']] : null), $s, $message, $simulate, $this->get('id')
);
if($s != Field::__OK__){
$status = __ENTRY_FIELD_ERROR__;
$errors[$info['id']] = $message;
}
$this->setData($info['id'], $result);
}
// Failed to create entry, cleanup
if($status != __ENTRY_OK__ and !is_null($entry_id)) {
Symphony::Database()->delete('tbl_entries', " `id` = '$entry_id' ");
}
return $status;
}
/**
* Accessor function to return data from this Entry for a particular
* field. Optional parameter to return this data as an object instead
* of an array. If a Field is not provided, an associative array of all data
* assigned to this Entry will be returned.
*
* @param integer $field_id
* The ID of the Field whose data you want
* @param boolean $asObject
* If true, the data will be returned as an object instead of an
* array. Defaults to false. Note that if a `$field_id` is not provided
* the result will always be an array.
* @return array|object
* Depending on the value of `$asObject`, return the field's data
* as either an array or an object. If no data exists, null will be
* returned.
*/
public function getData($field_id=null, $asObject=false){
$fieldData = isset($this->_data[$field_id])
? $this->_data[$field_id]
: array();
if(!$field_id) return $this->_data;
return ($asObject == true ? (object)$fieldData : $fieldData);
}
/**
* Given a array of data from a form, this function will iterate over all the fields
* in this Entry's Section and call their `checkPostFieldData()` function.
*
* @param array $data
* An associative array of the data for this entry where they key is the
* Field's handle for this Section and the value is the data from the form
* @param array $error
* An array of errors, by reference. Defaults to empty
* @param boolean $ignore_missing_fields
* This parameter allows Entries to be updated, rather than replaced. This is
* useful if the input form only contains a couple of the fields for this Entry.
* Defaults to false, which will check all Fields even if they are not
* provided in the $data
* @return integer
* Either `__ENTRY_OK__` or `__ENTRY_FIELD_ERROR__`
*/
public function checkPostData($data, &$errors = null, $ignore_missing_fields=false){
$status = __ENTRY_OK__;
$section = SectionManager::fetch($this->get('section_id'));
$schema = $section->fetchFieldsSchema();
foreach($schema as $info){
$result = null;
$message = null;
$field = FieldManager::fetch($info['id']);
if($ignore_missing_fields && !isset($data[$field->get('element_name')])) continue;
if(Field::__OK__ != $field->checkPostFieldData((isset($data[$info['element_name']]) ? $data[$info['element_name']] : null), $message, $this->get('id'))){
$status = __ENTRY_FIELD_ERROR__;
$errors[$info['id']] = $message;
}
}
return $status;
}
/**
* Iterates over all the Fields in this Entry calling their
* `processRawFieldData()` function to set default values for this Entry.
*
* @see toolkit.Field#processRawFieldData()
*/
public function findDefaultData(){
$section = SectionManager::fetch($this->get('section_id'));
$schema = $section->fetchFields();
foreach($schema as $field){
if(isset($this->_data[$field->get('field_id')])) continue;
$result = $field->processRawFieldData(null, $status, $message, false, $this->get('id'));
$this->setData($field->get('field_id'), $result);
}
$this->set('modification_date', DateTimeObj::get('Y-m-d H:i:s'));
$this->set('modification_date_gmt', DateTimeObj::getGMT('Y-m-d H:i:s'));
if(!$this->get('creation_date')) $this->set('creation_date', $this->get('modification_date'));
if(!$this->get('creation_date_gmt')) $this->set('creation_date_gmt', $this->get('modification_date_gmt'));
}
/**
* Commits this Entry's data to the database, by first finding the default
* data for this `Entry` and then utilising the `EntryManager`'s
* add or edit function. The `EntryManager::edit` function is used if
* the current `Entry` object has an ID, otherwise `EntryManager::add`
* is used.
*
* @see toolkit.Entry#findDefaultData()
* @return boolean
* true if the commit was successful, false otherwise.
*/
public function commit(){
$this->findDefaultData();
return ($this->get('id') ? EntryManager::edit($this) : EntryManager::add($this));
}
/**
* Entries may link to other Entries through fields. This function will return the
* number of entries that are associated with the current entry as an associative
* array. If there are no associated entries, null will be returned.
*
* @param array $associated_sections
* An associative array of sections to return the Entry counts from. Defaults to
* null, which will fetch all the associations of this Entry.
* @return array
* An associative array with the key being the associated Section's ID and the
* value being the number of entries associated with this Entry.
*/
public function fetchAllAssociatedEntryCounts($associated_sections = null) {
if(is_null($this->get('section_id'))) return null;
if(is_null($associated_sections)) {
$section = SectionManager::fetch($this->get('section_id'));
$associated_sections = $section->fetchAssociatedSections();
}
if(!is_array($associated_sections) || empty($associated_sections)) return null;
$counts = array();
foreach($associated_sections as $as) {
$field = FieldManager::fetch($as['child_section_field_id']);
$parent_section_field_id = $as['parent_section_field_id'];
$search_value = null;
if(!is_null($parent_section_field_id)){
$search_value = $field->fetchAssociatedEntrySearchValue(
$this->getData($as['parent_section_field_id']),
$as['parent_section_field_id'],
$this->get('id')
);
}
else {
$search_value = $this->get('id');
}
$counts[$as['child_section_id']] = $field->fetchAssociatedEntryCount($search_value);
}
return $counts;
}
}
/**
* The constant for when an Entry is ok, that is, no errors have
* been raised by any of it's Fields.
* @var integer
*/
define_safe('__ENTRY_OK__', 0);
/**
* The constant for an Entry if there is an error is raised by any of
* it's Fields.
* @var integer
*/
define_safe('__ENTRY_FIELD_ERROR__', 100);