/** * */ private function _convertCodeToDisplayText($ps_prop, $pa_path_components, $pt_instance, $pa_options = null) { $vs_prop = $ps_prop; $vs_field_name = $pa_path_components['subfield_name'] ? $pa_path_components['subfield_name'] : $pa_path_components['field_name']; $vs_table_name = $pa_path_components['table_name']; if (method_exists($pt_instance, 'setLabelTypeList')) { $pt_instance->setLabelTypeList($this->opo_subject_instance->getAppConfig()->get($pa_path_components['field_name'] == 'nonpreferred_labels' ? "{$vs_table_name}_nonpreferred_label_type_list" : "{$vs_table_name}_preferred_label_type_list")); } if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $pt_instance->getFieldInfo($vs_field_name, "LIST_CODE"))) { $vs_prop = $this->opt_list->getItemFromListForDisplayByItemID($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $pt_instance->getFieldInfo($vs_field_name, "LIST"))) { $vs_prop = $this->opt_list->getItemFromListForDisplayByItemValue($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $vs_field_name === 'locale_id' && (int) $vs_prop > 0) { $t_locale = new ca_locales($vs_prop); $vs_prop = $t_locale->getName(); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && is_array($va_list = $pt_instance->getFieldInfo($vs_field_name, "BOUNDS_CHOICE_LIST"))) { foreach ($va_list as $vs_option => $vs_value) { if ($vs_value == $vs_prop) { $vs_prop = $vs_option; break; } } } } } } return $vs_prop; }
/** * Get a field value of the table row that is represented by this object. * * @param string $ps_field field name * @param array $pa_options options array; can be omitted. * It should be an associative array of boolean (except one of the options) flags. In case that some of the options are not set, they are treated as 'false'. * Possible options (keys) are: * BINARY: return field value as is * FILTER_HTML_SPECIAL_CHARS: convert all applicable chars to their html entities * DONT_PROCESS_GLOSSARY_TAGS: ? * CONVERT_HTML_BREAKS: similar to nl2br() * convertLineBreaks: same as CONVERT_HTML_BREAKS * getDirectDate: return raw date value from database if $ps_field adresses a date field, otherwise the value will be parsed using the TimeExpressionParser::getText() method * getDirectTime: return raw time value from database if $ps_field adresses a time field, otherwise the value will be parsed using the TimeExpressionParser::getText() method * TIMECODE_FORMAT: set return format for fields representing time ranges possible (string) values: COLON_DELIMITED, HOURS_MINUTES_SECONDS, RAW; data will be passed through floatval() by default * QUOTE: set return value into quotes * URL_ENCODE: value will be passed through urlencode() * ESCAPE_FOR_XML: convert <, >, &, ' and " characters for XML use * DONT_STRIP_SLASHES: if set to true, return value will not be passed through stripslashes() * template: formatting string to use for returned value; ^<fieldname> placeholder is used to represent field value in template * returnAsArray: if true, fields that can return multiple values [currently only <table_name>.children.<field>] will return values in an indexed array; default is false * returnAllLocales: * delimiter: if set, value is used as delimiter when fields that can return multiple fields are returned as strings; default is a single space * convertCodesToDisplayText: if set, id values refering to foreign keys are returned as preferred label text in the current locale * returnURL: if set then url is returned for media, otherwise an HTML tag for display is returned * dateFormat: format to return created or lastModified dates in. Valid values are iso8601 or text * checkAccess = array of access values to filter results by; if defined only items with the specified access code(s) are returned. Only supported for table that have an "access" field. * sort = optional field to sort returned values on. The field specifiers are fields with or without table name specified. * sort_direction = direction to sort results by, either 'asc' for ascending order or 'desc' for descending order; default is 'asc' */ public function get($ps_field, $pa_options = null) { if (!$ps_field) { return null; } if (!is_array($pa_options)) { $pa_options = array(); } $vb_return_as_array = caGetOption('returnAsArray', $pa_options, false); $vb_return_with_structure = caGetOption('returnWithStructure', $pa_options, false); $vb_return_all_locales = caGetOption('returnAllLocales', $pa_options, false); $vs_delimiter = caGetOption('delimiter', $pa_options, ' '); if (($vb_return_with_structure || $vb_return_all_locales) && !$vb_return_as_array) { $vb_return_as_array = true; } $vn_row_id = $this->getPrimaryKey(); if ($vb_return_as_array && $vb_return_as_array) { $vn_locale_id = $this->hasField('locale_id') ? $this->get('locale_id') : null; } $va_tmp = explode('.', $ps_field); if (sizeof($va_tmp) > 1) { if ($va_tmp[0] === $this->tableName()) { // // Return created on or last modified // if (in_array($va_tmp[1], array('created', 'lastModified'))) { if ($vb_return_as_array) { return $va_tmp[1] == 'lastModified' ? $this->getLastChangeTimestamp() : $this->getCreationTimestamp(); } else { $va_data = $va_tmp[1] == 'lastModified' ? $this->getLastChangeTimestamp() : $this->getCreationTimestamp(); $vs_subfield = isset($va_tmp[2]) && isset($va_data[$va_tmp[2]]) ? $va_tmp[2] : 'timestamp'; $vm_val = $va_data[$vs_subfield]; if ($vs_subfield == 'timestamp') { $o_tep = new TimeExpressionParser(); $o_tep->setUnixTimestamps($vm_val, $vm_val); $vm_val = $o_tep->getText($pa_options); } return $vm_val; } } // // Generalized get // $va_field_info = $this->getFieldInfo($va_tmp[1]); switch (sizeof($va_tmp)) { case 2: // support <table_name>.<field_name> syntax $ps_field = $va_tmp[1]; break; default: // > 2 elements // media field? if ($va_field_info['FIELD_TYPE'] === FT_MEDIA && !isset($pa_options['returnAsArray']) && !$pa_options['returnAsArray']) { $o_media_settings = new MediaProcessingSettings($va_tmp[0], $va_tmp[1]); $va_versions = $o_media_settings->getMediaTypeVersions('*'); $vs_version = $va_tmp[2]; if (!isset($va_versions[$vs_version])) { $va_available_versions = array_keys($va_versions); $vs_version = $va_tmp[2] = array_shift($va_available_versions); } if (isset($va_tmp[3])) { return $this->getMediaInfo($va_tmp[1], $vs_version, 'width'); } else { if (isset($pa_options['returnURL']) && $pa_options['returnURL']) { return $this->getMediaUrl($va_tmp[1], $vs_version, $pa_options); } else { return $this->getMediaTag($va_tmp[1], $vs_version, $pa_options); } } } if ($va_tmp[1] == 'parent' && $this->isHierarchical() && ($vn_parent_id = $this->get($this->getProperty('HIERARCHY_PARENT_ID_FLD')))) { $t_instance = $this->getAppDatamodel()->getInstanceByTableNum($this->tableNum()); if (!$t_instance->load($vn_parent_id)) { return $vb_return_as_array ? array() : null; } else { unset($va_tmp[1]); $va_tmp = array_values($va_tmp); if ($vb_return_as_array) { if ($vb_return_all_locales) { return array($vn_row_id => array($vn_locale_id => array($t_instance->get(join('.', $va_tmp))))); } else { return array($vn_row_id => $t_instance->get(join('.', $va_tmp))); } } else { return $t_instance->get(join('.', $va_tmp)); } } } else { if ($va_tmp[1] == 'children' && $this->isHierarchical()) { $vb_check_access = is_array($pa_options['checkAccess']) && $this->hasField('access'); $va_sort = isset($pa_options['sort']) ? $pa_options['sort'] : null; if (!is_array($va_sort) && $va_sort) { $va_sort = array($va_sort); } if (!is_array($va_sort)) { $va_sort = array(); } $vs_sort_direction = isset($pa_options['sort_direction']) && in_array(strtolower($pa_options['sort_direction']), array('asc', 'desc')) ? strtolower($pa_options['sort_direction']) : 'asc'; unset($va_tmp[1]); // remove 'children' from field path $va_tmp = array_values($va_tmp); $vs_childless_path = join('.', $va_tmp); $va_data = array(); $va_children_ids = $this->getHierarchyChildren(null, array('idsOnly' => true)); if (is_array($va_children_ids) && sizeof($va_children_ids)) { $t_instance = $this->getAppDatamodel()->getInstanceByTableNum($this->tableNum()); if ($va_tmp[1] == $this->primaryKey() && !$vs_sort) { foreach ($va_children_ids as $vn_child_id) { $va_data[$vn_child_id] = $vn_child_id; } } else { if (method_exists($this, "makeSearchResult")) { // Use SearchResult lazy loading when available $vs_table = $this->tableName(); $vs_pk = $vs_table . '.' . $this->primaryKey(); $qr_children = $this->makeSearchResult($this->tableName(), $va_children_ids); while ($qr_children->nextHit()) { if ($vb_check_access && !in_array($qr_children->get("{$vs_table}.access"), $pa_options['checkAccess'])) { continue; } $vn_child_id = $qr_children->get($vs_pk); $vs_sort_key = ''; foreach ($va_sort as $vs_sort) { $vs_sort_key .= $vs_sort ? $qr_children->get($vs_sort) : 0; } if (!is_array($va_data[$vs_sort_key])) { $va_data[$vs_sort_key] = array(); } if ($vb_return_as_array) { $va_data[$vs_sort_key][$vn_child_id] = array_shift($qr_children->get($vs_childless_path, array_merge($pa_options, array('returnAsArray' => $vb_return_as_array, 'returnAllLocales' => $vb_return_all_locales)))); } else { $va_data[$vs_sort_key][$vn_child_id] = $qr_children->get($vs_childless_path, array_merge($pa_options, array('returnAsArray' => false, 'returnAllLocales' => false))); } } ksort($va_data); if ($vs_sort_direction && $vs_sort_direction == 'desc') { $va_data = array_reverse($va_data); } $va_sorted_data = array(); foreach ($va_data as $vs_sort_key => $va_items) { foreach ($va_items as $vs_k => $vs_v) { $va_sorted_data[] = $vs_v; } } $va_data = $va_sorted_data; } else { // Fall-back to loading records row-by-row (slow) foreach ($va_children_ids as $vn_child_id) { if ($t_instance->load($vn_child_id)) { if ($vb_check_access && !in_array($t_instance->get("access"), $pa_options['checkAccess'])) { continue; } $vs_sort_key = $vs_sort ? $t_instance->get($vs_sort) : 0; if (!is_array($va_data[$vs_sort_key])) { $va_data[$vs_sort_key] = array(); } if ($vb_return_as_array) { $va_data[$vs_sort_key][$vn_child_id] = array_shift($t_instance->get($vs_childless_path, array_merge($pa_options, array('returnAsArray' => $vb_return_as_array, 'returnAllLocales' => $vb_return_all_locales)))); } else { $va_data[$vs_sort_key][$vn_child_id] = $t_instance->get($vs_childless_path, array_merge($pa_options, array('returnAsArray' => false, 'returnAllLocales' => false))); } } } ksort($va_data); if ($vs_sort_direction && $vs_sort_direction == 'desc') { $va_data = array_reverse($va_data); } $va_sorted_data = array(); foreach ($va_data as $vs_sort_key => $va_items) { foreach ($va_items as $vs_k => $vs_v) { $va_sorted_data[] = $vs_v; } } $va_data = $va_sorted_data; } } } if ($vb_return_as_array) { return $va_data; } else { return join($vs_delimiter, $va_data); } } } break; } } else { $va_rels = $this->getRelatedItems($va_tmp[0]); $va_vals = array(); if (is_array($va_rels)) { foreach ($va_rels as $va_rel_item) { if (isset($va_rel_item[$va_tmp[1]])) { $va_vals[] = $va_rel_item[$va_tmp[1]]; } } return $vb_return_as_array ? $va_vals : join($vs_delimiter, $va_vals); } // can't pull fields from other tables! return $vb_return_as_array ? array() : null; } } if (isset($pa_options["BINARY"]) && $pa_options["BINARY"]) { return $this->_FIELD_VALUES[$ps_field]; } if (array_key_exists($ps_field, $this->FIELDS)) { $ps_field_type = $this->getFieldInfo($ps_field, "FIELD_TYPE"); if ($this->getFieldInfo($ps_field, 'IS_LIFESPAN')) { $pa_options['isLifespan'] = true; } switch ($ps_field_type) { case FT_BIT: $vs_prop = isset($this->_FIELD_VALUES[$ps_field]) ? $this->_FIELD_VALUES[$ps_field] : ""; if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText']) { $vs_prop = (bool) $vs_prop ? _t('yes') : _t('no'); } return $vs_prop; break; case FT_TEXT: case FT_NUMBER: case FT_PASSWORD: $vs_prop = isset($this->_FIELD_VALUES[$ps_field]) ? $this->_FIELD_VALUES[$ps_field] : null; if (isset($pa_options["FILTER_HTML_SPECIAL_CHARS"]) && $pa_options["FILTER_HTML_SPECIAL_CHARS"]) { $vs_prop = htmlentities(html_entity_decode($vs_prop)); } // // Convert foreign keys and choice list values to display text is needed // if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $this->getFieldInfo($ps_field, "LIST_CODE"))) { $t_list = new ca_lists(); $vs_prop = $t_list->getItemFromListForDisplayByItemID($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $this->getFieldInfo($ps_field, "LIST"))) { $t_list = new ca_lists(); if (!($vs_tmp = $t_list->getItemFromListForDisplayByItemValue($vs_list_code, $vs_prop))) { if ($vs_tmp = $this->getChoiceListValue($ps_field, $vs_prop)) { $vs_prop = $vs_tmp; } } else { $vs_prop = $vs_tmp; } } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $ps_field === 'locale_id' && (int) $vs_prop > 0) { $t_locale = new ca_locales($vs_prop); $vs_prop = $t_locale->getName(); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && is_array($va_list = $this->getFieldInfo($ps_field, "BOUNDS_CHOICE_LIST"))) { foreach ($va_list as $vs_option => $vs_value) { if ($vs_value == $vs_prop) { $vs_prop = $vs_option; break; } } } } } } if (isset($pa_options["CONVERT_HTML_BREAKS"]) && $pa_options["CONVERT_HTML_BREAKS"] || isset($pa_options["convertLineBreaks"]) && $pa_options["convertLineBreaks"]) { $vs_prop = caConvertLineBreaks($vs_prop); } break; case FT_DATETIME: case FT_TIMESTAMP: case FT_HISTORIC_DATETIME: case FT_HISTORIC_DATE: case FT_DATE: $vn_timestamp = isset($this->_FIELD_VALUES[$ps_field]) ? $this->_FIELD_VALUES[$ps_field] : 0; if ($vb_return_with_structure) { $vs_prop = array('start' => $this->_FIELD_VALUES[$ps_field], 'end' => $this->_FIELD_VALUES[$ps_field]); } elseif (caGetOption('GET_DIRECT_DATE', $pa_options, false) || caGetOption('getDirectDate', $pa_options, false) || caGetOption('rawDate', $pa_options, false)) { $vs_prop = $this->_FIELD_VALUES[$ps_field]; } elseif (isset($pa_options['sortable']) && $pa_options['sortable']) { $vs_prop = $vn_timestamp . "/" . $vn_timestamp; } else { $o_tep = new TimeExpressionParser(); if ($ps_field_type == FT_HISTORIC_DATETIME || $ps_field_type == FT_HISTORIC_DATE) { $o_tep->setHistoricTimestamps($vn_timestamp, $vn_timestamp); } else { $o_tep->setUnixTimestamps($vn_timestamp, $vn_timestamp); } if ($ps_field_type == FT_DATE || $ps_field_type == FT_HISTORIC_DATE) { $vs_prop = $o_tep->getText(array_merge(array('timeOmit' => true), $pa_options)); } else { $vs_prop = $o_tep->getText($pa_options); } } break; case FT_TIME: if ($vb_return_with_structure) { $vs_prop = array('start' => $this->_FIELD_VALUES[$ps_field], 'end' => $this->_FIELD_VALUES[$ps_field]); } elseif (caGetOption('GET_DIRECT_TIME', $pa_options, false) || caGetOption('getDirectTime', $pa_options, false) || caGetOption('rawTime', $pa_options, false)) { $vs_prop = $this->_FIELD_VALUES[$ps_field]; } else { $o_tep = new TimeExpressionParser(); $vn_timestamp = isset($this->_FIELD_VALUES[$ps_field]) ? $this->_FIELD_VALUES[$ps_field] : 0; $o_tep->setTimes($vn_timestamp, $vn_timestamp); $vs_prop = $o_tep->getText($pa_options); } break; case FT_DATERANGE: case FT_HISTORIC_DATERANGE: $vs_start_field_name = $this->getFieldInfo($ps_field, "START"); $vs_end_field_name = $this->getFieldInfo($ps_field, "END"); $vn_start_date = isset($this->_FIELD_VALUES[$vs_start_field_name]) ? $this->_FIELD_VALUES[$vs_start_field_name] : null; $vn_end_date = isset($this->_FIELD_VALUES[$vs_end_field_name]) ? $this->_FIELD_VALUES[$vs_end_field_name] : null; if ($vb_return_with_structure) { $vs_prop = array('start' => $vn_start_date, 'end' => $vn_end_date); } elseif (!caGetOption('GET_DIRECT_DATE', $pa_options, false) && !caGetOption('getDirectDate', $pa_options, false) && !caGetOption('rawDate', $pa_options, false)) { $o_tep = new TimeExpressionParser(); if ($ps_field_type == FT_HISTORIC_DATERANGE) { $o_tep->setHistoricTimestamps($vn_start_date, $vn_end_date); } else { $o_tep->setUnixTimestamps($vn_start_date, $vn_end_date); } $vs_prop = $o_tep->getText($pa_options); } elseif (isset($pa_options['sortable']) && $pa_options['sortable']) { $vs_prop = $vn_start_date; //."/".$vn_timestamp; } else { $vs_prop = $vn_start_date; //array($vn_start_date, $vn_end_date); } break; case FT_TIMERANGE: $vs_start_field_name = $this->getFieldInfo($ps_field, "START"); $vs_end_field_name = $this->getFieldInfo($ps_field, "END"); $vn_start_date = isset($this->_FIELD_VALUES[$vs_start_field_name]) ? $this->_FIELD_VALUES[$vs_start_field_name] : null; $vn_end_date = isset($this->_FIELD_VALUES[$vs_end_field_name]) ? $this->_FIELD_VALUES[$vs_end_field_name] : null; if ($vb_return_with_structure) { $vs_prop = array('start' => $vn_start_date, 'end' => $vn_end_date); } elseif (!caGetOption('GET_DIRECT_TIME', $pa_options, false) && !caGetOption('getDirectTime', $pa_options, false) && !caGetOption('rawTime', $pa_options, false)) { $o_tep = new TimeExpressionParser(); $o_tep->setTimes($vn_start_date, $vn_end_date); $vs_prop = $o_tep->getText($pa_options); } else { $vs_prop = array($vn_start_date, $vn_end_date); } break; case FT_TIMECODE: $o_tp = new TimecodeParser(); $o_tp->setParsedValueInSeconds($this->_FIELD_VALUES[$ps_field]); $vs_prop = $o_tp->getText(isset($pa_options["TIMECODE_FORMAT"]) ? $pa_options["TIMECODE_FORMAT"] : null); break; case FT_MEDIA: case FT_FILE: if ($vb_return_with_structure || $pa_options["USE_MEDIA_FIELD_VALUES"]) { if (isset($pa_options["USE_MEDIA_FIELD_VALUES"]) && $pa_options["USE_MEDIA_FIELD_VALUES"]) { $vs_prop = $this->_FIELD_VALUES[$ps_field]; } else { $vs_prop = isset($this->_SET_FILES[$ps_field]['tmp_name']) && $this->_SET_FILES[$ps_field]['tmp_name'] ? $this->_SET_FILES[$ps_field]['tmp_name'] : $this->_FIELD_VALUES[$ps_field]; } } else { $va_versions = $this->getMediaVersions($ps_field); $vs_tag = $this->getMediaTag($ps_field, array_shift($va_versions)); if ($vb_return_as_array) { return array($vs_tag); } else { return $vs_tag; } } break; case FT_VARS: $vs_prop = isset($this->_FIELD_VALUES[$ps_field]) && $this->_FIELD_VALUES[$ps_field] ? $this->_FIELD_VALUES[$ps_field] : null; break; } if (isset($pa_options["QUOTE"]) && $pa_options["QUOTE"]) { $vs_prop = $this->quote($ps_field, $vs_prop); } } else { $this->postError(710, _t("'%1' does not exist in this object", $ps_field), "BaseModel->get()"); return $vb_return_as_array ? array() : null; } if (isset($pa_options["URL_ENCODE"]) && $pa_options["URL_ENCODE"]) { $vs_prop = urlEncode($vs_prop); } if (isset($pa_options["ESCAPE_FOR_XML"]) && $pa_options["ESCAPE_FOR_XML"]) { $vs_prop = caEscapeForXML($vs_prop); } if (!(isset($pa_options["DONT_STRIP_SLASHES"]) && $pa_options["DONT_STRIP_SLASHES"])) { if (is_string($vs_prop)) { $vs_prop = stripSlashes($vs_prop); } } if (isset($pa_options["template"]) && $pa_options["template"]) { $vs_template_with_substitution = str_replace("^" . $ps_field, $vs_prop, $pa_options["template"]); $vs_prop = str_replace("^" . $this->tableName() . "." . $ps_field, $vs_prop, $vs_template_with_substitution); } if ($vb_return_as_array) { if ($vb_return_all_locales) { return array($vn_row_id => array($vn_locale_id => array($vs_prop))); } else { return array($vn_row_id => $vs_prop); } } else { return $vs_prop; } }
/** * Implementation of primary get() functionality */ private function _get($ps_field, $pa_options = null) { if (!is_array($pa_options)) { $pa_options = array(); } if (isset($pa_options['restrictToType']) && (!isset($pa_options['restrict_to_type']) || !$pa_options['restrict_to_type'])) { $pa_options['restrict_to_type'] = $pa_options['restrictToType']; } if (isset($pa_options['restrictToTypes']) && (!isset($pa_options['restrict_to_types']) || !$pa_options['restrict_to_types'])) { $pa_options['restrict_to_types'] = $pa_options['restrictToTypes']; } if (isset($pa_options['restrictToRelationshipTypes']) && (!isset($pa_options['restrict_to_relationship_types']) || !$pa_options['restrict_to_relationship_types'])) { $pa_options['restrict_to_relationship_types'] = $pa_options['restrictToRelationshipTypes']; } if (isset($pa_options['excludeType']) && (!isset($pa_options['exclude_type']) || !$pa_options['exclude_type'])) { $pa_options['exclude_type'] = $pa_options['excludeType']; } if (isset($pa_options['excludeTypes']) && (!isset($pa_options['exclude_types']) || !$pa_options['exclude_types'])) { $pa_options['exclude_types'] = $pa_options['excludeTypes']; } if (isset($pa_options['excludeRelationshipTypes']) && (!isset($pa_options['exclude_relationship_types']) || !$pa_options['exclude_relationship_types'])) { $pa_options['exclude_relationship_types'] = $pa_options['excludeRelationshipTypes']; } $vb_return_as_array = caGetOption('returnAsArray', $pa_options, false, array('castTo' => 'bool')); $vb_return_all_locales = caGetOption('returnAllLocales', $pa_options, false, array('castTo' => 'bool')); $vb_return_as_link = caGetOption('returnAsLink', $pa_options, false, array('castTo' => 'bool')); $vs_return_as_link_text = caGetOption('returnAsLinkText', $pa_options, ''); $vs_return_as_link_target = caGetOption('returnAsLinkTarget', $pa_options, ''); $vs_return_as_link_attributes = caGetOption('returnAsLinkAttributes', $pa_options, array(), array('castTo' => 'array')); $va_original_path_components = $va_path_components = $this->getFieldPathComponents($ps_field); if ($va_path_components['table_name'] != $this->ops_table_name) { $vs_access_chk_key = $va_path_components['table_name'] . ($va_path_components['field_name'] ? '.' . $va_path_components['field_name'] : ''); } else { $vs_access_chk_key = $va_path_components['field_name']; } if (caGetBundleAccessLevel($this->ops_table_name, $vs_access_chk_key) == __CA_BUNDLE_ACCESS_NONE__) { return null; } $vo_request = caGetOption('request', $pa_options, null); unset($pa_options['request']); // first see if the search engine can provide the field value directly (fastest) if (!(($vs_value = $this->opo_engine_result->get($ps_field, $pa_options)) === false)) { if ($vb_return_as_array) { if ($vb_return_all_locales) { return array(1 => $vs_value); } else { return array($vs_value); } } else { return $vs_value; } } $vs_template = caGetOption('template', $pa_options, null); $vs_delimiter = caGetOption('delimiter', $pa_options, ' '); $vs_hierarchical_delimiter = caGetOption('hierarchicalDelimiter', $pa_options, ' '); if ($vb_return_all_locales && !$vb_return_as_array) { $vb_return_as_array = true; } if (isset($pa_options['sort']) && !is_array($pa_options['sort'])) { $pa_options['sort'] = array($pa_options['sort']); } if (is_array($va_sort_fields = isset($pa_options['sort']) && is_array($pa_options['sort']) ? $pa_options['sort'] : null)) { foreach ($va_sort_fields as $vn_i => $vs_sort_fld) { if (!trim($vs_sort_fld)) { unset($va_sort_fields[$vn_i]); } } } $vn_row_id = $this->opo_engine_result->get($this->ops_table_pk); // try to lazy load (slower)... // // Are we getting timestamp (created on or last modified) info? // if ($va_path_components['table_name'] == $this->ops_table_name && $va_path_components['field_name'] == 'created') { if (!isset($this->opa_timestamp_cache['created_on'][$this->ops_table_name][$vn_row_id])) { $this->prefetchChangeLogData($this->ops_table_name, $this->opo_engine_result->currentRow(), $this->getOption('prefetch')); } if ($vb_return_as_array) { return $this->opa_timestamp_cache['created_on'][$this->ops_table_name][$vn_row_id]; } else { $vs_subfield = $va_path_components['subfield_name'] ? $va_path_components['subfield_name'] : 'timestamp'; $vm_val = $this->opa_timestamp_cache['created_on'][$this->ops_table_name][$vn_row_id][$vs_subfield]; if ($vs_subfield == 'timestamp') { $o_tep = new TimeExpressionParser(); $o_tep->setUnixTimestamps($vm_val, $vm_val); $vm_val = $o_tep->getText($pa_options); } return $vm_val; } } if ($va_path_components['table_name'] == $this->ops_table_name && $va_path_components['field_name'] == 'lastModified') { if (!isset($this->opa_timestamp_cache['last_changed'][$this->ops_table_name][$vn_row_id])) { $this->prefetchChangeLogData($this->ops_table_name, $this->opo_engine_result->currentRow(), $this->getOption('prefetch')); } if ($vb_return_as_array) { return $this->opa_timestamp_cache['last_changed'][$this->ops_table_name][$vn_row_id]; } else { $vs_subfield = $va_path_components['subfield_name'] ? $va_path_components['subfield_name'] : 'timestamp'; $vm_val = $this->opa_timestamp_cache['last_changed'][$this->ops_table_name][$vn_row_id][$vs_subfield]; if ($vs_subfield == 'timestamp') { $o_tep = new TimeExpressionParser(); $o_tep->setUnixTimestamps($vm_val, $vm_val); $vm_val = $o_tep->getText($pa_options); } return $vm_val; } } if (!($t_instance = $this->opo_datamodel->getInstanceByTableName($va_path_components['table_name'], true))) { return null; } // Bad table $t_original_instance = $t_instance; // $t_original_instance will always be the as-called subject; optimizations may results in $t_instance being transformed into a different model // // Simple related table get: // <table> // <table>.related // <table>.hierarchy // <table>.related.hierarchy // if ($va_path_components['num_components'] == 1 && $va_path_components['table_name'] !== $this->ops_table_name || $va_path_components['num_components'] == 2 && $va_path_components['field_name'] == 'related' || $va_path_components['num_components'] == 2 && $va_path_components['field_name'] == 'hierarchy' || $va_path_components['num_components'] == 3 && $va_path_components['field_name'] == 'related' && $va_path_components['subfield_name'] == 'hierarchy') { if (!($t_table = $this->opo_datamodel->getInstanceByTableName($this->ops_table_name, true))) { return null; } $vb_show_hierarachy = (bool) ($va_path_components['field_name'] == 'hierarchy' && $t_instance->isHierarchical()); if ($va_path_components['num_components'] == 2) { $va_path_components['num_components'] = 1; $va_path_components['field_name'] = null; } $vs_opt_md5 = caMakeCacheKeyFromOptions($pa_options); if (!isset($this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5])) { $this->prefetchRelated($va_path_components['table_name'], $this->opo_engine_result->currentRow(), $this->getOption('prefetch'), $pa_options); } $va_related_items = $this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5]; if (!is_array($va_related_items)) { return null; } if (is_array($va_sort_fields) && sizeof($va_sort_fields)) { $va_related_items = caSortArrayByKeyInValue($va_related_items, $va_sort_fields); } // Return as array if ($vs_template) { return caProcessTemplateForIDs($vs_template, $this->opo_subject_instance->tableName(), array($vn_row_id), array_merge($pa_options, array('placeholderPrefix' => $va_path_components['field_name']))); } if ($vb_return_as_array || $vb_return_all_locales) { if ($vb_return_all_locales) { $va_related_tmp = array(); foreach ($va_related_items as $vn_i => $va_related_item) { $va_related_tmp[$vn_i][$va_related_item['locale_id']] = $va_related_item; } return $va_related_tmp; } else { if (!$vs_template && !$va_path_components['field_name']) { return $va_related_items; } $vs_pk = $t_instance->primaryKey(); $va_links = array(); foreach ($va_related_items as $vn_relation_id => $va_relation_info) { $va_relation_info['labels'] = caExtractValuesByUserLocale(array(0 => $va_relation_info['labels'])); if ($vb_return_as_link) { $va_template_opts = array(); $va_template_opts['relationshipValues'][$va_relation_info[$vs_pk]][$va_relation_info['relation_id']]['relationship_typename'] = $va_relation_info['relationship_typename']; $vs_text = $vs_template ? caProcessTemplateForIDs($vs_template, $t_instance->tableName(), array($va_relation_info[$vs_pk]), $va_template_opts) : join("; ", $va_relation_info['labels']); $va_link = caCreateLinksFromText(array($vs_text), $va_original_path_components['table_name'], array($va_relation_info[$vs_pk]), $vs_return_as_link_class, $vs_return_as_link_target); $va_links[$vn_relation_id] = array_pop($va_link); } else { $va_related_items[$vn_relation_id]['labels'] = $va_relation_info['labels']; } } if ($vb_return_as_link) { return $va_links; } return $va_related_items; } } else { // Return scalar $va_proc_labels = array(); $va_row_ids = array(); $vs_rel_pk = $t_instance->primaryKey(); $va_relationship_values = array(); foreach ($va_related_items as $vn_relation_id => $va_relation_info) { $va_row_ids[] = $va_relation_info[$vs_rel_pk]; $va_relationship_values[$va_relation_info[$vs_rel_pk]][$vn_relation_id] = array('relationship_typename' => $va_relation_info['relationship_typename'], 'relationship_type_id' => $va_relation_info['relationship_type_id'], 'relationship_type_code' => $va_relation_info['relationship_type_code'], 'relationship_typecode' => $va_relation_info['relationship_type_code'], 'label' => $va_relation_info['label']); } if (!sizeof($va_row_ids)) { return ''; } if (!$vs_template) { $vs_template = "^label"; } $va_template_opts = $pa_options; unset($va_template_opts['request']); unset($va_template_opts['template']); $va_template_opts['returnAsLink'] = false; $va_template_opts['returnAsArray'] = true; $va_text = caProcessTemplateForIDs($vs_template, $t_instance->tableNum(), $va_row_ids, array_merge($va_template_opts, array('relationshipValues' => $va_relationship_values, 'showHierarchicalLabels' => $vb_show_hierarachy))); if ($vb_return_as_link) { $va_links = caCreateLinksFromText($va_text, $va_original_path_components['table_name'], $va_row_ids, $vs_return_as_link_class, $vs_return_as_link_target); return join($vs_delimiter, $va_links); } return join($vs_delimiter, $va_text); } } $vb_need_parent = false; $vb_need_children = false; // // Transform "preferred_labels" into tables for pre-fetching // $vb_is_get_for_labels = $vb_return_all_label_values = $vb_get_preferred_labels_only = $vb_get_nonpreferred_labels_only = false; if (in_array($va_path_components['field_name'], array('preferred_labels', 'nonpreferred_labels'))) { if ($t_instance->getProperty('LABEL_TABLE_NAME')) { $vb_get_preferred_labels_only = $va_path_components['field_name'] == 'preferred_labels' ? true : false; $vb_get_nonpreferred_labels_only = $va_path_components['field_name'] == 'nonpreferred_labels' ? true : false; if ($va_path_components['num_components'] == 2) { // if it's just <table_name>.preferred_labels then return an array of fields from the label table $vb_return_all_label_values = true; } $va_path_components['table_name'] = $t_instance->getLabelTableName(); $t_label_instance = $t_instance->getLabelTableInstance(); if (!$va_path_components['subfield_name'] || !$t_label_instance->hasField($va_path_components['subfield_name'])) { $va_path_components['field_name'] = $t_instance->getLabelDisplayField(); } else { $va_path_components['field_name'] = $va_path_components['subfield_name']; } $va_path_components['subfield_name'] = null; $va_path_components = $this->getFieldPathComponents($va_path_components['table_name'] . '.' . $va_path_components['field_name']); // Ok, convert the table instance to the label table since that's the table we'll be grabbing data from $t_instance = $t_label_instance; $vb_is_get_for_labels = true; } } // // Handle modifiers (parent, children, related, hierarchy) with and without fields // if ($va_path_components['num_components'] >= 2) { switch ($va_path_components['field_name']) { case 'parent': if ($t_instance->isHierarchical() && ($vn_parent_id = $this->get($va_path_components['table_name'] . '.' . $t_instance->getProperty('HIERARCHY_PARENT_ID_FLD')))) { // // TODO: support some kind of prefetching of parents? // unset($va_path_components['components'][1]); if ($t_instance->load($vn_parent_id)) { return $t_instance->get(join('.', array_values($va_path_components['components'])), $pa_options); } return null; } break; case 'children': if ($t_instance->isHierarchical()) { //unset($va_path_components['components'][1]); // remove 'children' from field path $vs_field_spec = join('.', array_values($va_path_components['components'])); if ($vn_id = $this->get($va_path_components['table_name'] . '.' . $t_instance->primaryKey(), array('returnAsArray' => false))) { if ($t_instance->load($vn_id)) { return $t_instance->get($vs_field_spec, $pa_options); } } return null; } break; case 'related': // Regular related table call if ($va_path_components['table_name'] != $this->ops_table_name) { // just remove "related" from name and be on our way $va_tmp = $va_path_components['components']; array_splice($va_tmp, 1, 1); return $this->get(join('.', $va_tmp), $pa_options); } // Self-relations need special handling $vs_opt_md5 = caMakeCacheKeyFromOptions($pa_options); if (!isset($this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5])) { $this->prefetchRelated($va_path_components['table_name'], $this->opo_engine_result->currentRow(), $this->getOption('prefetch'), $pa_options); } $va_related_items = $this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5]; if (!($t_table = $this->opo_datamodel->getInstanceByTableName($va_path_components['table_name'], true))) { return null; } $va_ids = array(); foreach ($va_related_items as $vn_relation_id => $va_item) { $va_ids[] = $va_item[$t_table->primaryKey()]; } $va_vals = array(); if ($qr_res = $t_table->makeSearchResult($va_path_components['table_name'], $va_ids)) { $va_tmp = $va_path_components['components']; unset($va_tmp[1]); $vs_rel_field = join('.', $va_tmp); while ($qr_res->nextHit()) { if ($vb_return_as_array) { $va_vals = array_merge($va_vals, $qr_res->get($vs_rel_field, $pa_options)); } else { $va_vals[] = $qr_res->get($vs_rel_field, $pa_options); } } } //if (is_array($va_sort_fields) && sizeof($va_sort_fields)) { // $va_vals = caSortArrayByKeyInValue($va_vals, $va_sort_fields); //} if ($vb_return_as_link) { if (!$vb_return_all_locales) { $va_vals = caCreateLinksFromText($va_vals, $va_original_path_components['table_name'], $va_ids, $vs_return_as_link_class, $vs_return_as_link_target); } } if ($vb_return_as_array) { return $va_vals; } else { return join($vs_delimiter, $va_vals); } break; case 'hierarchy': $vn_max_levels_from_bottom = caGetOption('maxLevelsFromBottom', $pa_options, caGetOption('maxLevels', $pa_options, null)); $vn_max_levels_from_top = caGetOption('maxLevelsFromTop', $pa_options, null); if ($t_instance->isHierarchical()) { $vs_field_spec = join('.', array_values($va_path_components['components'])); $vs_hier_pk_fld = $t_instance->primaryKey(); if ($va_ids = $this->get($va_path_components['table_name'] . '.' . $vs_hier_pk_fld, array_merge($pa_options, array('returnAsArray' => true, 'returnAsLink' => false, 'returnAllLocales' => false)))) { $va_vals = array(); if ($va_path_components['subfield_name'] == $vs_hier_pk_fld) { foreach ($va_ids as $vn_id) { // TODO: This is too slow if ($t_instance->load($vn_id)) { $va_vals = array_merge($va_vals, $t_instance->get($va_path_components['table_name'] . ".hierarchy." . $vs_hier_pk_fld, array_merge($pa_options, array('returnAsArray' => true)))); } } } else { foreach ($va_ids as $vn_id) { // TODO: This is too slow if ($t_instance->load($vn_id)) { $va_vals = $t_instance->get($vs_field_spec, array_merge($pa_options, array('returnAsArray' => true))); if (is_array($va_vals)) { $va_vals = array_reverse($va_vals); } // Add/replace hierarchy name if ($t_instance->getProperty('HIERARCHY_TYPE') == __CA_HIER_TYPE_MULTI_MONO__ && $t_instance->getHierarchyName()) { $vn_first_key = array_shift(array_keys($va_vals)); if ($vb_return_all_locales) { $va_vals[$vn_first_key] = array(0 => array($t_instance->getHierarchyName())); } else { $va_vals[$vn_first_key] = $t_instance->getHierarchyName(); } } if ($vn_max_levels_from_bottom > 0) { if (($vn_start = sizeof($va_vals) - $vn_max_levels_from_bottom) < 0) { $vn_start = 0; } $va_vals = array_slice($va_vals, $vn_start, $vn_max_levels_from_bottom, true); } elseif ($vn_max_levels_from_top > 0) { $va_vals = array_slice($va_vals, 0, $vn_max_levels_from_top, true); } } } } if ($vb_return_as_array) { return $va_vals; } else { return join($vs_hierarchical_delimiter, $va_vals); } } return null; } break; } } // If the requested table was not added to the query via SearchEngine::addTable() // then auto-add it here. It's better to explicitly add it with addTables() as that call // gives you precise control over which fields are autoloaded and also lets you specify limiting criteria // for selection of related field data; and it also lets you explicitly define the tables used to join the // related table. Autoloading guesses and usually does what you want, but not always. if (!isset($this->opa_tables[$va_path_components['table_name']]) || !$this->opa_tables[$va_path_components['table_name']]) { $va_join_tables = $this->opo_datamodel->getPath($this->ops_table_name, $va_path_components['table_name']); array_shift($va_join_tables); // remove subject table array_pop($va_join_tables); // remove content table (we only need linking tables here) $va_join_criteria = array(); if (is_array($va_primary_ids)) { foreach ($va_primary_ids as $vs_t => $va_t_ids) { if (isset($va_join_tables[$vs_t]) && sizeof($va_t_ids) > 0) { $vs_t_pk = $this->opo_datamodel->getTablePrimaryKeyName($vs_t); $va_join_criteria[] = "{$vs_t}.{$vs_t_pk} NOT IN (" . join(",", $va_t_ids) . ")"; } } } $this->opa_tables[$va_path_components['table_name']] = array('fieldList' => array($va_path_components['table_name'] . '.*'), 'joinTables' => array_keys($va_join_tables), 'criteria' => $va_join_criteria); } if ($va_path_components['table_name'] === $this->ops_table_name && !$t_instance->hasField($va_path_components['field_name']) && method_exists($t_instance, 'getAttributes')) { // // Return attribute values for primary table // if ($va_path_components['field_name'] && ($t_element = $t_instance->_getElementInstance($va_path_components['field_name']))) { $vn_element_id = $t_element->getPrimaryKey(); } else { $vn_element_id = null; } if (!isset(ca_attributes::$s_get_attributes_cache[$this->opn_table_num . '/' . $vn_row_id][$vn_element_id])) { ca_attributes::prefetchAttributes($this->opo_db, $this->opn_table_num, $this->getRowIDsToPrefetch($va_path_components['table_name'], $this->opo_engine_result->currentRow(), $this->getOption('prefetch')), $vn_element_id ? array($vn_element_id) : null, array('dontFetchAlreadyCachedValues' => true)); } if (!$vb_return_as_array && !$vb_return_all_locales) { // return scalar // // Handle "hierarchy" modifier on list elements // if ($va_hier = $this->_getElementHierarchy($t_instance, $va_path_components)) { return join($vs_hierarchical_delimiter, $va_hier); } if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $va_path_components['field_name']) { $vs_template = null; if ($va_path_components['subfield_name']) { $va_values = $t_instance->getAttributeDisplayValues($va_path_components['field_name'], $vn_row_id, $pa_options); $va_value_list = array(); foreach ($va_values as $vn_id => $va_attr_val_list) { foreach ($va_attr_val_list as $vn_value_id => $va_value_array) { $va_value_list[] = $va_value_array[$va_path_components['subfield_name']]; } } return join(" ", $va_value_list); } else { if (isset($pa_options['template'])) { $vs_template = $pa_options['template']; } } unset($pa_options['template']); if (!$vs_template) { $vs_template = "^" . $va_path_components['subfield_name'] ? $va_path_components['subfield_name'] : $va_path_components['field_name']; } return $t_instance->getAttributesForDisplay($va_path_components['field_name'], $vs_template, array_merge(array('row_id' => $vn_row_id), $pa_options)); } if ($t_element && !$va_path_components['subfield_name'] && $t_element->get('datatype') == 0) { return $t_instance->getAttributesForDisplay($va_path_components['field_name'], $vs_template, array_merge($pa_options, array('row_id' => $vn_row_id))); } else { if (!$vs_template) { return $t_instance->getRawValue($vn_row_id, $va_path_components['field_name'], $va_path_components['subfield_name'], ',', $pa_options); } else { return caProcessTemplateForIDs($vs_template, $va_path_components['table_name'], array($vn_row_id), array()); } } } else { // return array // // Handle "hierarchy" modifier on list elements // if ($va_hier = $this->_getElementHierarchy($t_instance, $va_path_components)) { return $va_hier; } $va_values = $t_instance->getAttributeDisplayValues($va_path_components['field_name'], $vn_row_id, $pa_options); if ($vs_template && !$vb_return_all_locales) { $va_values_tmp = array(); foreach ($va_values as $vn_i => $va_value_list) { foreach ($va_value_list as $vn_attr_id => $va_attr_data) { $va_values_tmp[] = caProcessTemplateForIDs($vs_template, $va_path_components['table_name'], array($vn_row_id), array_merge($pa_options, array('placeholderPrefix' => $va_path_components['field_name']))); } } $va_values = $va_values_tmp; } else { if ($va_path_components['subfield_name']) { if ($vb_return_all_locales) { foreach ($va_values as $vn_row_id => $va_values_by_locale) { foreach ($va_values_by_locale as $vn_locale_id => $va_value_list) { foreach ($va_value_list as $vn_attr_id => $va_attr_data) { $va_values[$vn_row_id][$vn_locale_id][$vn_attr_id] = $va_attr_data[$va_path_components['subfield_name']]; } } } } else { $va_processed_value_list = array(); foreach ($va_values as $vn_row_id => $va_value_list) { foreach ($va_value_list as $vn_attr_id => $va_attr_data) { $va_processed_value_list[$vn_attr_id] = $va_attr_data[$va_path_components['subfield_name']]; } } $va_values = $va_processed_value_list; } } else { if (!$vb_return_all_locales) { $va_values = array_shift($va_values); } } } return $va_values; } } else { // Prefetch intrinsic fields in primary and related tables if (!isset($this->opa_prefetch_cache[$va_path_components['table_name']][$vn_row_id])) { $this->prefetch($va_path_components['table_name'], $this->opo_engine_result->currentRow(), $this->getOption('prefetch'), $pa_options); // try to prefetch ahead (usually doesn't hurt and very often helps performance) } } $va_return_values = array(); if ($va_path_components['table_name'] !== $this->ops_table_name && $va_path_components['field_name'] !== 'relationship_typename' && !$t_instance->hasField($va_path_components['field_name']) && method_exists($t_instance, 'getAttributes')) { // // Return metadata attributes in a related table // $vs_pk = $t_instance->primaryKey(); $vb_is_related = $this->ops_table_name !== $va_path_components['table_name']; $va_ids = array(); $vs_opt_md5 = caMakeCacheKeyFromOptions($pa_options); if (!isset($this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5])) { $this->prefetchRelated($va_path_components['table_name'], $this->opo_engine_result->currentRow(), $this->getOption('prefetch'), $pa_options); } if (is_array($this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5])) { foreach ($this->opa_rel_prefetch_cache[$va_path_components['table_name']][$vn_row_id][$vs_opt_md5] as $vn_i => $va_values) { //$vn_locale_id => $va_values_by_locale) { $va_ids[] = $va_values[$vs_pk]; if (!$vb_return_as_array) { $vs_val = $t_instance->getAttributesForDisplay($va_path_components['field_name'], $vs_template, array_merge(array('row_id' => $va_values[$vs_pk]), $pa_options)); } else { $vs_val = $t_instance->getAttributeDisplayValues($va_path_components['field_name'], $va_values[$vs_pk], $pa_options); } if ($vs_val) { if ($vb_return_as_array) { if (!$vb_return_all_locales) { foreach ($vs_val as $vn_i => $va_values_list) { foreach ($va_values_list as $vn_j => $va_values) { $va_return_values[] = $va_values; } } } else { foreach ($vs_val as $vn_i => $va_values_list) { $va_return_values[] = $va_values_list; } } } else { $va_return_values[] = $vs_val; } } } } if ($vb_return_as_array || $vb_return_all_locales) { // return array if ($vb_return_as_link && $vb_is_related) { $vs_table_name = $t_instance->tableName(); $vs_fld_key = $va_path_components['subfield_name'] ? $va_path_components['subfield_name'] : $va_path_components['field_name']; if (!$vb_return_all_locales) { $va_return_values_tmp = array(); foreach ($va_return_values as $vn_i => $va_value) { if ($vs_template) { $vs_value = caProcessTemplateForIDs($vs_template, $va_path_components['table_name'], array($va_ids[$vn_i][$vs_pk]), array('returnAsArray' => false)); } else { $vs_value = $va_value[$vs_fld_key]; } if ($vb_return_as_link) { $va_return_values_tmp[$vn_i] = array_pop(caCreateLinksFromText(array($vs_value), $va_original_path_components['table_name'], array($va_ids[$vn_i]), $vs_return_as_link_class, $vs_return_as_link_target)); } else { $va_return_values_tmp[$vn_i] = $vs_value; } } $va_return_values = $va_return_values_tmp; } } return $va_return_values; } else { // return scalar if ($vb_return_as_link && $vb_is_related) { $va_return_values = caCreateLinksFromText($va_return_values, $va_original_path_components['table_name'], $va_ids, $vs_return_as_link_class, $vs_return_as_link_target); } if (isset($pa_options['convertLineBreaks']) && $pa_options['convertLineBreaks']) { return caConvertLineBreaks(join($vs_delimiter, $va_return_values)); } else { return join($vs_delimiter, $va_return_values); } } } else { if ($vs_template) { return caProcessTemplateForIDs($vs_template, $this->opo_subject_instance->tableName(), array($vn_row_id), array_merge($pa_options, array('placeholderPrefix' => $va_path_components['field_name']))); } // // Return fields (intrinsics, labels) in primary or related table // $t_list = $this->opo_datamodel->getInstanceByTableName('ca_lists', true); $va_value_list = array($vn_row_id => $this->opa_prefetch_cache[$va_path_components['table_name']][$vn_row_id]); // Restrict to relationship types (related) if (isset($pa_options['restrict_to_relationship_types']) && $pa_options['restrict_to_relationship_types']) { if (!is_array($pa_options['restrict_to_relationship_types'])) { $pa_options['restrict_to_relationship_types'] = array($pa_options['restrict_to_relationship_types']); } if (sizeof($pa_options['restrict_to_relationship_types'])) { $t_rel_type = $this->opo_datamodel->getInstanceByTableName('ca_relationship_types', true); $va_rel_types = array(); $va_rel_path = array_keys($this->opo_datamodel->getPath($this->ops_table_name, $va_path_components['table_name'])); foreach ($pa_options['restrict_to_relationship_types'] as $vm_type) { if (!$vm_type) { continue; } if ($vn_type_id = $t_rel_type->getRelationshipTypeID($va_rel_path[1], $vm_type)) { $va_rel_types[] = $vn_type_id; if (is_array($va_children = $t_rel_type->getHierarchyChildren($vn_type_id, array('idsOnly' => true)))) { $va_rel_types = array_merge($va_rel_types, $va_children); } } } if (sizeof($va_rel_types)) { $va_tmp = array(); foreach ($va_value_list as $vn_id => $va_by_locale) { foreach ($va_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if (!$va_value['rel_type_id'] || in_array($va_value['rel_type_id'], $va_rel_types)) { $va_tmp[$vn_id][$vn_locale_id][$vn_i] = $va_value; } } } } $va_value_list = $va_tmp; } } } // Exclude relationship types (related) if (isset($pa_options['exclude_relationship_types']) && $pa_options['exclude_relationship_types']) { if (!is_array($pa_options['exclude_relationship_types'])) { $pa_options['exclude_relationship_types'] = array($pa_options['exclude_relationship_types']); } if (sizeof($pa_options['exclude_relationship_types'])) { $t_rel_type = $this->opo_datamodel->getInstanceByTableName('ca_relationship_types', true); $va_rel_types = array(); $va_rel_path = array_keys($this->opo_datamodel->getPath($this->ops_table_name, $va_path_components['table_name'])); foreach ($pa_options['exclude_relationship_types'] as $vm_type) { if ($vn_type_id = $t_rel_type->getRelationshipTypeID($va_rel_path[1], $vm_type)) { $va_rel_types[] = $vn_type_id; if (is_array($va_children = $t_rel_type->getHierarchyChildren($vn_type_id, array('idsOnly' => true)))) { $va_rel_types = array_merge($va_rel_types, $va_children); } } } if (sizeof($va_rel_types)) { $va_tmp = array(); foreach ($va_value_list as $vn_id => $va_by_locale) { foreach ($va_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if (!in_array($va_value['rel_type_id'], $va_rel_types)) { $va_tmp[$vn_id][$vn_locale_id][$vn_i] = $va_value; } } } } $va_value_list = $va_tmp; } } } // Restrict to types (related) $va_type_ids = $vs_type_fld = null; if (method_exists($t_instance, "getTypeFieldName")) { $va_type_ids = caMergeTypeRestrictionLists($t_instance, $pa_options); $vs_type_fld = $t_instance->getTypeFieldName(); } else { if (method_exists($t_instance, "getSubjectTableInstance")) { $t_label_subj_instance = $t_instance->getSubjectTableInstance(); if (method_exists($t_label_subj_instance, "getTypeFieldName")) { $va_type_ids = caMergeTypeRestrictionLists($t_label_subj_instance, $pa_options); $vs_type_fld = 'item_type_id'; } } } if (is_array($va_type_ids) && sizeof($va_type_ids)) { $va_tmp = array(); foreach ($va_value_list as $vn_id => $va_by_locale) { foreach ($va_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if (!$va_value[$vs_type_fld ? $vs_type_fld : 'item_type_id'] || in_array($va_value[$vs_type_fld ? $vs_type_fld : 'item_type_id'], $va_type_ids)) { $va_tmp[$vn_id][$vn_locale_id][$vn_i] = $va_value; } } } } $va_value_list = $va_tmp; } // Restrict to sources (related) $va_source_ids = $vs_source_id_fld = null; if (method_exists($t_instance, "getSourceFieldName")) { $va_source_ids = caMergeSourceRestrictionLists($t_instance, $pa_options); $vs_source_id_fld = $t_instance->getSourceFieldName(); } else { if (method_exists($t_instance, "getSubjectTableInstance")) { $t_label_subj_instance = $t_instance->getSubjectTableInstance(); if (method_exists($t_label_subj_instance, "getSourceFieldName")) { $va_source_ids = caMergeSourceRestrictionLists($t_label_subj_instance, $pa_options); $vs_source_id_fld = 'item_source_id'; } } } if (is_array($va_source_ids) && sizeof($va_source_ids)) { $va_tmp = array(); foreach ($va_value_list as $vn_id => $va_by_locale) { foreach ($va_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if (!$va_value[$vs_source_id_fld ? $vs_source_id_fld : 'item_source_id'] || in_array($va_value[$vs_source_id_fld ? $vs_source_id_fld : 'item_source_id'], $va_source_ids)) { $va_tmp[$vn_id][$vn_locale_id][$vn_i] = $va_value; } } } } $va_value_list = $va_tmp; } // Exclude types (related) if (isset($pa_options['exclude_type']) && $pa_options['exclude_type']) { if (!isset($pa_options['exclude_types']) || !is_array($pa_options['exclude_types'])) { $pa_options['exclude_types'] = array(); } $pa_options['exclude_types'][] = $pa_options['exclude_type']; } if (isset($pa_options['exclude_types']) && is_array($pa_options['exclude_types'])) { $va_ids = caMakeTypeIDList($va_path_components['table_name'], $pa_options['exclude_types']); if (is_array($va_ids) && sizeof($va_ids) > 0) { $va_tmp = array(); foreach ($va_value_list as $vn_id => $va_by_locale) { foreach ($va_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if (!in_array($va_value[$vs_type_fld ? $vs_type_fld : 'item_type_id'], $va_type_ids)) { $va_tmp[$vn_id][$vn_locale_id][$vn_i] = $va_value; } } } } $va_value_list = $va_tmp; } } // Handle 'relationship_typename' (related) $vb_get_relationship_typename = false; if ($va_path_components['field_name'] == 'relationship_typename') { $va_path_components['field_name'] = 'rel_type_id'; $vb_get_relationship_typename = true; } if ($vb_return_as_array) { // return array (intrinsics or labels in primary or related table) if ($t_instance->hasField($va_path_components['field_name']) && $va_path_components['table_name'] === $t_instance->tableName()) { // Intrinsic $va_field_info = $t_instance->getFieldInfo($va_path_components['field_name']); $vs_pk = $t_original_instance->primaryKey(); // Handle specific intrinsic types switch ($va_field_info['FIELD_TYPE']) { case FT_DATERANGE: case FT_HISTORIC_DATERANGE: foreach ($va_value_list as $vn_id => $va_values_by_locale) { foreach ($va_values_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { $va_ids[] = $va_value[$vs_pk]; if (caGetOption('GET_DIRECT_DATE', $pa_options, false) || caGetOption('getDirectDate', $pa_options, false)) { if (caGetOption('sortable', $pa_options, false)) { $vs_prop = $va_value[$va_field_info['START']] . '/' . $va_value[$va_field_info['END']]; } else { $vs_prop = $va_value[$va_field_info['START']]; } } else { $this->opo_tep->init(); if ($va_field_info['FIELD_TYPE'] == FT_DATERANGE) { $this->opo_tep->setUnixTimestamps($va_value[$va_field_info['START']], $va_value[$va_field_info['END']]); } else { $this->opo_tep->setHistoricTimestamps($va_value[$va_field_info['START']], $va_value[$va_field_info['END']]); } $vs_prop = $this->opo_tep->getText($pa_options); } if ($vb_return_all_locales) { $va_return_values[$vn_row_id][$vn_locale_id][] = $vs_prop; } else { $va_return_values[] = $vs_prop; } } } } break; case FT_MEDIA: if (!($vs_version = $va_path_components['subfield_name'])) { $vs_version = "largeicon"; } foreach ($va_value_list as $vn_id => $va_values_by_locale) { foreach ($va_values_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { $va_ids[] = $va_value[$vs_pk]; if (isset($pa_options['unserialize']) && $pa_options['unserialize']) { $vs_prop = caUnserializeForDatabase($va_value[$va_path_components['field_name']]); if ($vb_return_all_locales) { $va_return_values[$vn_row_id][$vn_locale_id][] = $vs_prop; } else { $va_return_values[] = $vs_prop; } } else { $o_media_settings = new MediaProcessingSettings($va_path_components['table_name'], $va_path_components['field_name']); $va_versions = $o_media_settings->getMediaTypeVersions('*'); if (!isset($va_versions[$vs_version])) { $va_tmp = array_keys($va_versions); $vs_version = array_shift($va_tmp); } // See if an info element was passed, eg. ca_object_representations.media.icon.width should return the width of the media rather than a tag or url to the media $vs_info_element = $va_path_components['num_components'] == 4 ? $va_path_components['components'][3] : null; if ($vb_return_all_locales) { if ($vs_info_element) { $va_return_values[$vn_row_id][$vn_locale_id][] = $this->getMediaInfo($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $vs_info_element, $pa_options); } elseif (isset($pa_options['returnURL']) && $pa_options['returnURL']) { $va_return_values[$vn_row_id][$vn_locale_id][] = $this->getMediaUrl($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } else { $va_return_values[$vn_row_id][$vn_locale_id][] = $this->getMediaTag($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } } else { if ($vs_info_element) { $va_return_values[] = $this->getMediaInfo($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $vs_info_element, $pa_options); } elseif (isset($pa_options['returnURL']) && $pa_options['returnURL']) { $va_return_values[] = $this->getMediaUrl($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } else { $va_return_values[] = $this->getMediaTag($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } } } } } } break; default: // is intrinsic field in primary table $vb_supports_preferred = (bool) $t_instance->hasField('is_preferred'); foreach ($va_value_list as $vn_id => $va_values_by_locale) { foreach ($va_values_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { $va_ids[] = $vn_id = $va_value[$vs_pk]; if ($vb_get_preferred_labels_only && $vb_supports_preferred && !$va_value['is_preferred']) { continue; } if ($vb_get_nonpreferred_labels_only && $vb_supports_preferred && $va_value['is_preferred']) { continue; } $vs_prop = $va_value[$va_path_components['field_name']]; if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST_CODE"))) { $vs_prop = $t_list->getItemFromListForDisplayByItemID($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST"))) { $vs_prop = $t_list->getItemFromListForDisplayByItemValue($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $va_path_components['field_name'] === 'locale_id' && (int) $vs_prop > 0) { $t_locale = new ca_locales($vs_prop); $vs_prop = $t_locale->getName(); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && is_array($va_list = $t_instance->getFieldInfo($va_path_components['field_name'], "BOUNDS_CHOICE_LIST"))) { foreach ($va_list as $vs_option => $vs_value) { if ($vs_value == $vs_prop) { $vs_prop = $vs_option; break; } } } } } } if ($vb_return_all_locales) { $va_return_values[$vn_id][$vn_locale_id][] = $vs_prop; } else { $va_return_values[$vn_id][$vn_locale_id] = $vs_prop; } } } } if (!$vb_return_all_locales) { $va_return_values = array_values(caExtractValuesByUserLocale($va_return_values)); } break; } } else { // Attributes $vs_pk = $t_original_instance->primaryKey(); $vb_is_related = $this->ops_table_name !== $va_path_components['table_name']; $va_ids = array(); $t_instance = $this->opo_datamodel->getInstanceByTableName($va_path_components['table_name'], true); foreach ($va_value_list as $vn_i => $va_values_by_locale) { foreach ($va_values_by_locale as $vn_locale_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { if ($vb_is_related) { $va_ids[] = $va_value[$vs_pk]; } if ($vb_get_preferred_labels_only && !$va_value['is_preferred']) { continue; } if ($vb_get_nonpreferred_labels_only && $va_value['is_preferred']) { continue; } // do we need to translate foreign key and choice list codes to display text? $vs_prop = $vb_return_all_label_values && !$vb_return_as_link ? $va_value : $va_value[$va_path_components['field_name']]; if ($vb_get_relationship_typename) { if (!$t_rel_type) { $t_rel_type = $this->opo_datamodel->getInstanceByTableName('ca_relationship_types', true); } if (is_array($va_labels = $t_rel_type->getDisplayLabels(false, array('row_id' => (int) $vs_prop)))) { $va_label = array_shift($va_labels); $vs_prop = $va_label[0]['typename']; } else { $vs_prop = "?"; } } else { // Decode list items to text if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST_CODE"))) { $vs_prop = $t_list->getItemFromListForDisplayByItemID($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST"))) { $vs_prop = $t_list->getItemFromListForDisplayByItemValue($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $va_path_components['field_name'] === 'locale_id' && (int) $vs_prop > 0) { $t_locale = new ca_locales($vs_prop); $vs_prop = $t_locale->getName(); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && is_array($va_list = $t_instance->getFieldInfo($va_path_components['field_name'], "BOUNDS_CHOICE_LIST"))) { foreach ($va_list as $vs_option => $vs_value) { if ($vs_value == $vs_prop) { $vs_prop = $vs_option; break; } } } } } } } if ($vb_return_all_locales) { $va_return_values[$vn_row_id][$vn_locale_id][] = $vs_prop; } else { if ($vb_get_nonpreferred_labels_only && is_array($vs_prop)) { // non-preferred labels are lists of lists because they can repeat $va_return_values[][] = $vs_prop; } else { $va_return_values[] = $vs_prop; } } } } } } if ($vb_return_as_link) { if (!$vb_return_all_locales) { $va_return_values = caCreateLinksFromText($va_return_values, $va_original_path_components['table_name'], $va_ids, $vs_return_as_link_class, $vs_return_as_link_target); } } return $va_return_values; } else { // Return scalar (intrinsics or labels in primary or related table) if ($vb_get_preferred_labels_only || $vb_get_nonpreferred_labels_only) { // We have to distinguish between preferred and non-preferred labels here // so that only appropriate labels are passed for output. $va_filtered_values = array(); foreach ($va_value_list as $vn_label_id => $va_labels_by_locale) { foreach ($va_labels_by_locale as $vn_locale_id => $va_labels) { foreach ($va_labels as $vn_i => $va_label) { if ($vb_get_preferred_labels_only && (!isset($va_label['is_preferred']) || $va_label['is_preferred']) || $vb_get_nonpreferred_labels_only && !$va_label['is_preferred']) { $va_filtered_values[$vn_label_id][$vn_locale_id][] = $va_label; } } } } $va_value_list = $va_filtered_values; } $va_value_list = caExtractValuesByUserLocale($va_value_list); // do we need to translate foreign key and choice list codes to display text? $t_instance = $this->opo_datamodel->getInstanceByTableName($va_path_components['table_name'], true); $va_field_info = $t_instance->getFieldInfo($va_path_components['field_name']); $vs_pk = $t_instance->primaryKey(); $vb_is_related = $this->ops_table_name !== $va_path_components['table_name']; $va_ids = array(); foreach ($va_value_list as $vn_i => $va_values) { if (!is_array($va_values)) { continue; } // Handle specific intrinsic types $vs_template_value = $vs_template; foreach ($va_values as $vn_j => $va_value) { switch ($va_field_info['FIELD_TYPE']) { case FT_BIT: if ($pa_options['convertCodesToDisplayText']) { $va_value[$va_path_components['field_name']] = (bool) $vs_prop ? _t('yes') : _t('no'); } break; case FT_DATERANGE: if (caGetOption('GET_DIRECT_DATE', $pa_options, false) || caGetOption('getDirectDate', $pa_options, false)) { if (isset($pa_options['sortable']) && $pa_options['sortable']) { $va_value[$va_path_components['field_name']] = $va_value[$va_field_info['START']] . '/' . $va_value[$va_field_info['END']]; } else { $va_value[$va_path_components['field_name']] = $va_value[$va_field_info['START']]; } } else { $this->opo_tep->init(); $this->opo_tep->setUnixTimestamps($va_value[$va_field_info['START']], $va_value[$va_field_info['END']]); $va_value[$va_path_components['field_name']] = $this->opo_tep->getText($pa_options); } break; case FT_HISTORIC_DATERANGE: if (caGetOption('GET_DIRECT_DATE', $pa_options, false) || caGetOption('getDirectDate', $pa_options, false)) { if (caGetOption('sortable', $pa_options, false)) { $va_value[$va_path_components['field_name']] = $va_value[$va_field_info['START']] . '/' . $va_value[$va_field_info['END']]; } else { $va_value[$va_path_components['field_name']] = $va_value[$va_field_info['START']]; } } else { $this->opo_tep->init(); $this->opo_tep->setHistoricTimestamps($va_value[$va_field_info['START']], $va_value[$va_field_info['END']]); $va_value[$va_path_components['field_name']] = $this->opo_tep->getText($pa_options); } break; case FT_MEDIA: if (!($vs_version = $va_path_components['subfield_name'])) { $vs_version = "largeicon"; } // See if an info element was passed, eg. ca_object_representations.media.icon.width should return the width of the media rather than a tag or url to the media $vs_info_element = $va_path_components['num_components'] == 4 ? $va_path_components['components'][3] : null; if (isset($pa_options['unserialize']) && $pa_options['unserialize']) { return caUnserializeForDatabase($va_value[$va_path_components['field_name']]); } else { $o_media_settings = new MediaProcessingSettings($va_path_components['table_name'], $va_path_components['field_name']); $va_versions = $o_media_settings->getMediaTypeVersions('*'); if (!isset($va_versions[$vs_version])) { $va_tmp = array_keys($va_versions); $vs_version = array_shift($va_tmp); } if ($vs_info_element) { // Return media info $va_value[$va_path_components['field_name']] = $this->getMediaInfo($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $vs_info_element, $pa_options); } elseif (isset($pa_options['returnURL']) && $pa_options['returnURL']) { $va_value[$va_path_components['field_name']] = $this->getMediaUrl($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } else { $va_value[$va_path_components['field_name']] = $this->getMediaTag($va_path_components['table_name'] . '.' . $va_path_components['field_name'], $vs_version, $pa_options); } } break; default: // noop break; } $vs_prop = $va_value[$va_path_components['field_name']]; // Decode list items to text if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST_CODE"))) { $va_value[$va_path_components['field_name']] = $t_list->getItemFromListForDisplayByItemID($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && ($vs_list_code = $t_instance->getFieldInfo($va_path_components['field_name'], "LIST"))) { $va_value[$va_path_components['field_name']] = $t_list->getItemFromListForDisplayByItemValue($vs_list_code, $vs_prop); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && $va_path_components['field_name'] === 'locale_id' && (int) $vs_prop > 0) { $t_locale = new ca_locales($vs_prop); $va_value[$va_path_components['field_name']] = $t_locale->getName(); } else { if (isset($pa_options['convertCodesToDisplayText']) && $pa_options['convertCodesToDisplayText'] && is_array($va_list = $t_instance->getFieldInfo($va_path_components['field_name'], "BOUNDS_CHOICE_LIST"))) { foreach ($va_list as $vs_option => $vs_value) { if ($vs_value == $vs_prop) { $va_value[$va_path_components['field_name']] = $vs_option; break; } } } } } } $vs_pk = $this->opo_datamodel->getTablePrimaryKeyName($va_original_path_components['table_name']); if ($vs_template) { foreach ($va_value_list as $vn_id => $va_values) { foreach ($va_values as $vn_i => $va_value) { $vs_prop = caProcessTemplateForIDs($vs_template, $va_original_path_components['table_name'], array($va_value[$vs_pk]), array('returnAsArray' => false)); $va_return_values[] = $vs_prop; $va_ids[] = $va_value[$vs_pk]; } } } else { $vs_prop = $va_value[$va_path_components['field_name']]; $va_return_values[] = $vs_prop; if ($vb_is_related) { $va_ids[] = $va_value[$vs_pk]; } } } } if ($vb_return_as_link && $vb_is_related) { $va_return_values = caCreateLinksFromText($va_return_values, $va_original_path_components['table_name'], $va_ids, $vs_return_as_link_class, $vs_return_as_link_target); } if (isset($pa_options['convertLineBreaks']) && $pa_options['convertLineBreaks']) { return caConvertLineBreaks(join($vs_delimiter, $va_return_values)); } else { return join($vs_delimiter, $va_return_values); } } } return null; }