Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
metadata.inc
1 <?php
17 require_once SQ_LIB_PATH.'/html_form/html_form.inc';
18 
40 function paintMetadata(&$owner, &$o, &$ei, $keywords=NULL, Array $layout_options=Array())
41 {
42  $root = $ei->findScreen('static_screen_metadata');
43  if (is_null($root)) return FALSE;
44 
45  $prefix = $owner->getPrefix();
46  $print_commit_button = FALSE;
47 
48  $mm = $GLOBALS['SQ_SYSTEM']->getMetadataManager();
49  $schemas = $mm->getSchemas($owner->id, TRUE);
50  $metadata_warnings = Array();
51  $contextid = $GLOBALS['SQ_SYSTEM']->getContextId();
52 
53  // If we are in Simple Edit, obtain the "Show Cascade Metadata field" option value so we can determine
54  // whether or not to print the checkbox
55  $print_cascade_values_option = TRUE;
56 
57  if ((!SQ_IN_BACKEND) && (isset($layout_options['show_cascade_metadata_field']))) {
58  $print_cascade_values_option = $layout_options['show_cascade_metadata_field'];
59  }
60 
61  foreach ($root->section as $section) {
62  // do this if keywords are set
63  if (is_null($keywords)) {
64  // if we are in limbo and this section is not to be printed in limbo - dont print it
65  if (SQ_IN_LIMBO && (!isset($section->attributes()->limbo_access) || (int)$section->attributes()->limbo_access == 0)) {
66  continue;
67  }
68  }
69 
70  $section_access = $ei->_getAccess($owner, $section, $prefix);
71  if (!($section_access & SQ_EI_READ)) {
72  continue;
73  }
74 
75  if (!is_null($keywords) && isset($keywords['sections'][strtolower(str_replace(' ', '_', (string) $section->attributes()->name))])) {
76  ob_start();
77  }
78 
79  // TODO: Fix this section->attributes() call here, don't use array get index.
80  $o->openSection(array_get_index($section->attributes, 'display_name', (string) $section->attributes()->name));
81 
82  if (!($num_fields = count($section->children()))) {
83  continue;
84  }
85 
86  foreach ($section->field as $field) {
87  $field_access = $ei->_getAccess($owner, $field, $prefix);
88  if (!($field_access & SQ_EI_READ)) {
89  continue;
90  }
91 
92  switch (strtolower((string) $field->attributes()->code)) {
94 
95  case 'metadata_current' :
96 
97  $o->openField('');
98  if (!is_null($keywords) && isset($keywords['fields']['metadata_current'])) {
99  ob_start();
100  }
101 
102  if ($contextid === 0) {
103  $metadata_basename = 'metadata.php';
104  } else {
105  $metadata_basename = 'metadata.'.$contextid.'.php';
106  }
107  $metadata_default_name = 'metadata.php';
108  $metadata = NULL;
109 
110  if (empty($schemas)) {
111  echo translate('no_metadata_schemas_applied');
112  } else if (file_exists($owner->data_path.'/'.$metadata_basename)) {
113  ob_start();
114  require($owner->data_path.'/'.$metadata_basename);
115  $metadata = ob_get_contents();
116  ob_end_clean();
117  } else if (file_exists($owner->data_path.'/'.$metadata_default_name)) {
118  // No generated metadata for this context yet. We can assume
119  // that until it is generated, it's using the same defaults
120  ob_start();
121  require($owner->data_path.'/'.$metadata_default_name);
122  $metadata = ob_get_contents();
123  ob_end_clean();
124  }
125 
126  // If metadata was filled, clean it and print it
127  // for the user's edification
128  if ($metadata !== NULL) {
129  echo nl2br(htmlspecialchars(trim($metadata)));
130  }
131 
132  // if there is a keyword replacement for this, add it to the replacements
133  if (!is_null($keywords) && isset($keywords['fields']['metadata_current'])) {
134  $ei->_tmp['layout_keyword_replacements'][$keywords['fields']['metadata_current']] = ob_get_contents();
135  ob_end_flush();
136  }
137  $o->closeField();
138 
139  break;
140 
142 
143  case 'metadata_instructions' :
144 
145  $o->openField('&nbsp;');
146  if (!is_null($keywords) && isset($keywords['fields']['metadata_instructions'])) {
147  ob_start();
148  }
149 
150  // construct example keywords link
151  $replacements_link = '<a href="'.sq_web_path('data').'/asset_types/metadata_field/popups/keywords.php?assetid='.$owner->id.'&amp;all=0" onclick="var win = window.open(this.href, \'keywords\', \'toolbar=0,menubar=0,location=0,status=0,scrollbars=1,resizable=1,width=580,height=320\'); return false;">'.translate('click_here').'</a>';
152  echo '<p>'.translate('metadata_keyword_replacements_usage', $replacements_link).'</p>';
153 
154  $sm = $GLOBALS['SQ_SYSTEM']->am->getSystemAsset('search_manager', TRUE);
155  if (!empty($sm) && $sm->attr('indexing')) {
156  ?>
157  <?php
158  $replacements_link = '<a href="'.sq_web_path('data').'/asset_types/metadata_field/popups/keyword_extraction.php?assetid='.$owner->id.'" onclick="var win = window.open(this.href, \'keywords\', \'toolbar=0,menubar=0,location=0,status=0,scrollbars=1,resizable=1,width=580,height=320\'); return false;">'.translate('keyword_extraction').'</a>';
159  echo '<p>'.translate('metadata_indexed_keywords', $replacements_link).'</p>';
160 
161  }
162 
163  // paint the instructions for 'Use Default'
164  echo '<p>'.translate('metadata_explain_use_default').'</p>';
165 
166  // paint the instructions for 'Cascade value'
167  echo '<p>'.translate('metadata_explain_cascade_value').'</p>';
168 
169  // paint required field
170  echo '<p> '.translate('denotes_required_field', '<span class="sq-backend-warning">*</span>').'</p>';
171 
172  // if there is a keyword replacement for this, add it to the replacements
173  if (!is_null($keywords) && isset($keywords['fields']['metadata_instructions'])) {
174  $ei->_tmp['layout_keyword_replacements'][$keywords['fields']['metadata_instructions']] = ob_get_contents();
175  ob_end_flush();
176  }
177  $o->closeField();
178 
179  break;
180 
182 
183  case 'metadata_values' :
184  if (empty($schemas)) {
185  $o->openField('&nbsp;');
186  if (!is_null($keywords) && isset($keywords['fields']['metadata_values'])) {
187  ob_start();
188  }
189 
190  echo translate('must_apply_one_or_more_schemas');
191 
192  // if there is a keyword replacement for this, add it to the replacements
193  if (!is_null($keywords) && isset($keywords['fields']['metadata_values'])) {
194  $ei->_tmp['layout_keyword_replacements'][$keywords['fields']['metadata_values']] = ob_get_contents();
195  ob_end_flush();
196  }
197  $o->closeField();
198  } else {
199  $write_access = $owner->writeAccess('metadata');
200  $print_commit_button = FALSE;
201 
202  if (!is_null($keywords) && isset($keywords['fields']['metadata_values'])) {
203  ob_start();
204  }
205 
206  $values = $mm->getMetadata($owner->id);
207  foreach ($schemas as $schemaid) {
208  $schema = $GLOBALS['SQ_SYSTEM']->am->getAsset($schemaid);
209  if (is_null($schema)) continue;
210  $edit_fns = $schema->getEditFns();
211 
212  // Paint only if user is not in limbo or if keywords for metadata fields are set
213  if ((!is_null($keywords) && isset($keywords['fields']['metadata_values'])) || !SQ_IN_LIMBO) {
214  if ($edit_fns->paintInlineValueInterface($schema, $o, $values, $write_access, $print_cascade_values_option, $owner->type())) {
215  $print_commit_button = TRUE;
216  }
217  }
218  else {
219  $print_commit_button = TRUE;
220  }
221  }
222 
223  // if there is a keyword replacement for this, add it to the replacements
224  if (!is_null($keywords) && isset($keywords['fields']['metadata_values'])) {
225  // Wrap this keyword's contents in table tags because it is printing out the contents of nested sections,
226  // but the top level section (opened earlier in this file) is not printed along with it.
227  $ei->_tmp['layout_keyword_replacements'][$keywords['fields']['metadata_values']] = '<table>'.ob_get_contents().'</table>';
228  ob_end_flush();
229  }
230  }
231 
232  break;
233 
234  }//end switch
235 
236  $note = (string) $field->note;
237  if (!empty($note)) {
238  $o->note($note);
239  }//end if
240 
241  }//end for
242  $o->closeSection();
243 
244  if (!is_null($keywords) && isset($keywords['sections'][strtolower(str_replace(' ', '_', $section->attributes()->name))])) {
245  $ei->_tmp['layout_keyword_replacements'][$keywords['sections'][strtolower(str_replace(' ', '_', $section->attributes()->name))]] = ob_get_contents();
246  ob_end_flush();
247  }
248 
249  }//end for
250  // prints a sq backend warning message if we have same metadata field names
251  $field_names = Array();
252  $duplicate_field_names = Array();
253  $field_ids = $mm->getMetadataFields($schemas);
254  if (!empty($field_ids)) {
255  foreach ($field_ids as $field_assetid => $field_info) {
256  $field = $GLOBALS['SQ_SYSTEM']->am->getAsset($field_assetid);
257  if (!isset($field_names[$field->attr('name')])) {
258  $field_names[$field->attr('name')] = 1;
259  } else {
260  $duplicate_field_names[$field->attr('name')] = $field->attr('name');
261  }
262  $GLOBALS['SQ_SYSTEM']->am->forgetAsset($field);
263  }
264  }
265 
266  if (!empty($duplicate_field_names)) {
267  $o->openSection(translate('warning'));
268  $o->openField('&nbsp;');
269  // paint required field
270  ob_start();
271  ?><ul><?php
272  foreach ($duplicate_field_names as $name) {
273  ?><li><?php echo $name ?></li><?php
274  }
275  ?></ul><span class="sq-backend-warning"><?php echo translate('duplicate_metadata_fields'); ?></span>
276  <?php
277  ob_end_flush();
278  $o->closeField();
279  $o->closeSection();
280  }
281 
282  // $metadata_warnings is provided by the metadata cache file
283  if (!empty($metadata_warnings['keyword_circular_references'])) {
284  $o->openSection(translate('warning'));
285  $o->openField('&nbsp;');
286  // paint required field
287  ob_start();
288  ?><ul><?php
289  foreach ($metadata_warnings['keyword_circular_references'] as $name) {
290  ?><li><?php echo $name ?></li><?php
291  }
292  ?></ul><span class="sq-backend-warning"><?php echo translate('circular_reference_metadata_field_keywords'); ?></span>
293  <?php
294  ob_end_flush();
295  $o->closeField();
296  $o->closeSection();
297  }
298 
299  // set the keyword replacements for any numbered field or section keywords
300  if (!is_null($keywords) && isset($keywords['fields'])) {
301 
302  // get the schemas that apply to this asset
303  $schemas = $mm->getSchemas($owner->id, TRUE);
304  $write_access = $owner->writeAccess('metadata');
305 
306  foreach ($keywords['fields'] as $field_assetid => $keyword) {
307 
308  // is this actually a metadata field or what?!
309  if ($mm->isMetadataFieldAssetid($field_assetid)) {
310  // get the parent schema of this metadata field
311  $schemaid = $GLOBALS['SQ_SYSTEM']->am->getParents($field_assetid, 'metadata_schema');
312 
313  // Only display the field if its schema is applied to the asset,
314  // or if the asset is not yet created
315  if (empty($owner->id) || (array_intersect($schemas, array_keys($schemaid)) != Array())) {
316  $value = $mm->getMetadataInterfaceValueByAssetid($owner->id, $field_assetid);
317 
318  $field = $GLOBALS['SQ_SYSTEM']->am->getAsset($field_assetid);
319  $edit_fns = $field->getEditFns();
320 
321  ob_start();
322  $edit_fns->paintValueInterface($field, $o, $value, $write_access, FALSE, $print_cascade_values_option, $owner->type());
323  $ei->_tmp['layout_keyword_replacements'][$keywords['fields'][$field_assetid]] = ob_get_contents();
324  ob_end_flush();
325  }
326  }
327  // if this is section keyword replacement
328  $matches = Array();
329  if (preg_match('/section_(\d+)_(name|description|values)/', $field_assetid, $matches)) {
330  // get the parent of this metadata section
331  $section_id = $matches[1];
332  $keyword_suffix = $matches[2];
333  $schemaid = $GLOBALS['SQ_SYSTEM']->am->getParents($section_id, 'metadata_schema');
334 
335  // Only display the section if its schema is applied to the asset,
336  // or if the asset is not yet created
337  if (empty($owner->id) || (array_intersect($schemas, array_keys($schemaid)) != Array())) {
338  $section = $GLOBALS['SQ_SYSTEM']->am->getAsset($section_id);
339 
340  if ($keyword_suffix == 'values') {
341  ob_start();
342  $values = $mm->getMetadata($owner->id);
343  $edit_fns = $section->getEditFns();
344  $edit_fns->paintInlineValueInterface($section, $o, $values, $write_access, $print_cascade_values_option, $owner->type());
345  $ei->_tmp['layout_keyword_replacements'][$keywords['fields'][$field_assetid]] = ob_get_contents();
346  ob_end_flush();
347  } else {
348  ob_start();
349  echo $section->attr($keyword_suffix);
350  $ei->_tmp['layout_keyword_replacements'][$keywords['fields'][$field_assetid]] = ob_get_contents();
351  ob_end_flush();
352  }
353  }//end if
354  }//end if
355  }//end foreach
356  }//end if
357 
358  return $print_commit_button;
359 
360 }//end paintMetadata()
361 
362 
373 function processMetadata(&$owner, &$o, $ei)
374 {
375  // if we dont have write access, dont process anything
376  if (!$owner->writeAccess('metadata')) return FALSE;
377 
378  $cascade_values_asset_ids = Array();
379 
380  $mm = $GLOBALS['SQ_SYSTEM']->getMetadataManager();
381  $schemas = $mm->getSchemas($owner->id, TRUE);
382  $save = FALSE;
383  if (!empty($schemas)) {
384  $new_values = Array();
385  foreach ($schemas as $schemaid) {
386  $schema = $GLOBALS['SQ_SYSTEM']->am->getAsset($schemaid);
387  $edit_fns = $schema->getEditFns();
388  if ($edit_fns->processInlineValueInterface($schema, $new_values, $cascade_values_asset_ids, $owner->type())) {
389  $save = TRUE;
390  }
391  }
392  }
393  if ($save) {
394  $mm->setMetadata($owner->id, $new_values);
395 
396  // All context metadata files need to be regenerated if there is a non-contextable field changed
397  $regen_all_contexts = FALSE;
398  foreach ($new_values as $fieldid => $field_data) {
399  $field = $GLOBALS['SQ_SYSTEM']->am->getAsset($fieldid);
400  if (!$field) continue;
401 
402  if ((boolean)$field->attr('is_contextable') === FALSE || $field instanceof Metadata_Field_Select) {
403  $regen_all_contexts = TRUE;
404  break;
405  }
406  }
407 
408  if ($regen_all_contexts) {
409  $all_contexts = $GLOBALS['SQ_SYSTEM']->getAllContexts();
410  foreach ($all_contexts as $contextid => $context_data) {
411  $mm->generateContentFile($owner->id, FALSE, $contextid);
412  }
413  } else {
414  $mm->generateContentFile($owner->id);
415  }
416 
417  // If the user has opted to cascade field values, we will handle these now
418  if (!empty($cascade_values_asset_ids)) {
419  $metadata_values_vars = Array();
420  foreach($cascade_values_asset_ids as $asset_id => $val) {
421  $field_value = Array($asset_id => $new_values[$asset_id]);
422  $metadata_values_vars[$asset_id] = Array('field_asset_id' => $asset_id, 'field_value' => $field_value);
423  }
424 
425  // Time to feed the HIPO
426  $hh = $GLOBALS['SQ_SYSTEM']->getHipoHerder();
427  $vars = Array(
428  'assets' => Array($owner->id => Array('type_code' => $owner->type())),
429  'metadata_field_value_changes' => $metadata_values_vars,
430  'dependants_only' => 1,
431  'contextid' => $GLOBALS['SQ_SYSTEM']->getContextId(),
432  );
433 
434  $hh->queueHipo('hipo_job_edit_metadata_field_values', $vars);
435 
436  }
437  }
438  return FALSE; // no need to call saveAttributes
439 
440 }//end processMetadata()
441 
442 
443 ?>