問題描述

我想為多個網址提供特定的 WordPress 頁面。基本上我想把所有的 url 以特定的格式指向一個已知的頁面:

/some-prefix-* => /target-page

並訪問/some-prefix-and-here-something 它應該加載/target-page

怎麼辦?

注意我不想重定向用户,但是能夠將現有頁面提供給多個 URL 。

.htaccess 看起來像這樣:

# BEGIN s2Member GZIP exclusions
RewriteEngine On RewriteRule ^prefix-*$ some/path/to/directory-$1 [NC,L]
<IfModule rewrite_module>
    RewriteEngine On
    RewriteBase /
    RewriteCond %{QUERY_STRING} (^|?|&)s2member_file_download=.+ [OR]
    RewriteCond %{QUERY_STRING} (^|?|&)no-gzip=1
    RewriteRule .* - [E=no-gzip:1]
</IfModule>
# END s2Member GZIP exclusions

# BEGIN WordPress
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>

# END WordPress

DirectoryIndex index.php index.html

我想通過添加 RewriteEngine On RewriteRule ^prefix-*$ some/path/to/directory-$1 [NC,L]將服務/prefix-*some/path/to/directory-$1 。例如:訪問 example.com/prefix-foo 時應與 example.com/some/path/to/directory-foo 相同 (解析為 example.com/some/path/to/directory-foo/index.html) 。

另外,如果已經有名為 prefix-bar 的 Wordpress 頁面,/prefix-bar 不應加載 example.com/some/path/to/directory-bar/index.html

最佳解決方案

您可以使用 template_include,但在掛接到此過濾器之前,您必須執行以下步驟:

  1. 創建頁面模板。例如:page-target.php

    <?php
    /**
     * Template Name: Page Target
     */
    ...
    
  2. page-target.php 模板上手動查詢 target-page 的內容,因為全局 $post 將引用到 some-prefix-*頁面。

  3. (可選):從頁面屬性編輯並應用頁面模板 Page Target/target-page

然後將以下內容添加到 functions.php 文件中

add_filter('template_include', function($template) {
    global $post;

    $prefix = 'some-prefix-'; // Your prefix
    $prefixExist = strpos($post->post_name, $prefix) !== false;

    if ($prefixExist) {
        return locate_template('page-target.php'); //Your template
    }

    return $template;
});

如果條件滿足,以上過濾器將覆蓋 page-target.php 的模板,否則默認

編輯:

我想我已經找到一個更好的方式來解決這個使用 add_rewrite_rule

function custom_rewrite_basic() {
  $page_id = 123; //Your serve page id
  add_rewrite_rule('^some-prefix-.*', 'index.php?page_id=' . $page_id, 'top');
}
add_action('init', 'custom_rewrite_basic');

IMPORTANT: Do not forget to flush and regenerate the rewrite rules database after modifying rules. From WordPress Administration Screens, Select Settings -> Permalinks and just click Save Changes without any changes.

次佳解決方案

請注意,搜索引擎可能不喜歡同一內容的多個路徑!

在這裏我假設你想要例如:

example.tld/some/path/to/painting-orange
example.tld/painting-blue
example.tld/painting-red
example.tld/painting-yellow

表現得像這個頁面:

example.tld/paintings

但不是如此:

example.tld/painting-white/painting-brown/large
example.tld/painting-brown/small

這裏的規則是匹配 basename( $path )左側的前綴。

以下是 request 篩選器的一些小問題,以檢查當前頁面名稱是否正確前綴:

<?php
/**
 * Plugin Name: Wildcard Pages
 */
add_filter( 'request', function( $qv )
{
    // Edit to your needs
    $prefix = 'painting-';
    $target = 'paintings';

    // Check if the current page name is prefixed
    if(    isset( $qv['pagename'] )
        && $prefix === substr( basename( $qv['pagename'] ), 0, strlen( $prefix ) )
    )
        $qv['pagename'] = $target;

    return $qv;
} );

根據您的需要修改然後創建插件文件/wp-content/plugins/wpse-wildcard-pages/wpse-wildcard-pages.php 文件並從後端激活插件。

我們還可以在目標頁面上添加 get_page_by_path()的支票,以確保它存在。我們也可能會將其限制為某些帖子類型。

參考文獻

注:本文內容整合自 Google/Baidu/Bing 輔助翻譯的英文資料結果。如果您對結果不滿意,可以加入我們改善翻譯效果:薇曉朵技術論壇。