- shares
- Facebook Messenger
- Gmail
- Viber
- Skype
Sau khi cấu hình đường dẫn trong wordpress bằng cách vào menu settings->permalinks có 6 lựa chọn:
– Default: không sử dụng rewrite, để nhìn được bản chất wordpress url mà rewrite convert thành:
eg: post url có dạng http://localhost/test-wordpress/?p=123
– Day and name: base-url/ngày,tháng,năm/post-name
– Month and name: base-url/năm,tháng/sample-post
– Post name: base-url/post-name
– Custom structure: sử dụng rewrite tag, chúng ta có 1 số rewrite tag:
%category%: category name
%postname%: post name
%tag%: post tag
%author%: user
%pagename%
%postname%
%post_id%
%year%
%day%
%hour%
%minute%
%second%
%monthnum%
%posttype%
…
đây là rewrite tag mặc định của wordpress được sinh ra từ post,tag..
Nếu bạn dùng custom post type và muốn sử dụng rewrite tag cho custom post thì cài plugin “Custom Post Type Permalinks”
Sau khi cài sẽ có thêm phần custom post type permalink ở cuối menu settings->permalinks và sử dụng rewrite tag trong đường dẫn custom post.
Sau đó chúng thể dùng được rewrite tag cho custom post. ví dụ chằng hạn bạn có tạo custom post: “tutorial” thì taxonomy tag là %tutorial_taxonomy%
Để xem rewrite tag của custom post permalinks sử dụng filter hook post_type_link
.
add_filter('post_type_link', 'filter_post_type_link', 10, 3); function filter_post_type_link($link, $post,$leavename) { print_r($link); return $link; }
Chú ý: post_type link filter cần phải trả về giá trị không sẽ bị lỗi.
custom post taxonomy chứa giá trị của query category_name, nó có thể là 1 term taxonomy slug hoặc nhiều hơn một nếu post thiết lập nhiều categories.
category_name=slug1/slug2/sulg3
Nếu category bao gồm category mẹ (parent) và category con (sub category) trong custom post URL bạn có thể làm gọn đi chỉ sử dụng 1 category slug. Copy đoạn code sau vào functions.php và tuỳ chỉnh thêm theo ý bạn.
function filter_post_type_link($link, $post,$leavename) { if ($post->post_type != 'tutorial_posttype' || 'publish' != $post->post_status) return $link; if (($cats = (array)wp_get_post_terms($post->ID, tutorial_tax))) { $cat=reset($cats); while($cat && $cat->parent){ $cat=get_term_by('id',$cat->parent,$cat->taxonomy); break; } //if(!$cat) return $link; $link = str_replace('%tutorial_taxonomy%',$cat->slug, $link); // see custom function defined below $pt=get_post_type_object($post->post_type); $link = str_replace( '/' . $pt->rewrite['slug'] . '/', '/', $link ); } return $link; } add_filter('post_link', 'filter_post_type_link', 10, 3); add_filter('post_type_link', 'filter_post_type_link', 10, 3);
filter “post_type_link” sẽ thay đổi lại post url. Một vài trường hợp gây ra lỗi 404 not found là do mất một số tham số query post_type,page…hãy sử dụng thêm action “pre_get_posts” để xác định dữ liệu. Ví dụ code sau đây xác định lại post_type trước khi lấy posts data tránh xẩy ra lỗi 404.
add_action( 'pre_get_posts', 'my_post_queries' ); function my_post_queries( $query ) { global $wp_query; // Only noop the main query if ( ! $query->is_main_query() ) return; // do not alter the query on wp-admin pages and only alter it if it's the main query if ($query->is_main_query()){ $query->set( 'numberposts', -1 ); if((is_single() || is_home() || is_search() ) && !$query->get('post_type')){ $posttype=get_post_types(); if(!is_search()) unset($posttype['page']); unset($posttype['nav_menu_item']); $query->set('post_type',$posttype); } // alter the query for the home and category pages if(is_home() || is_search()){ $query->set('posts_per_page', get_option('posts_per_page')); } } return $query; }
THam khảo ví dụ khác về filter post_type_link.
// Add filter to plugin init function add_filter('post_type_link', 'gallery_permalink', 10, 3); // Adapted from get_permalink function in wp-includes/link-template.php function gallery_permalink($permalink, $post_id, $leavename) { $post = get_post($post_id); $rewritecode = array( '%year%', '%monthnum%', '%day%', '%hour%', '%minute%', '%second%', $leavename? '' : '%postname%', '%post_id%', '%category%', '%author%', $leavename? '' : '%pagename%',); if ( '' != $permalink && !in_array($post->post_status, array('draft', 'pending', 'auto-draft')) ) { $unixtime = strtotime($post->post_date); $category = ''; if ( strpos($permalink, '%category%') !== false ) { $cats = get_the_category($post->ID); if ( $cats ) { usort($cats, '_usort_terms_by_ID'); // order by ID $category = $cats[0]->slug; if ( $parent = $cats[0]->parent ) $category = get_category_parents($parent, false, '/', true) . $category; } // show default category in permalinks, without // having to assign it explicitly if ( empty($category) ) { $default_category = get_category( get_option( 'default_category' ) ); $category = is_wp_error( $default_category ) ? '' : $default_category->slug; } } $author = ''; if ( strpos($permalink, '%author%') !== false ) { $authordata = get_userdata($post->post_author); $author = $authordata->user_nicename; } $date = explode(" ",date('Y m d H i s', $unixtime)); $rewritereplace = array( $date[0], $date[1], $date[2], $date[3], $date[4], $date[5], $post->post_name, $post->ID, $category, $author, $post->post_name, ); $permalink = str_replace($rewritecode, $rewritereplace, $permalink); } else { // if they're not using the fancy permalink option } return $permalink; }
page rewrite
add_filter( 'page_rewrite_rules', 'wpse7243_page_rewrite_rules' ); function wpse7243_page_rewrite_rules( $rewrite_rules ) { // The most generic page rewrite rule is at end of the array // We place our rule one before that end( $rewrite_rules ); $last_pattern = key( $rewrite_rules ); $last_replacement = array_pop( $rewrite_rules ); $rewrite_rules += array( '(.+?)/([0-9]+)/([^/]+)/([^/]+)/?$' => 'index.php?pagename=$matches[1]&id=$matches[2]&fname=$matches[3]&lname=$matches[4]', $last_pattern => $last_replacement, ); return $rewrite_rules; }
Add new rewrite rules
Mỗi khi bạn có 1 cấu trúc url mới, ví dụ: thì cần thêm rewrite rule.
add_filter('rewrite_rules_array','wp_insertMyRewriteRules'); // Adding a new rule function wp_insertMyRewriteRules($rules) { $newrules = array(); $newrules['(profile)/(.*)$'] = 'index.php?pagename=profile&profile=$matches[2]'; return $newrules + $rules; }
Nhớ sau khi thêm cấu trúc mới thì update rewrite bằng cách gọi $wp_rewrite->flush_rules(); và thiết lập lại ở trong mục settings->permalinks là được, nếu chưa được thì load page và đợi vài giây.
Để lấy tham số trong url, bạn không dùng được $_GET vì phải nhìn thấy tham số trên địa chỉ, trong wordpress có hàm get_query_var() sẽ giúp bạn nhưng trước tiên phải đăng ký url query var.
add_filter('query_vars','wp_insertMyRewriteQueryVars'); // Adding the id var so that WP recognizes it function wp_insertMyRewriteQueryVars($vars) { array_push($vars, 'profile'); return $vars; }
Đoạn code trên tôi đăng ký tham số ‘profile’ ở url: ‘/profile/huyhoang08’ theo rewrite url ở trên thì ‘huyhoang08’ là giá trị của tham số profile, bạn sẽ lấy tham số này như sau:
echo get_query_var('profile');
Cuối cùng update lại rewrite:
add_filter('init','flushRules'); // Remember to flush_rules() when adding rules->nhớ là pải chạy cái này (hay pải flush) thì rewrite mới có tác dụng. function flushRules(){ global $wp_rewrite; $wp_rewrite->flush_rules(); }
Mình lấy ví dụ là, bạn muốn tạo các url có cấu trúc sau:
www.example.com/events/?location=nsw,qld&industry=web+mobile
rewrite: www.example.com/events/location/nsw,qld/industry/web+mobile/
Tạo rewrite rules nhanh sử dụng action “generate_rewrite_rules”.
add_action( 'generate_rewrite_rules', 'eg_add_rewrite_rules' ); function eg_add_rewrite_rules() { global $wp_rewrite; $new_rules = array( 'event/(industry|location)/(.+?)/(industry|location)/(.+?)/?$' => 'index.php?post_type=eg_event&' . $wp_rewrite->preg_index(1) . '=' . $wp_rewrite->preg_index(2) . '&' . $wp_rewrite->preg_index(3) . '=' . $wp_rewrite->preg_index(4), 'event/(industry|location)/(.+)/?$' => 'index.php?post_type=eg_event&' . $wp_rewrite->preg_index(1) . '=' . $wp_rewrite->preg_index(2) ); $wp_rewrite->rules = $new_rules + $wp_rewrite->rules; }
Hàm Tạo permlinks.
function eg_get_filter_permalink( $taxonomy_slug, $term ) { global $wp_query; // If there is already a filter running for this taxonomy if( isset( $wp_query->query_vars[$taxonomy_slug] ) ){ // And the term for this URL is not already being used to filter the taxonomy if( strpos( $wp_query->query_vars[$taxonomy_slug], $term ) === false ) { // Append the term $filter_query = $taxonomy_slug . '/' . $wp_query->query_vars[$taxonomy_slug] . '+' . $term; } else { // Otherwise, remove the term if( $wp_query->query_vars[$taxonomy_slug] == $term ) { $filter_query = ''; } else { $filter = str_replace( $term, '', $wp_query->query_vars[$taxonomy_slug] ); // Remove any residual + symbols left behind $filter = str_replace( '++', '+', $filter ); $filter = preg_replace( '/(^\+|\+$)/', '', $filter ); $filter_query = $taxonomy_slug . '/' . $filter; } } } else { $filter_query = $taxonomy_slug . '/' . $term; } // Maintain the filters for other taxonomies if( isset( $wp_query->tax_query ) ) { foreach( $wp_query->tax_query->queries as $query ) { $tax = get_taxonomy( $query['taxonomy'] ); // Have we already handled this taxonomy? if( $tax->query_var == $taxonomy_slug ) continue; // Make sure taxonomy hasn't already been added to query string if( strpos( $existing_query, $tax->query_var ) === false ) $existing_query .= $tax->query_var . '/' . $wp_query->query_vars[$tax->query_var] . '/'; } } if( isset( $existing_query ) ) $filter_query = $existing_query . $filter_query; return trailingslashit( get_post_type_archive_link( 'eg_event' ) . $filter_query ); }
-Ví dụ bạn tạo permalinks cho custom post taxonomy với taxonomy=’location’ và term=’nsw’ , bạn chỉ việc gọi:
// Link to page with only events in NSW echo eg_get_filter_permalink( 'location', 'nsw' ); </pre> Cuối cùng Generate Rewrite Rule. <pre lang="php"> function eg_generate_rewrite_rules( $post_type, $query_vars = array() ) { global $wp_rewrite; if( ! is_object( $post_type ) ) $post_type = get_post_type_object( $post_type ); $new_rewrite_rules = array(); $taxonomies = get_object_taxonomies( $post_type->name, 'objects' ); // Add taxonomy filters to the query vars array foreach( $taxonomies as $taxonomy ) $query_vars[] = $taxonomy->query_var; // Loop over all the possible combinations of the query vars for( $i = 1; $i <= count( $query_vars ); $i++ ) { $new_rewrite_rule = $post_type->rewrite['slug'] . '/'; $new_query_string = 'index.php?post_type=' . $post_type->name; // Prepend the rewrites & queries for( $n = 1; $n <= $i; $n++ ) { $new_rewrite_rule .= '(' . implode( '|', $query_vars ) . ')/(.+?)/'; $new_query_string .= '&' . $wp_rewrite->preg_index( $n * 2 - 1 ) . '=' . $wp_rewrite->preg_index( $n * 2 ); } // Allow paging of filtered post type - WordPress expects 'page' in the URL but uses 'paged' in the query string so paging doesn't fit into our regex $new_paged_rewrite_rule = $new_rewrite_rule . 'page/([0-9]{1,})/'; $new_paged_query_string = $new_query_string . '&paged=' . $wp_rewrite->preg_index( $i * 2 + 1 ); // Make the trailing backslash optional $new_paged_rewrite_rule = $new_paged_rewrite_rule . '?$'; $new_rewrite_rule = $new_rewrite_rule . '?$'; // Add the new rewrites $new_rewrite_rules = array( $new_paged_rewrite_rule => $new_paged_query_string, $new_rewrite_rule => $new_query_string ) + $new_rewrite_rules; } return $new_rewrite_rules; }
Using rewrite tag
Sử dụng rewrite tag với custom post thì có plugin “custom post type permalinks”, tuy nhiên bạn sẽ tự học được cách tạo rewrite tag riêng mà không dùng plugin. Rewrite tag còn gọi là custom variables.
function rewrite_bank(){ // add to our plugin init function global $wp_rewrite; $gallery_structure = '/bank/%year%/%monthnum%/%bank%'; $wp_rewrite->add_rewrite_tag("%bank%", '([^/]+)', "bank="); $wp_rewrite->add_permastruct('bank', $gallery_structure, false); } add_action('init','rewrite_bank');
Hoặc Sử dụng hàm add_rewrite_tag. Ví dụ sau đăng ký rewrite tag %film_title%
add_rewrite_tag('%film_title%','([^&]+)');
Dùng rewrite tag để đặt vào rewrite URL.e.g:
/films/%film_title%.html
tương ứng với URL: /films/phim-bo-ba-di-thoa.html
thì giá trị của tag %film_title% sẽ là ‘phim-bo-ba-di-thoa’. Để lấy giá trị rewrite tag ta dùng hàm query_vars hoặc get_query_var.
$wp_query->query_vars['film_title']
Hãy cho mình biết suy nghĩ của bạn trong phần bình luận bên dưới bài viết này. Hãy theo dõi kênh chia sẻ kiến thức WordPress của Hoangweb trên Twitter và Facebook
- shares
- Facebook Messenger
- Gmail
- Viber
- Skype