I'm working on changing the permalink of a Custom Post Type to include the taxonomy prior to the post id. I'm capable of it displaying the taxonomy in the URL however when I go to the page I get a 404 Error. It looks like the structure of the permalink is correct however the location of the post isn't synced up w/ the database location.
Any help is appreciated and thanks in advance!
Couple of notes:
My .htaccess file has mod rewrite on.
I've added %tax% to the permalink rewrite for the CPT
I have archive turned on for the CPT
Code
function change_permalink( $link, $post ) {
if ( ‘custom-post-type-name’ == get_post_type( $post ) ) {
// Get post
$post = get_post($post_id);
if (!$post) return $permalink;
// Get taxonomy terms
$terms = wp_get_object_terms($post->ID, ’taxonomy-name’);
if (!is_wp_error($terms) && !empty($terms) && is_object($terms[0])) $taxonomy_slug = $terms[0]->slug;
else $taxonomy_slug = 'no-taxonomy-listed’;
return str_replace('%tax%', $taxonomy_slug, $link);
}
return $link;
}
add_filter( 'post_type_link', ‘change_permalink’, 10, 2 );
Figured it out. Needed to wp_rewrite:
add_action( 'wp_loaded', 'urban_permastructure' );
function urban_permastructure($post) {
if ( 'custom-post-type-name' == get_post_type( $post ) ) {
global $wp_rewrite;
$structure = '/cat/%tax%';
$wp_rewrite->add_rewrite_tag("%tax%", '([^/]+)', "tax-type=");
$wp_rewrite->add_permastruct('tax-type', $structure, false);
}
}
Related
I'm a wordpress newbie. I will try to describe my problem in the clearest way possible.
I'm trying to do two things here:
Remove CPT from a permalink.
Add a custom taxonomy type where it used to be the CPT in the permalink.
Permalinks on site used to be like this:
http://example.com/custom-post-type/post-name
I managed to remove the CPT from the permalink based on this:
how to remove custom post type from wordpress url?
Then I modify my code to add the custom taxonomy type to the permalink to be like this:
http://example.com/post-category/post-name
This is my code:
function remove_cpt_slug( $post_link, $post ) {
if ( 'custom-post-type-name' === $post->post_type && 'publish' === $post->post_status ) {
$post_tags = get_the_terms($post->ID, 'custom-post-type-name-category');
$post_link = str_replace( '/' . $post->post_type . '/', '/' . $post_tags[0]->slug . '/', $post_link );
}
return $post_link;
}
add_filter( 'post_type_link', 'remove_cpt_slug', 10, 2 );
function add_cpt_post_names_to_main_query( $query ) {
// Return if this is not the main query.
if ( ! $query->is_main_query() ) {
return;
}
// Return if this query doesn't match our very specific rewrite rule.
if ( ! isset( $query->query['page'] ) || 2 !== count( $query->query ) ) {
return;
}
// Return if we're not querying based on the post name.
if ( empty( $query->query['name'] ) ) {
return;
}
// Add CPT to the list of post types WP will include when it queries based on the post name.
$query->set( 'post_type', array( 'post', 'page', 'custom-post-type-name' ) );
}
add_action( 'pre_get_posts', 'add_cpt_post_names_to_main_query' );
This worked but now every post from my CPT gives a 404. How can I solve this?
I built a custom template page named Single Listing. permalink for this page is / homes /
But I'd like to show this custom template page for all the urls formatted like this homes/*
I am new to wordpress so any help or suggestions would be welcome.
Thanks.
Not tested, but this might be helpful for you.
add_filter( 'template_include', 'portfolio_page_template', 99 );
function portfolio_page_template( $template ) {
global $wp;
$current_url_path = home_url( $wp->request );
$url_pattern = '/(^homes[\/\w]*)/gim'
if ( is_page() && preg_match($pattern, $current_url_path)) {
$new_template = locate_template( array( 'home-page-template.php' ) );
if ( '' != $new_template ) {
return $new_template ;
}
}
return $template;
}
Is it possible to use a post meta value instead of the title as permalink?
I tried different methods, but i did'nt work as i would like
As for now the structure is: www.website../property/post-title
i achived this up to now.. www.website../property/post-meta/post-title
what i would like is: www.website../property/post-meta
my code is:
function property_query_vars( $qv ) {
$qv[] = 'meta';
return $qv;
}
add_filter( 'query_vars', 'property_query_vars' );
add_filter( 'post_type_link', 'property_post_type_link2', 10, 3);
function property_post_type_link2($permalink, $post, $leavename) {
if ($post->post_type == 'property') {
$meta = get_post_meta($post->ID, '_boP_prop-id', true);
$postname = $post->post_name;
if (isset($meta) && !empty($meta))
$permalink = home_url( " property/" . $meta . "/");
}
return $permalink;
}
function mycustomname_rewrites_init2(){
add_rewrite_rule('property/([^/]*)/?$',
'index.php?post_type=property&meta=$matches[1]',
'top'
);
}
add_action('init', 'mycustomname_rewrites_init2');
this shows the permalink as i wanted but, only the archive page is shown, click on the permalink returns me to archive page.
I have a website with some custom post type created with Ultimate CMS plugin.
In admin area, when I make a new search, the result is ok, but after that, when I'm try to make a second search, It give me an error "Invalid post type".
I also realize that the url it's not ok:
In the first search, the url is something like this:
http://www.site.com/wp-admin/edit.php?s=SearchTerm1&post_status=all&post_type=post&action=-1&m=0&cat=0&paged=1&mode=list&action2=-1
In the second search, the url is something like:
http://www.site.com/wp-admin/edit.php?s=SearchTerm2&post_status=all&post_type=Array&_wpnonce=4d88f268e4&_wp_http_referer=%2Fwp-admin%2Fedit.php%3Fs%3DSearchTerm1%26post_status%3Dall%26post_type%3Dpost%26action%3D-1%26m%3D0%26cat%3D0%26paged%3D1%26mode%3Dlist%26action2%3D-1&action=-1&m=0&cat=0&paged=1&mode=list&action2=-1
And the error message: "Invalid post type".
I deactived all of my plugins, I upgraded wordpress to the latest version 3.5.1, I reset permalinks to default, but this error still remain.
Any help would be much appreciated!
Thank you
I also came across this issue and found that it was a result of one of my functions in my functions.php file that was modifying the global wordpress query parameters.
It sounds like you edited the global $query object. If you used a hook such as 'pre_get_posts' and manipulated the $query object and you do not exclude the admin area, then any changes you make to the query parameters will also apply to the admin panel and it will display that error when trying to add in parameters that don't fit your search.
For example:
Let's say you have a search feature on your site, and when the user enters a search and goes to the search results page, you only want to display posts of a custom post type called $searchable_posts, then you would add a hook to your functions.php file like this:
function searchfilter($query) {
if ($query->is_search && $query->is_main_query() ) {
$query->set('post_type', $searchable_posts);
}
return $query;
}
add_filter('pre_get_posts', 'searchfilter');
This will make it so that any global default $query will only search for results that have a matching post type of $searchable_posts. However, the way it is written above means this will also apply to any global $query in the admin panel also.
The way around this is to structure your query like this:
function searchfilter($query) {
if ($query->is_search && $query->is_main_query() && !is_admin() ) {
$query->set('post_type', $searchable_posts);
}
return $query;
}
add_filter('pre_get_posts', 'searchfilter');
Adding in that !is_admin() means that your function will exclude anything in the backend administration panel (see is_admin ).
Alternatively, a safer way if you can, instead of using the global default $query is to create your own new WP_Query and searching using that instead - the codex has good examples of how to set that up.
I am also get the issue same as you and finally I got the solution.
We have to add $query->is_main_query() in IF CONDITION.
Below is the full code.
function acf_meta_value_filter() {
global $typenow;
global $wp_query;
if ( $typenow == 'your_custom_post_type_name' ) { // Your custom post type meta_key_name
$plugins = array( 'value1', 'value2', 'value3' ); // Options for the filter select field
$current_plugin = '';
if( isset( $_GET['meta_key_name'] ) ) {
$current_plugin = $_GET['meta_key_name']; // Check if option has been selected
} ?>
<select name="meta_key_name" id="meta_key_name">
<option value="all" <?php selected( 'all', $current_plugin ); ?>><?php _e( 'All', '' ); ?></option>
<?php foreach( $plugins as $key=>$value ) { ?>
<option value="<?php echo esc_attr( $value ); ?>" <?php selected( $value, $current_plugin ); ?>><?php echo esc_attr( $value ); ?></option>
<?php } ?>
</select>
<?php }
}
add_action( 'restrict_manage_posts', 'acf_meta_value_filter' );
function acf_meta_value_filter_by_slug( $query ) {
global $pagenow;
// Get the post type
$post_type = isset( $_GET['post_type'] ) ? $_GET['post_type'] : '';
if ( is_admin() && $pagenow=='edit.php' && $post_type == 'your_custom_post_type_name' && isset( $_GET['meta_key_name'] ) && $_GET['meta_key_name'] !='all' && $query->is_main_query()) {
$query->query_vars['meta_key'] = 'meta_key_name';
$query->query_vars['meta_value'] = $_GET['meta_key_name'];
$query->query_vars['meta_compare'] = '=';
}
}
add_filter( 'parse_query', 'acf_meta_value_filter_by_slug' );
I had a similar problem with a site a took over from other dev.
function anty_search_form( $query ) {
if ( $query->is_search ) {
$query->set( 'post_type', array('post', 'product') );
}
return $query;
}
add_filter( 'pre_get_posts', 'anty_search_form' );
Someone forgot to exclude this function from wp-admin page. So changing to this helped Invalid post type.
function anty_search_form( $query ) {
if (!is_admin()){
if ( $query->is_search ) {
$query->set( 'post_type', array('post', 'product') );
}
return $query;
}
}
add_filter( 'pre_get_posts', 'anty_search_form' );
At wp-admin when submitted the second search for a custom post type, I was getting the same error, "Invalid post type." The URL seemed long and incorrect. Anyway, the following code worked perfectly:
add_filter( 'pre_get_posts', 'tgm_io_cpt_search' );
function tgm_io_cpt_search( $query ) {
if ( $query->is_search ) {
$query->set( 'post_type', 'your_custom_post_type' );
}
return $query;
}
I want to use something like:
http://example.com/%category_id%/%postname%/
for the permalink structure.
For example, if a post has a category with an ID of 3, then the URL for the post will be
http://example.com/3/post-name/
Does anyone know how this can be done? I don't mind modifying WordPress core.
This code adds the %category_id% rewrite tag, and filters post permalinks to replace them with the actual category ID (lowest if there are multiple categories). You can place this in a plugin or in your theme file.
add_action( 'init', 'so6159452_init' );
function so6159452_init()
{
add_rewrite_tag( '%category_id%', '([0-9]+)' );
}
add_filter( 'post_link', 'so6159452_post_link', 10, 2 );
function so6159452_post_link( $permalink, $post )
{
if ( false !== strpos( $permalink, '%category_id%' ) ) {
$cats = get_the_category( $post->ID );
if ( $cats ) {
usort( $cats, '_usort_terms_by_ID' ); // order by ID
$category_id = $cats[0]->cat_ID;
} else {
// Error: no category assigned to this post
// Just use a dummy variable
$category_id = '0';
}
$permalink = str_replace( '%category_id%', $category_id, $permalink );
}
return $permalink;
}