Search custom post type by year - php

I've created a more advanced search for the standard Wordpress search. To go along with the keyword text input I've added two drop downs that are searching my custom taxonomies.
This is working great.
The only dropdown I've yet to create the functionality for is the year dropdown. I'd like to be able to filter the results to show posts within that specific year.
How can I search through all the posts and only output the custom posts that were published for that year?
It's important that the posts are searched for by their publish date (ie. no custom fields!).
<form action="<?php echo home_url( '/' ); ?>" method="get" id="advanced-search">
<div id="search-nudge">
<h1 id="search-title">Search Policy's</h1>
<p id="search-strap">Search by some or all of the following criteria</p>
<div class="clear"></div>
<div id="search-left">
<p class="search-label">Keyword</p>
<input type="text" name="s" id="s" class="keyword" value="<?php the_search_query(); ?>" />
<input type="hidden" value="policies" name="post_type" id="post_type" /><br /><br />
</div>
<div id="search-right">
<p class="search-label">Year of publication</p>
<select class="work-list search-dropdown" name="year">
<option value="">All</option>
</select>
<div class="clear"></div>
</div>
<div class="clear"></div>
<div class="search-element">
<?php // List all event subjects
$subjectList = get_terms('topics', array( 'taxonomy' => 'topics' ));
if(!empty($subjectList)) { ?>
<p class="search-label">Category</p>
<select class="work-list search-dropdown" name="subject">
<option value="">All</option>
<?php foreach($subjectList as $subject){
if(isset($_GET['subject'])) {
$selected = ($subject->slug == $_GET['subject']) ? ' selected="selected"' : '';
}
echo '<option value="' . $subject->slug . '"'. $selected.'> ' . $subject->name . '</option>';
}
echo '</select><br /><br />';
} ?>
</div>
<div class="search-element">
<?php // list all event types
$document = get_terms('document_type', array( 'taxonomy' => 'document_type' ));
if(!empty($subjectList)) { ?>
<p class="search-label">Document Type</p>
<select class="work-list search-dropdown search-dropdown-right" name="type">
<option value="">All</option>
<?php foreach($document as $type){
if(isset($_GET['type'])) {
$selected = ($type->slug == $_GET['type']) ? ' selected="selected"' : '';
}
echo '<option value="' . $type->slug . '"'. $selected.'> ' . $type->name . '</option>';
}
echo '</select><br /><br />';
} ?>
</div>
<input type="radio" name="sort" class="search-input" value="date" checked> <p class="search-label radio radio-nudge">Order by date</p>
<input type="radio" name="sort" class="search-input" value="title"> <p class="search-label radio">Order by title</p>
<input type="submit" id="searchsubmit2" class="search-submit" value="Search" />
<div class="clear"></div>
</div>
</form>
<?php if(isset($_GET['sort']) && $_GET['sort'] === "date") {
$sort = $_GET['sort'];
$order = "DESC";
} else {
$sort = $_GET['sort'];
$order = "ASC";
}
// default args to search by custom post type and search term
$args = array(
'post_type' => 'policies',
'posts_per_page' => 10,
'orderby' => $sort,
'order' => $order,
's' => $s
);
// add the subject to args if there is one
if(isset($_GET['subject']) && $_GET['subject'] != "") {
$args['tax_query'][1] = array(
'taxonomy' => 'topics',
'field' => 'slug',
'terms' => array($_GET['subject'])
);
}
// add the subject to args if there is one
if(isset($_GET['type']) && $_GET['type'] != "") {
$args['tax_query'][1] = array(
'taxonomy' => 'document_type',
'field' => 'slug',
'terms' => array($_GET['type'])
);
}
// Run the query
$the_query = new WP_Query( $args );
// The Loop
if ( $the_query->have_posts() ) {
while ( $the_query->have_posts() ) {
$the_query->the_post();
the_title();
the_content();
}
} else {
echo "No results";
}
/* Restore original Post Data */
wp_reset_postdata(); ?>
Update:
I've tried the following but no luck displaying any posts.
if(isset($_GET['year']) && $_GET['year'] != "") {
$args = array(
'date_query' => array(
array(
'year' => array($_GET['year'])
),
),
);
}

