/** * Returns the current category being viewed. * * @access public * @since 8.5.18 * @static * * @return false|cnTerm_Object */ public static function getCurrent() { $current = FALSE; if (cnQuery::getVar('cn-cat-slug')) { $slug = explode('/', cnQuery::getVar('cn-cat-slug')); // If the category slug is a descendant, use the last slug from the URL for the query. $current = end($slug); } elseif ($catIDs = cnQuery::getVar('cn-cat')) { if (is_array($catIDs)) { // If value is a string, strip the white space and covert to an array. $catIDs = wp_parse_id_list($catIDs); // Use the first element $current = reset($catIDs); } else { $current = $catIDs; } } if (!empty($current)) { if (ctype_digit((string) $current)) { $field = 'id'; } else { $field = 'slug'; } $current = cnTerm::getBy($field, $current, 'category'); // cnTerm::getBy() can return NULL || an instance of WP_Error, so, lets check for that. if (!is_a($current, 'cnTerm_Object')) { $current = FALSE; } } return $current; }
/** * Display a message box above the search results with information * about the current query and the option (a button) to clear results. * * @access public * @since 0.8 * @static * @param array $atts The shortcode $atts array. * @param array $results The cnRetrieve query results. * @param cnTemplate|null $template An instance of the cnTemplate object. * * @return string */ public static function searchingMessage($atts = array(), $results = array(), $template = NULL) { // Check whether or not the category description should be displayed or not. if (!cnSettingsAPI::get('connections', 'connections_display_results', 'search_message')) { return ''; } $html = ''; $messages = array(); $defaults = array('header' => '', 'header_tag' => 'h3', 'container_tag' => 'ul', 'item_tag' => 'li', 'before' => '', 'before-item' => '', 'after-item' => '', 'after' => '', 'return' => FALSE); $atts = wp_parse_args($atts, apply_filters('cn_search_results_atts', $defaults)); // Get the directory home page ID. $homeID = $atts['force_home'] ? cnSettingsAPI::get('connections', 'connections_home_page', 'page_id') : $atts['home_id']; //$addAction = cnSettingsAPI::get( 'connections', 'connections_home_page', 'page_id' ) != $atts['home_id'] ? TRUE : FALSE; // The base post permalink is required, do not filter the permalink thru cnSEO. if (!is_admin()) { cnSEO::doFilterPermalink(FALSE); } $permalink = get_permalink($homeID); $permalink = apply_filters('cn_permalink', $permalink, $atts); // Re-enable the filter. if (!is_admin()) { cnSEO::doFilterPermalink(); } // Store the query vars $queryVars = array(); $queryVars['cn-s'] = cnQuery::getVar('cn-s') ? esc_html(cnQuery::getVar('cn-s')) : FALSE; $queryVars['cn-char'] = cnQuery::getVar('cn-char') ? esc_html(urldecode(cnQuery::getVar('cn-char'))) : FALSE; $queryVars['cn-cat'] = cnQuery::getVar('cn-cat') ? cnQuery::getVar('cn-cat') : FALSE; $queryVars['cn-organization'] = cnQuery::getVar('cn-organization') ? esc_html(urldecode(cnQuery::getVar('cn-organization'))) : FALSE; $queryVars['cn-department'] = cnQuery::getVar('cn-department') ? esc_html(urldecode(cnQuery::getVar('cn-department'))) : FALSE; $queryVars['cn-locality'] = cnQuery::getVar('cn-locality') ? esc_html(urldecode(cnQuery::getVar('cn-locality'))) : FALSE; $queryVars['cn-region'] = cnQuery::getVar('cn-region') ? esc_html(urldecode(cnQuery::getVar('cn-region'))) : FALSE; $queryVars['cn-postal-code'] = cnQuery::getVar('cn-postal-code') ? esc_html(urldecode(cnQuery::getVar('cn-postal-code'))) : FALSE; $queryVars['cn-country'] = cnQuery::getVar('cn-country') ? esc_html(urldecode(cnQuery::getVar('cn-country'))) : FALSE; // if ( cnQuery::getVar('cn-near-coord') ) $queryVars['cn-near-coord'] = cnQuery::getVar('cn-near-coord'); // if ( cnQuery::getVar('cn-radius') ) $queryVars['cn-radius'] = cnQuery::getVar('cn-radius'); // if ( cnQuery::getVar('cn-unit') ) $queryVars['cn-unit'] = cnQuery::getVar('cn-unit'); $messages = apply_filters('cn_search_results_messages-before', $messages, $atts, $results, $template); if ($queryVars['cn-cat']) { $categoryID = $queryVars['cn-cat']; $terms = array(); // Since the `cn-cat` query var can be an array, we'll only add the category slug // template name when querying a single category. if (is_array($categoryID)) { foreach ($categoryID as $id) { $term = cnTerm::getBy('id', $id, 'category'); $terms[] = esc_html($term->name); } } else { $term = cnTerm::getBy('id', $categoryID, 'category'); $terms[] = esc_html($term->name); } $messages['cn-cat'] = sprintf(__('You are searching within category(ies): %s', 'connections'), implode(', ', $terms)); } if ($queryVars['cn-s']) { // If value is a string, string the white space and covert to an array. if (!is_array($queryVars['cn-s'])) { $originalString = array($queryVars['cn-s']); $queryVars['cn-s'] = cnFunction::parseStringList($queryVars['cn-s'], '\\s'); $queryVars['cn-s'] = array_merge($originalString, $queryVars['cn-s']); $queryVars['cn-s'] = array_unique($queryVars['cn-s']); } // Trim any white space from around the terms in the array. array_walk($queryVars['cn-s'], 'trim'); $messages['cn-s'] = sprintf(__('You are searching for the keyword(s): %s', 'connections'), esc_html(implode(', ', $queryVars['cn-s']))); } if ($queryVars['cn-char']) { $messages['cn-char'] = sprintf(__('The results are being filtered by the character: %s', 'connections'), $queryVars['cn-char']); } if ($queryVars['cn-organization']) { $messages['cn-organization'] = sprintf(__('The results are being filtered by the organization: %s', 'connections'), $queryVars['cn-organization']); } if ($queryVars['cn-department']) { $messages['cn-department'] = sprintf(__('The results are being filtered by the department: %s', 'connections'), $queryVars['cn-department']); } if ($queryVars['cn-locality']) { $messages['cn-locality'] = sprintf(__('The results are being filtered by the locality: %s', 'connections'), $queryVars['cn-locality']); } if ($queryVars['cn-region']) { $messages['cn-region'] = sprintf(__('The results are being filtered by the region: %s', 'connections'), $queryVars['cn-region']); } if ($queryVars['cn-postal-code']) { $messages['cn-postal-code'] = sprintf(__('The results are being filtered by the postal code: %s', 'connections'), $queryVars['cn-postal-code']); } if ($queryVars['cn-country']) { $messages['cn-country'] = sprintf(__('The results are being filtered by the country: %s', 'connections'), $queryVars['cn-country']); } $messages = apply_filters('cn_search_results_messages-after', $messages, $atts, $results, $template); $messages = apply_filters('cn_search_results_messages', $messages, $atts, $results, $template); if (!empty($messages)) { if (0 < strlen($atts['header'])) { $header = sprintf('<%1$s class="cn-search-message-header">%2$s</%1$s>', $atts['header_tag'], esc_html($atts['header'])); } else { $header = ''; } // Render the HTML <li> items. foreach ($messages as $key => $message) { $html .= sprintf(PHP_EOL . "\t" . '<%2$s class="cn-search-message-list-item" id="cn-search-message-list-item-%3$s">%1$s%4$s%5$s</%2$s>', $atts['before-item'], $atts['item_tag'], esc_attr($key), wp_kses_post($message), $atts['after-item']); } // Wrap the <li> items in a <ul>. $html = sprintf('<%1$s class="cn-search-message-list">%2$s' . PHP_EOL . '</%1$s>', $atts['container_tag'], $html); // Add the clear search button. $html .= sprintf('<div id="cn-clear-search"><a class="button btn" id="cn-clear-search-button" href="%1$s">%2$s</a></div>' . PHP_EOL, esc_url($permalink), __('Clear Search', 'connections')); // Wrap it all in a <div>. $html = '<div id="cn-search-messages">' . $header . $html . '</div>' . PHP_EOL; } $html = $atts['before'] . $html . $atts['after'] . PHP_EOL; return self::echoOrReturn($atts['return'], $html); }
/** * Add the the current Connections category description or entry bio excerpt as the page meta description. * * @access private * @since 0.7.8 * @static * * @uses cnQuery::getVar() * @uses esc_attr() * @uses strip_shortcodes() */ public static function metaDesc() { // Whether or not to filter the page title with the current directory location. if (!cnSettingsAPI::get('connections', 'seo_meta', 'page_desc')) { return; } $description = ''; if (cnQuery::getVar('cn-cat-slug')) { // If the category slug is a descendant, use the last slug from the URL for the query. $categorySlug = explode('/', cnQuery::getVar('cn-cat-slug')); if (isset($categorySlug[count($categorySlug) - 1])) { $categorySlug = $categorySlug[count($categorySlug) - 1]; } $term = cnTerm::getBy('slug', $categorySlug, 'category'); $category = new cnCategory($term); $description = $category->getExcerpt(array('length' => 160)); } if (cnQuery::getVar('cn-cat')) { if (is_array(cnQuery::getVar('cn-cat'))) { return; } $categoryID = cnQuery::getVar('cn-cat'); $term = cnTerm::getBy('id', $categoryID, 'category'); $category = new cnCategory($term); $description = $category->getExcerpt(array('length' => 160)); } if (cnQuery::getVar('cn-entry-slug')) { // Grab an instance of the Connections object. $instance = Connections_Directory(); $result = $instance->retrieve->entries(array('slug' => urldecode(cnQuery::getVar('cn-entry-slug')))); // Make sure an entry is returned and then echo the meta desc. if (!empty($result)) { $entry = new cnEntry($result[0]); $description = $entry->getExcerpt(array('length' => 160)); } } if (0 == strlen($description)) { return; } echo '<meta name="description" content="' . esc_attr(trim(strip_shortcodes(strip_tags(stripslashes($description))))) . '"/>' . "\n"; }
/** * Constructor. * * @access public * @since 8.2 * * @uses cnTerm::getBy() * * @see WP_List_Table::__construct() for more information on default arguments. * * @param array $args An associative array of arguments. */ public function __construct($args = array()) { // @todo allow this to be settable via an option in arg. Also should verify the taxonomy exists. $this->taxonomy = 'category'; parent::__construct(array('plural' => 'terms', 'singular' => 'term', 'ajax' => FALSE)); // @todo Add option for user to get the default category. //$this->default_term = get_option( "cn_default_{$taxonomy}" ); // Temporarily hard code the default category to the Uncategorized category // and ensure it can not be deleted. This should be removed when the default // category can be set by the user. $default_term = cnTerm::getBy('slug', 'uncategorized', $this->taxonomy); $this->default_term = $default_term->term_id; }
/** * An indexed array of file names to be searched for. * * The file names is an index array of file names where the * highest priority is first and the lowest priority is last. * * @access private * @since 0.8 * @uses apply_filters() * @uses get_query_var() * @param string $base The base file name. Typically `card` for a template file and the template slug for CSS and JS files. * @param string $name The template part name; such as `single` or `category`. * @param string $slug The template part slug; such as an entry slug or category slug. * @param string $ext [optional] The template file name extension. Defaults to `php`. * * @return array An indexed array of file names to search for. */ private function fileNames($base, $name = NULL, $slug = NULL, $ext = 'php') { $files = array(); if (get_query_var('cn-cat')) { $categoryID = get_query_var('cn-cat'); // Since the `cn-cat` query var can be an array, we'll only add the category slug // template name when querying a single category. if (!is_array($categoryID)) { $term = cnTerm::getBy('id', $categoryID, 'category'); $files[] = $this->fileName($base, 'category', $term->slug, $ext); } $files[] = $this->fileName($base, 'category', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-cat-slug')) { $files[] = $this->fileName($base, 'category', get_query_var('cn-cat-slug'), $ext); $files[] = $this->fileName($base, 'category', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-country')) { $country = $this->queryVarSlug(get_query_var('cn-country')); $files[] = $this->fileName($base, 'country', $country, $ext); $files[] = $this->fileName($base, 'country', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-region')) { $region = $this->queryVarSlug(get_query_var('cn-region')); $files[] = $this->fileName($base, 'region', $region, $ext); $files[] = $this->fileName($base, 'region', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-postal-code')) { $zipcode = $this->queryVarSlug(get_query_var('cn-postal-code')); $files[] = $this->fileName($base, 'postal-code', $zipcode, $ext); $files[] = $this->fileName($base, 'postal-code', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-locality')) { $locality = $this->queryVarSlug(get_query_var('cn-locality')); $files[] = $this->fileName($base, 'locality', $locality, $ext); $files[] = $this->fileName($base, 'locality', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-organization')) { $organization = $this->queryVarSlug(get_query_var('cn-organization')); $files[] = $this->fileName($base, 'organization', $organization, $ext); $files[] = $this->fileName($base, 'organization', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-department')) { $department = $this->queryVarSlug(get_query_var('cn-department')); $files[] = $this->fileName($base, 'department', $department, $ext); $files[] = $this->fileName($base, 'department', NULL, $ext); // var_dump( $files ); } if (get_query_var('cn-entry-slug')) { $files[] = $this->fileName($base, NULL, get_query_var('cn-entry-slug'), $ext); $files[] = $this->fileName($base, 'single', NULL, $ext); // var_dump( $files ); } // Add the base as the least priority, since it is required. $files[] = $this->fileName($base, NULL, NULL, $ext); /** * Allow template choices to be filtered. * * The resulting array should be in the order of most specific first, least specific last. * e.g. 0 => card-single.php, 1 => card.php */ $files = apply_filters('cn_template_file_names-' . $this->slug, $files, $base, $name, $slug, $ext); // var_dump( $files ); // Sort the files based on priority ksort($files, SORT_NUMERIC); // var_dump( $files ); return array_filter($files); }
/** * Display a message box above the search results with information * about the current query and the option (a button) to clear results. * * @access public * @since 0.8 * @static * @param array $atts The shortcode $atts array. * @param array $results The cnRetrieve query results. * @param cnTemplate|null $template An instance of the cnTemplate object. * * @return string */ public static function searchingMessage($atts = array(), $results = array(), $template = NULL) { // Check whether or not the category description should be displayed or not. if (!cnSettingsAPI::get('connections', 'connections_display_results', 'search_message')) { return ''; } $defaults = array('return' => FALSE); $atts = wp_parse_args($atts, $defaults); $out = array(); // Get the directory home page ID. $homeID = $atts['force_home'] ? cnSettingsAPI::get('connections', 'connections_home_page', 'page_id') : $atts['home_id']; //$addAction = cnSettingsAPI::get( 'connections', 'connections_home_page', 'page_id' ) != $atts['home_id'] ? TRUE : FALSE; // The base post permalink is required, do not filter the permalink thru cnSEO. if (!is_admin()) { cnSEO::doFilterPermalink(FALSE); } $permalink = get_permalink($homeID); $permalink = apply_filters('cn_permalink', $permalink, $atts); // Re-enable the filter. if (!is_admin()) { cnSEO::doFilterPermalink(); } // Store the query vars $queryVars = array(); $queryVars['cn-s'] = get_query_var('cn-s') ? esc_html(get_query_var('cn-s')) : FALSE; $queryVars['cn-char'] = get_query_var('cn-char') ? esc_html(urldecode(get_query_var('cn-char'))) : FALSE; $queryVars['cn-cat'] = get_query_var('cn-cat') ? get_query_var('cn-cat') : FALSE; $queryVars['cn-organization'] = get_query_var('cn-organization') ? esc_html(urldecode(get_query_var('cn-organization'))) : FALSE; $queryVars['cn-department'] = get_query_var('cn-department') ? esc_html(urldecode(get_query_var('cn-department'))) : FALSE; $queryVars['cn-locality'] = get_query_var('cn-locality') ? esc_html(urldecode(get_query_var('cn-locality'))) : FALSE; $queryVars['cn-region'] = get_query_var('cn-region') ? esc_html(urldecode(get_query_var('cn-region'))) : FALSE; $queryVars['cn-postal-code'] = get_query_var('cn-postal-code') ? esc_html(urldecode(get_query_var('cn-postal-code'))) : FALSE; $queryVars['cn-country'] = get_query_var('cn-country') ? esc_html(urldecode(get_query_var('cn-country'))) : FALSE; // if ( get_query_var('cn-near-coord') ) $queryVars['cn-near-coord'] = get_query_var('cn-near-coord'); // if ( get_query_var('cn-radius') ) $queryVars['cn-radius'] = get_query_var('cn-radius'); // if ( get_query_var('cn-unit') ) $queryVars['cn-unit'] = get_query_var('cn-unit'); if ($queryVars['cn-cat']) { $categoryID = $queryVars['cn-cat']; $terms = array(); // Since the `cn-cat` query var can be an array, we'll only add the category slug // template name when querying a single category. if (is_array($categoryID)) { foreach ($categoryID as $id) { $term = cnTerm::getBy('id', $id, 'category'); $terms[] = esc_html($term->name); } } else { $term = cnTerm::getBy('id', $categoryID, 'category'); $terms[] = esc_html($term->name); } $out[] = sprintf(__('You are searching within category(ies): %s', 'connections'), implode(', ', $terms)); } if ($queryVars['cn-s']) { // If value is a string, string the white space and covert to an array. if (!is_array($queryVars['cn-s'])) { $queryVars['cn-s'] = explode(' ', trim($queryVars['cn-s'])); } // Trim any white space from around the terms in the array. array_walk($queryVars['cn-s'], 'trim'); $out[] = sprintf(__('You are searching for the keyword(s): %s', 'connections'), implode(', ', $queryVars['cn-s'])); } if ($queryVars['cn-char']) { $out[] = sprintf(__('The results are being filtered by the character: %s', 'connections'), $queryVars['cn-char']); } if ($queryVars['cn-organization']) { $out[] = sprintf(__('The results are being filtered by the organization: %s', 'connections'), $queryVars['cn-organization']); } if ($queryVars['cn-department']) { $out[] = sprintf(__('The results are being filtered by the department: %s', 'connections'), $queryVars['cn-department']); } if ($queryVars['cn-locality']) { $out[] = sprintf(__('The results are being filtered by the locality: %s', 'connections'), $queryVars['cn-locality']); } if ($queryVars['cn-region']) { $out[] = sprintf(__('The results are being filtered by the region: %s', 'connections'), $queryVars['cn-region']); } if ($queryVars['cn-postal-code']) { $out[] = sprintf(__('The results are being filtered by the postal code: %s', 'connections'), $queryVars['cn-postal-code']); } if ($queryVars['cn-country']) { $out[] = sprintf(__('The results are being filtered by the country: %s', 'connections'), $queryVars['cn-country']); } // Convert the search messages in a HTML UL list. if (!empty($out)) { $out = '<li class="cn-search-message">' . implode('</li><li class="cn-search-message">', $out) . '</li>'; $out = '<ul id="cn-search-message-list">' . $out . '</ul>'; $out .= sprintf('<div id="cn-clear-search"><a class="button btn" id="cn-clear-search-button" href="%1$s">%2$s</a></div>', esc_url($permalink), __('Clear Search', 'connections')); $out = '<div id="cn-search-messages">' . $out . '</div>'; } else { $out = ''; } return self::echoOrReturn($atts['return'], $out); }
/** * Get the default category ID. * * NOTE: This is also the callback for the `default_option_{name}` filter @see get_option(). * * NOTE: Uses the @see get_option() and @see update_option() functions instead of the @see cnSettingsAPI() * because it is used in places where the cnSettingsAPI() has not yet been fully initialized. * * @access public * @since 8.3.3 * @static * * @uses remove_filter() * @uses get_option() * @uses cnTerm::exists() * @uses cnTerm::getBy() * @uses cnTerm::insert() * @uses update_option() * @uses is_wp_error() * @uses add_filter() * * @return int */ public static function getDefaultCategoryID() { $id = 0; // Remove filter to prevent an infinite loop. remove_filter('default_option_cn_default_category', array(__CLASS__, 'getDefaultCategoryID')); // Use get_option() rather than cnSettingsAPI::get() because the class may not yet be initialized. $category = get_option('connections_category'); // Check to ensure the default category ID is saved in the options table before returning it. if (FALSE === $category || !isset($category['default']) || empty($category['default'])) { // If there was no default category set, check for the "Uncategorized" category. If it exists return its // `id` and if it does not, then create it an return the `id`. if (cnTerm::exists('uncategorized', 'category')) { $category = cnTerm::getBy('slug', 'uncategorized', 'category', ARRAY_A); // Ensure nothing went wrong when checking for the "Uncategorized" category. // If not, save the `id` in the options table. if (FALSE !== $category) { $id = $category['term_id']; // Use update_option() rather than cnSettingsAPI::set() because the class may not yet be initialized. update_option('connections_category', array('default' => $id)); } } else { $category = cnTerm::insert(__('Uncategorized', 'connections'), 'category'); // Ensure nothing went wrong when inserting the "Uncategorized" category. // If not, save the `id` in the options table. if (!is_wp_error($category)) { $id = $category['term_id']; // Use update_option() rather than cnSettingsAPI::set() because the class may not yet be initialized. update_option('connections_category', array('default' => $id)); } } } else { $id = $category['default']; } // Add the filter back. add_filter('default_option_cn_default_category', array(__CLASS__, 'getDefaultCategoryID')); /** * Allows the opportunity to change the default category. * * @since 8.3.3 * * @param int $id The default category ID. */ return apply_filters('cn_default_category', $id); }
/** * Get term data by 'name', 'id' or 'slug'. * * @deprecated 8.1.6 Use {@see cnTerm::getBy()} instead. * @see cnTerm::getBy() * * @param string $field * @param string | int -- Search term * @param string $taxonomy * * @return mixed | False or term object */ public function getTermBy($field, $value, $taxonomy) { return cnTerm::getBy($field, $value, $taxonomy); }
/** * Deletes the category from the database via the cnTerm class. * * @return bool The success or error message. */ public function delete() { // @todo Add option for user to set the default category, which should not be able to be deleted. //$defaults['default'] = get_option( 'cn_default_category' ); // Temporarily hard code the default category to the Uncategorized category // and ensure it can not be deleted. This should be removed when the default // category can be set by the user. $default_category = cnTerm::getBy('slug', 'uncategorized', 'category'); $defaults['default'] = $default_category->term_id; // Do not change the default category. // This should be able to be removed after the user configurable default category is implemented. if ($this->id == $default_category->term_id) { cnMessage::set('error', 'category_delete_uncategorized'); return FALSE; } $result = cnTerm::delete($this->id, 'category'); if (is_wp_error($result)) { cnMessage::set('error', $result->get_error_message()); return FALSE; } else { cnMessage::set('success', 'category_deleted'); return TRUE; } }
/** * Add the "Uncategorized" category" * * @access private * @since 0.7.5 * * @return void */ private static function addDefaultCategory() { $term = cnTerm::getBy('slug', 'uncategorized', 'category'); if (!$term) { $attributes['slug'] = ''; $attributes['parent'] = 0; $attributes['description'] = __('Entries not assigned to a category will automatically be assigned to this category and deleting a category which has been assigned to an entry will reassign that entry to this category. This category can not be edited or deleted.', 'connections'); cnTerm::insert(__('Uncategorized', 'connections'), 'category', $attributes); } }
/** * Add, update or delete the entry categories. * * @access public * @since 0.8 * @param string $action The action to being performed to an entry. * @param int $id The entry ID. * * @return void */ public static function processEntryCategory($action, $id) { // Grab an instance of the Connections object. $instance = Connections_Directory(); /* * Save the entry category(ies). If none were checked, send an empty array * which will add the entry to the default category. */ if (isset($_POST['entry_category']) && !empty($_POST['entry_category'])) { $instance->term->setTermRelationships($id, $_POST['entry_category'], 'category'); } else { // @todo Add option for user to set the default category, which should not be able to be deleted. //$defaults['default'] = get_option( 'cn_default_category' ); // Temporarily hard code the default category to the Uncategorized category // and ensure it can not be deleted. This should be removed when the default // category can be set by the user. $default_category = cnTerm::getBy('slug', 'uncategorized', 'category'); $instance->term->setTermRelationships($id, $default_category->term_id, 'category'); } }
/** * Will make slug unique, if it isn't already. * * The $slug has to be unique global to every taxonomy, meaning that one * taxonomy term can't have a matching slug with another taxonomy term. Each * slug has to be globally unique for every taxonomy. * * The way this works is that if the taxonomy that the term belongs to is * hierarchical and has a parent, it will append that parent to the $slug. * * If that still does not return an unique slug, then it try to append a number * until it finds a number that is truly unique. * * The only purpose for $term is for appending a parent, if one exists. * * NOTE: This is the Connections equivalent of @see wp_unique_term_slug() in WordPress core ../wp-includes/taxonomy.php * * @access private * @since 8.1.6 * @static * * @global wpdb $wpdb * * @uses cnTerm::exists() * @uses cnTerm::get() * @uses is_wp_error() * @uses wpdb::prepare() * @uses wpdb::get_var() * * @param string $slug The string that will be tried for a unique slug * @param object $term The term object that the $slug will belong too * * @return string Will return a true unique slug. */ private static function unique_slug($slug, $term) { global $wpdb; $needs_suffix = TRUE; $original_slug = $slug; if (!self::exists($slug) || !cnTerm::getBy('slug', $slug, $term->taxonomy)) { $needs_suffix = FALSE; } // If the taxonomy supports hierarchy and the term has a parent, make the slug unique // by incorporating parent slugs. $parent_suffix = ''; if ($needs_suffix && !empty($term->parent)) { $the_parent = $term->parent; while (!empty($the_parent)) { $parent_term = self::get($the_parent, $term->taxonomy); if (is_wp_error($parent_term) || empty($parent_term)) { break; } $parent_suffix .= '-' . $parent_term->slug; if (!self::exists($slug . $parent_suffix)) { break; } if (empty($parent_term->parent)) { break; } $the_parent = $parent_term->parent; } } // If we didn't get a unique slug, try appending a number to make it unique. /** * Filter whether the proposed unique term slug is bad. * * @since 8.5.10 * * @param bool $needs_suffix Whether the slug needs to be made unique with a suffix. * @param string $slug The slug. * @param object $term Term object. */ if (apply_filters('cn_unique_term_slug_is_bad_slug', $needs_suffix, $slug, $term)) { if ($parent_suffix) { $slug .= $parent_suffix; } else { if (!empty($term->term_id)) { $query = $wpdb->prepare("SELECT slug FROM " . CN_TERMS_TABLE . " WHERE slug = %s AND term_id != %d", $slug, $term->term_id); } else { $query = $wpdb->prepare("SELECT slug FROM " . CN_TERMS_TABLE . " WHERE slug = %s", $slug); } if ($wpdb->get_var($query)) { $num = 2; do { $alt_slug = $slug . "-{$num}"; $num++; $slug_check = $wpdb->get_var($wpdb->prepare("SELECT slug FROM " . CN_TERMS_TABLE . " WHERE slug = %s", $alt_slug)); } while ($slug_check); $slug = $alt_slug; } } } /** * Filter the unique term slug. * * @since 8.5.10 * * @param string $slug Unique term slug. * @param object $term Term object. * @param string $original_slug Slug originally passed to the function for testing. */ return apply_filters('cn_unique_term_slug', $slug, $term, $original_slug); }