0

I have a content type, books, with a field Category, based on a taxonomy. I have a View of books, and can filter by author, date, and also by field category. Everything works right, but when I try to add several subcategories (nested taxonomy), I have the problem that I cannot let the filter exactly as it is, as I can have two family names exactly equal, namely "offers". For example:

 http://www.example.com/books/science/offers
 http://www.example.com/books/sports/offers

As I am using arg(3) for retrieving "offers", I have the same name for two different taxonomies with different tid's.

How can I alter the SQL in ´MYMODULE_views_pre_view´ so I can filter by tid instead of name? I can programmaticaly get the tid from the URL and inject it directly into the SQL, but don't know how to alter this SQL accordingly.

1
  • Add contextual filter of Has taxonomy term ID >> select provide default value >> select Taxonomy ID from url.
    – No Sssweat
    Commented Sep 5, 2016 at 6:32

1 Answer 1

1

@no-sssweat' answer is what you want as long as views can figure out the right tid from the url. In cases where it can't but you know how to, you can do an argument replacement in a custom module. Here is some code I have that is doing that:

/**
 * Implements hook_views_pre_view().
 */
function MYMODULE_views_pre_view(&$view, &$display_id, &$args) {
    $views_to_process = array(
        'view_name1' => array(
            'display_name1',
            'display_name2',
            'display_name3',
        ),
        'view_name2' => array(
            'display_name1',
        )
    );
    if (!in_array($view->name, array_keys($views_to_process))) { return; }
    if (!in_array($view->current_display, $views_to_process[$view->name])) { return; }
    if (!empty($args[0]) && !_MYMODULE_isInteger($args[0])) {
        $tid = _MYMODULE_get_tid_for_top_level_term($args[0], 'area');
        if ($tid) {
            $args[0] = $tid;
        }
    }

}

/**
 * Helper function to determine whether a value is an integer or not.
 *
 * Sourced from http://php.net/manual/en/function.is-int.php#82857
 */
function _MYMODULE_isInteger($input){
    return(ctype_digit(strval($input)));
}

The `$views_to_process is a tree of views and displays that this should be applied to and the first two ifs just ignore this hook if the display isn't in $views_to_process. I then check to make sure there is an argument of some kind in place and that it isn't already an integer (helper function included for that), and then it loads a tid based on the current argument. It then replaces that argument with the tid. If you replaced _MYMODULE_get_tid_for_top_level_term with your helper function for loading up the tid, you can then use the tid as a contextual filter value. I hope that helps!

note: I currently have a question open on that very view, and while I don't think this solution has anything to do with the issue I'm having, there is a chance.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.