Solved with:
if(isset($_GET['year']) && $_GET['year'] != "") {
$args = array(
'post_type' => 'policies',
'posts_per_page' => 10,
'orderby' => $sort,
'order' => $order,
's' => $s,
'date_query' => array(
array(
'year' => ($_GET['year'])
),
),
);
} else {
// default args to search by custom post type and search term
$args = array(
'post_type' => 'policies',
'posts_per_page' => 10,
'orderby' => $sort,
'order' => $order,
's' => $s
);
}

Related

Wordpress Query Posts with Multiple Filters

I'm using AJAX to filter posts by category, which is working fine. But when I try to add another filter to filter by a custom field called album date my original category filter doesn't work. Each filter on there own works but they don't work together. Here is the stripped down code.
I'm still learning how this all works together so any help would be greatly appreciated!
PHP CODE
function my_filter_function(){
// post date
$args = array(
'orderby' => 'date',
'order' => $_POST['date']
);
// for taxonomies / categories
if(isset($_POST['categoryfilter']))
$args['tax_query'] = array(
array(
'taxonomy' => 'category',
'field' => 'id',
'terms' => $_POST['categoryfilter']
)
);
// album year
if(isset($_POST['yearfilter']))
$args = array(
'meta_key' => 'album_year',
'meta_value' => $_POST['yearfilter'],
);
$query = new WP_Query( $args );
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
echo '<h1>' . $query->post->post_title . '</h1>';
...
endwhile;
wp_reset_postdata();
else :
echo 'No posts found';
endif;
die();
}
add_action('wp_ajax_myfilter', 'my_filter_function'); // wp_ajax_{ACTION HERE}
add_action('wp_ajax_nopriv_myfilter', 'my_filter_function');
FORM CODE
<form action="<?php echo site_url() ?>/wp-admin/admin-ajax.php" method="POST" id="filter">
<?php
// Category Filter
if($terms = get_terms(array('taxonomy' => 'category', 'orderby' => 'name'))) :
echo '<select name="categoryfilter"><option value="">Select category...</option>';
foreach ( $terms as $term ) :
echo '<option value="' . $term->term_id . '">' . $term->name . '</option>'; // ID of the category as the value of an option
endforeach;
echo '</select>';
endif;
?>
<?php
// Year Filter
$posts = get_posts(array(
'posts_per_page' => -1,
'post_type' => 'post',
'meta_key' => 'album_year',
'orderby' => 'meta_value',
'order' => 'DESC'
));
if( $posts ):
echo '<select name="yearfilter"><option value="">Select Year...</option>';
foreach($posts as $post):
$album_year = get_field('album_year');
echo '<option value="' . $album_year . '">' . $album_year . '</option>';
endforeach;
echo '</select>';
wp_reset_postdata();
endif;
?>
<label>
<input type="radio" name="date" value="ASC" /> Date: Ascending
</label>
<label>
<input type="radio" name="date" value="DESC" checked="checked" /> Date: Descending
</label>
<button>Apply filter</button>
<input type="hidden" name="action" value="myfilter">
</form>
I haven't tested this code but it looks like you are overriding your args variable for yearfilter.
This
// album year
if(isset($_POST['yearfilter'])) {
$args = array(
'meta_key' => 'album_year',
'meta_value' => $_POST['yearfilter'],
);
}
should be this
// album year
if(isset($_POST['yearfilter'])) {
$args['meta_key'] = 'album_year';
$args['meta_value'] = $_POST['yearfilter'];
}
If they are working individually this should fix things.

Post filtering in wordpress returns all posts

I have this function to filter posts by fields and taxonomies. The problem is that when I use the taxonomy filter it doesn't work and it returns all the posts without filtering.
I didn't include js files because ajax is working well.
Here's the PHP in functions.php:
function post_filter()
{
$number = $_POST['number'];
$autor = $_POST['autor'];
$args = array(
'post_type' => 'publicaciones',
'orderby' => 'date',
'order' => 'ASC',
'meta_key' => 'numero',
'meta_value'=> $number
);
if( isset( $autor ) )
$args['tax_query'] = array(
array('taxonomy' => 'autors',
'field' => 'id',
'terms' => $autor)
);
$query = new WP_Query( $args );
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
//Post content
endwhile;
wp_reset_postdata();
else :
echo 'No results.';
endif;
wp_die();
}
And this is the form:
<form action="<?php echo site_url() ?>/wp-admin/admin-ajax.php" method="POST" class="my-5" id="buscador_numero">
<div class="row">
<div class="col-3">
<?php
if( $terms = get_terms( array( 'taxonomy' => 'autors', 'orderby' => 'name' ) ) ) :
echo '<select name="autor"><option value="">Autor/a</option>';
foreach ( $terms as $term ) :
echo '<option value="' . $term->term_id . '">' . $term->name . '</option>';
endforeach;
echo '</select>';
endif;
?>
</div>
<div class="col-2">
<input type="number" class="w-100 p-2" name="number" placeholder="Número">
</div>
<div class="col-2">
<button id="btn_buscar"><span class="dashicons dashicons-search"></span></button>
</div>
</div>
<input type="hidden" name="action" value="post_filter">
</form>
Thanks in advance :)

'key' meta_query not working custom advanced search (WordPress)

Been trying for hours now and have almost got to breaking point. Tried so many different things but can't seem to get my custom search bar to query results by a pre-defined select price range. I am using Advanced Custom Fields to add the meta tag 'investmentprice' to my custom post type called 'investments'. I feel like it's to do with WordPress not picking up the correct 'key' in my meta_query, even though I have changed this numerous times now.
Here's the code for the config bar:
<div class="config_bar cf">
<form method="get" role="search" action="<?php echo esc_url( home_url( '/' ) ); ?>">
<input type="hidden" name="s" value="">
<input type="hidden" name="post_type" value="investments" />
<div class="col">
<?php
$taxonomy = 'type';
$args = array( 'orderby' => 'name',
'order' => 'ASC',
'hide_empty' => true,
);
$tax_terms = get_terms($taxonomy, $args);
?>
<span class="label_inner">Investment Type</span>
<select name="type" id="type" class="postform standard">
<option value="" selected="selected">All Investment Types </option>
<?php if($tax_terms): ?>
<?php foreach ($tax_terms as $tax_term): ?>
<?php $title = $tax_term->name;
?>
<option value="<?php echo $tax_term->slug; ?>"><?php echo $title; ?></option>
<?php endforeach; ?>
<?php endif; ?>
</select>
</div><!-- col -->
<div class="col">
<span class="label_inner"><?php _e('Select Country','opencloud');?></span>
<select class="postform standard country " name="country" id="country">
<option value=""><?php _e('All Countries','opencloud');?></option>
<?php
// Display only parents here .
$terms = get_terms( array(
// Put your taxonomy name here.
'taxonomy' => 'location',
'parent' => 0,
'hide_empty' => false
) );
foreach ($terms as $term){?>
<!-- We are going to send value for $_POST and data-makeId's TERM_ID for ajax request -->
<option value="<?php echo $term->slug;?>" data-countryId="<?php echo $term->term_id ?>"><?php echo $term->name;?></option>
<?php
wp_reset_query(); // if you're not in your main loop! otherwise you can skip this
} ?>
</select>
</div><!-- col -->
<script type="text/javascript">
$( document ).ready(function() {
$('#country').change(function(){
var $mainCat= $(this).find(':selected').attr('data-countryId');
if ($mainCat != '0' ){
// call ajax
$("#city").empty();
$.ajax
(
{
url:"<?php bloginfo('wpurl'); ?>/wp-admin/admin-ajax.php",
type:'POST',
data:'action=get_city_lists_ajax&main_catid=' + $mainCat,
beforeSend:function()
{
},
success:function(results)
{
$("#loading_bar").hide();
$("#city").removeAttr("disabled").trigger('change.select2');
$("#city").append(results).trigger('change.select2');
}
}
);
}
});
});
</script>
<div class="col">
<span class="label_inner"><?php _e('Select City','opencloud');?></span>
<select class="postform standard city " name="city" id="city" disabled>
<option value="<?php echo $term->slug;?>"><?php _e('All Cities','opencloud');?></option>
</select>
</div><!-- col -->
<div class="col">
<span class="label_inner">Select Price</span>
<select class="postform standard price" name="price" id="price">
<option value="">All Prices</option>
<option value="500-1000">£500-£1000</option>
<option value="1000-1500">£1000-£1500</option>
<option value="1500-2000">£1500-£2000</option>
<option value="2000-5000">£1500-£2000</option>
<option value="5000-10000">£5000-£10,000</option>
</select>
</div><!-- col -->
<div class="col">
<button class="search_submit" type="submit">Search</button>
</div><!-- col -->
</form>
And here's my advanced search query function:
function advanced_search_query( $query ) {
if ( isset( $_REQUEST['search'] ) && $_REQUEST['search'] == 'advanced' && !is_admin() && $query->is_search && $query->is_main_query() ) {
// limit query for custom post type
$query->set( 'post_type', 'investments' );
// Get query strings from URL and store the min a variable
$_type = $_GET['type'] != '' ? $_GET['type'] : '';
$_country = $_GET['country'] != '' ? $_GET['country'] : '';
$_city = $_GET['city'] != '' ? $_GET['city'] : '';
$_price = $_GET['price'] != '' ? $_GET['price'] : '';
if( $_price != '' ) {
$metaquery = array(
array(
'key' => 'investmentprice',
'terms' => $_price,
'compare' => 'BETWEEN'
)
);
$query->set( 'meta_query', $metaquery );
}
// if type is not empty limit the taxonomy to the specified
if( $_type != '' ) {
$taxquery = array(
array(
'taxonomy' => 'type',
'field' => 'slug',
'terms' => $_type,
'operator'=> 'IN'
)
);
$query->set( 'tax_query', $taxquery );
}
// if country is not empty limit the taxonomy to the specified
if( $_country != '' ) {
$taxquery = array(
array(
'taxonomy' => 'country',
'field' => 'slug',
'terms' => $_country,
'operator'=> 'IN'
)
);
$query->set( 'tax_query', $taxquery );
}
// if city is not empty limit the taxonomy to the specified
if( $_city != '' ) {
$taxquery = array(
array(
'taxonomy' => 'city',
'field' => 'slug',
'terms' => $_city,
'operator'=> 'IN'
)
);
$query->set( 'tax_query', $taxquery );
}
return; // always return
}
}
Also, here's a screenshot of the Advanced Custom Field:
Unless there are any other issues, this should be a small fix. You are using the array key 'terms' instead of 'value' in your meta query. According to the WordPress Codex, a nested array of args for a meta query should use value, like this:
$metaquery = array(
array(
'key' => 'investmentprice',
'value' => $_price,
'compare' => 'BETWEEN'
)
);
$query->set( 'meta_query', $metaquery );
Hope that helps..

How do I POST values to a taxonomy archive using pre_get_posts()

I have a form (a search form) on a single page. The code is below.
I wish to post the values of the form fields over to a pre_get_posts() function and then use the "properties" post type archive template (archive_properties.php) to then show the results.
I have posted my pre_get_post function below the form and I was hoping that would be sufficient.
Im getting the following error:
Warning: Invalid argument supplied for foreach() in /var/www/address/wp-admin/includes/plugin.php on line 1432
Ive got
function knoppys_search_form() { ?>
<form action="" id="propertySearch" name="propertySearch" action="<?php echo esc_url( admin_url('admin-post.php') ); ?>" method="post" enctype="multipart/form-data" >
<div class="form-unit">
<select name="type">
<option value="">All</option>
<option value="Apartment">Apartments</option>
<option value="Villa">Villa</option>
</select>
</div>
<div class="form-unit">
<select name="location">
<?php $termsArgs = array( 'taxonomy' => 'locations' );
$terms = get_terms($termsArgs);
?>
<option value="">Location</option>
<?php foreach ($terms as $term) { ?>
<option value="<?php echo $term->term_id; ?>"><?php echo $term->name; ?></option>
<?php } ?>
</select>
</div>
<div class="form-unit">
<input type="number" min="0" name="bedfrom" placeholder="Bed From">
</div>
<div class="form-unit">
<input type="number" min="0" name="bedto" placeholder="Bed To">
</div>
<input type="hidden" name="action" value="">
<button class="btn btn-primary" type="submit"><i class="fa fa-search"></i> Submit</button>
function knoppys_pre_get_filter() {
if (!is_admin() && is_archive('properties')) {
$location = $_POST['location'];
$type = $_POST['type'];
$bedfrom = $_POST['bedfrom'];
$bedto = $_POST['bedto'];
//Get the correct location
$tax_query = array(
'taxonomy' => 'locations',
'field' => 'id',
'terms' => $location
);
$query->set( 'tax_query', $tax_query );
//Get the correct type
$meta_query = array(
'relation' => 'AND',
array(
'meta_key' => 'type_name',
'value' => $type
),
array(
'meta_key' => 'number_of_beds',
'value' => array($bedfrom, $bedto),
'type' => 'numeric',
'compare' => 'BETWEEN',
)
);
$query->set( 'meta_query', $meta_query);
}
}
add_action('pre_get_posts', 'knoppys_pre_get_filter');

Wordpress meta_query taxonomy don't work

On my blogI tried sucessfully to make a research for articles titles and content, but after I tried to make a research for custom taxonomy of articles 'categories' with meta_query() and REGEXP, didn't work.
My form :
<div class="zone_filters">
<form action="" method="GET">
<input type="hidden" name="page_id" value="249" />
<input type="text" name="search_input" />
<select name="type">
<option value="title">titre et texte</option>
<option value="category">catégorie</option>
</select>
<select name="orderby">
<option value="DESC">plus récent</option>
<option value="ASC">plus ancien</option>
</select>
<button type="submit">OK</button>
</form>
</div>
My arguments :
<?php
$orderby = 'DESC';
if($_GET['orderby']) {
$orderby = $_GET['orderby'];
}
$args = array(
'post_type' => 'article',
'posts_per_page' => 3,
'paged' => get_query_var('paged') ? get_query_var('paged') : 1,
'orderby' => array('date' => $orderby)
);
if($_GET['type'] == 'title') {
$args['s'] = $_GET['search_input'];
}
elseif($_GET['type'] == 'category') {
$value = '^[a-zA-Z|\s]*(' . strtoupper( $_GET['search_input']) . '|' . strtolower( $_GET['search_input']) . ')[a-zA-Z|\s]*$';
$args['meta_query'] = array(array('key' => 'categories', 'value' => $value, 'compare' => 'REGEXP'));
}
$query = new WP_Query($args);?>
I learned it from the Codex
and I can't found the differences between my code and the doc.
Use tax query for category.
$args['tax_query'] = array(array('taxonomy' => 'categories', 'field' => 'slug', 'terms' => $value));
as per your html
<div class="zone_filters">
<form action="" method="GET">
<input type="hidden" name="page_id" value="249" />
<input type="text" name="search_input" />
<select name="type">
<option value="">titre et texte</option>
<option value="category-1">Category 1</option>
<option value="category-2">Category 2</option>
<option value="category-3">Category 3</option>
</select>
<select name="orderby">
<option value="DESC">plus récent</option>
<option value="ASC">plus ancien</option>
</select>
<button type="submit">OK</button>
</form>
</div>
<?php
$orderby = 'DESC';
if($_GET['orderby']) {
$orderby = $_GET['orderby'];
}
$args = array(
'post_type' => 'article',
'posts_per_page' => 3,
'paged' => get_query_var('paged') ? get_query_var('paged') : 1,
'orderby' => array('date' => $orderby)
);
if($_GET['type'] == 'title') {
$args['s'] = $_GET['search_input'];
}
elseif($_GET['type'] == 'category') {
$value = '^[a-zA-Z|\s]*(' . strtoupper( $_GET['search_input']) . '|' . strtolower( $_GET['search_input']) . ')[a-zA-Z|\s]*$';
$args['tax_query'] = array(array('taxonomy' => 'categories', 'field' => 'slug', 'terms' => $value));
}
$query = new WP_Query($args);?>
It's working this way :
Form :
<div class="zone_filters">
<form action="" method="GET">
<input type="hidden" name="page_id" value="249" />
<input type="text" name="search_input" />
<select name="categories">
<?php $allterms = get_terms('categories');
foreach($allterms as $term) : ?>
<option value="<?php echo $term->slug; ?>"><?php echo $term->name; ?></option>
<?php endforeach ?>
</select>
<select name="orderby">
<option value="DESC">plus récent</option>
<option value="ASC">plus ancien</option>
</select>
<button type="submit">OK</button>
</form>
</div>
The arguments :
<?php
$orderby = 'DESC';
if($_GET['orderby']) {
$orderby = $_GET['orderby'];
}
$args = array(
'post_type' => 'article',
'posts_per_page' => 3,
'paged' => get_query_var('paged') ? get_query_var('paged') : 1,
'orderby' => array('date' => $orderby)
);
if($_GET['search_input'] != '') {
$args['s'] = $_GET['search_input'];
}
elseif($_GET['categories']) {
$args['categories'] = $_GET['categories'];
}
$query = new WP_Query($args);?>

Categories