htaccess中的Wordpress和CI重写规则

时间:2017-10-17 10:10:22

标签: wordpress .htaccess codeigniter

我在example.com中安装了WordPress。我还在ci文件夹example.com/ci/中安装了CodeIgniter,ci是文件夹名称,register是控制器名称,CI的工作URL是example.com/ci/register。我的基本网址以https://。

开头

现在我有一个WordPress网址example.com/hotelhotel是我在WordPress管理员中创建的网页,它运行正常。

我想像example.com/hotel/ci/register那样运行我的CI路径,我想我们可以使用一些重写规则来执行此操作,以便我的网址看起来像example.com/hotel/ci/register。我为wordpress添加了htaccess,将我重定向到example.com/hotel/ci/register。它向我展示了CI 404 error。这意味着现在我在CI。现在我在routes.php文件中做了以下事情。

$route['default_controller'] = 'register';
$route['404_override'] = 'register';

现在这个网址example.com/hotel/ci/register正在运行,但这不是正确的方法,下次会有更多的控制器,那么它将无法正常工作。

注意:我无法创建hotel文件夹,因为酒店是WordPress中的一个页面。如果我创建hotel文件夹,则WordPress URL example.com/hotel/将无效。它会将WordPress页面重定向到hotel文件夹。所以我必须在不创建hotel文件夹的情况下这样做。注意example.com = myurl.com。

我需要找到另一个好的解决方案。非常感谢任何建议或指导?

以下是我在wordpress htaccess中的重写规则:

# BEGIN WordPress
   <IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteBase /
    RewriteRule ^/?hotel/ci/register(/.*)?$ /ci/$1 [L]
    RewriteRule ^index\.php$ - [L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule . /index.php [L]
    </IfModule>
# END WordPress

以下是我的CI htaccess

<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond $1 !^(index\.php|resources|robots\.txt)
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php?/$1 [L,QSA] 
</IfModule>

4 个答案:

答案 0 :(得分:5)

有趣的问题!我设置了一个Docker容器,全新安装了Wordpress和Codeigniter,我在WP中创建了一个hotel页面,在CI中创建了一个Register控制器和视图,并进行了测试。我花了太长时间,但我确实找到了答案。

首先,你的Wordpress .htaccess。正如@tobiv在评论中指出的那样,你不应该在BEGIN/END WordPress评论之间添加任何内容,因为它可能会受到WP更新的影响。您的重定向必须在标准WP规则之前,因此请将其添加到文件的顶部

<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule ^hotel/ci/register /ci/register [L]
</IfModule>

# BEGIN WordPress
# ... These are the default, unchnaged WP rules
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>

<IfModule mod_rewrite.c>RewriteEngine On是重复的,看起来很混乱,但你确实需要它们,因为你的新规则必须先行,以便它在WP规则之前处理请求。

您无需修改​​Codeigniter .htaccess文件,您只需要默认文件即可。它应该位于Codeigniter安装的根目录ci/.htaccess

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/$1 [L]

此时https://example.com/hotel/ci/register将显示Codeigniter 404页面。如果您启用了日志记录(请参阅config/config.php),并且您看到了日志文件,您将看到原因:

ERROR - 2017-11-14 17:57:20 --> 404 Page Not Found: Hotel/ci

这是整个问题的根源。由于初始重定向是内部重定向(意味着浏览器中显示的URL不会更改),因此URI Codeigniter接收到的进程仍然是浏览器地址栏中显示的那个 - hotel/ci/register 。 Codeigniter将尝试以两种方式处理这样的请求:

  • application/config/routes.php

  • 中查找匹配的路线
  • 或者使用名为application/controllers/Hotel.php的方法查找名为ci的控制器;

在我们的案例中,没有Hotel控制器,也没有描述如何处理此类请求的路由,所以繁荣,404。

一个简单的解决方案是创建一个处理此请求的路由:

$route['hotel/ci/register'] = 'register/index';

现在https://example.com/hotel/ci/register有效!

注意:

  • 将默认路由设置为register$route['default_controller'] = 'register';)意味着https://example.com/ci/也会显示注册。我不确定你是否想要那个?如果该URL显示与https://example.com/hotel/ci/register相同,您可能会遇到重复内容的搜索引擎优化问题,因此您可能需要其他内容或404。

  • 确保删除$route['404_override'] = 'register';路线;

  • CI base_url与此问题无关,但显然应该设置。根据您希望链接的方式,我认为http://example.com/ci/http://example.com/hotel/ci/是正确的。

  • 我不太确定您的CI .htaccess中此条件的目的是什么:

    RewriteCond $1 !^(index\.php|resources|robots\.txt)
    

    现有的默认条件已经跳过磁盘上存在的文件和目录。这就是!-f!-d条件的含义 - “如果请求的模式与磁盘上的文件或目录不匹配,则执行重定向”。

    如果您的robots.txt目录中有ci/个文件,并且有人请求https://example.com/ci/robots.txt,则!-f条件将失败,并且会跳过重写 - 表示请求在没有重写的情况下处理,并且robots.txt成功返回。 index.php也是如此。如果您有一个名为ci/resources的目录,而某人请求https://example.com/ci/resources!-d条件将失败,重定向将被跳过,请求成功。

    我不确定你的resources部分,但也许你可以完全删除这个条件。

  • 如果您不需要漂亮的Codeigniter网址(我的意思是https://example.com/hotel/ci/register之外的其他网址,此更改不会影响它),而且事实证明您不需要上面的额外条件,可以完全摆脱CI .htaccess以简化事情。要做到这一点,只需将Wordpress RewriteRule更改为非漂亮版本:

    RewriteRule ^hotel/ci/register /ci/index.php/register [L]
    

    并删除您的CI .htacces

答案 1 :(得分:2)

我认为你走在正确的道路上,试试这个:

# BEGIN WordPress
   <IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteBase /
    RewriteRule ^/hotel/ci(/.*)?$ /ci/$1 [L]  # remove the register part 
                                              # so that it would be handled by CI
                                              # also remove the "?" in front of hotel
    RewriteRule ^index\.php$ - [L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule . /index.php [L]
    </IfModule>
# END WordPress

保持你的CI htaccess:

<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond $1 !^(index\.php|resources|robots\.txt)
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php?/$1 [L,QSA] 
</IfModule>

最后一部分与您的CI config.php匹配到您的新网址模型

$config['base_url'] = "http://example.com/hotel/ci/";

答案 2 :(得分:2)

我不认为这将是您问题的最佳答案,但如果我遇到同样的问题,我将使用routes查看示例代码。

$route['(:any)/ci/register']  = "register";

上述代码的作用(:any)表示第一个uri中的任何单词,之后您可以定义任何您想要定义的网址ci/register,您也可以这样做。

$route['(:any)/register']  = "here_you_can_add_your_controller/function";

如果像这样点击url,这将有效。

  

http://www.example.com/any_word_you_want/register

     

它会击中您的控制器功能。你需要echo一些东西,它会显示在你的浏览器中。

你也可以在你的基本网址中定义酒店字样,@ am05mhz在他的回答中显示,但我不认为这是一个好主意,因为将来你的网址中还有2个单词。

注意:上述代码示例仅在您.htaccess提供溃败访问时才有效,因为您在问题中显示.htaccess对您有用。有关溃败的完整知识,请查看codeigniter URI routing

的文档

答案 3 :(得分:1)

请改用htaccess [P]标志。

确保替换(目标)字符串以http://开头。否则,它会将替换字符串视为内部文件路径。

检查以下代码。

# BEGIN WordPress
   <IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteBase /

    RewriteRule ^/?hotel/ci/(.*)?$ http://example.com/ci/$1 [P]

    # If you want rewrite any URI as long it has */ci/* in it. 
    # Use the following rule instead.
    # RewriteRule ^(.*)/ci/(.*)?$ http://example.com/ci/$1 [P]

    RewriteRule ^index\.php$ - [L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule . /index.php [L]
    </IfModule>
# END WordPress

此外,您无需更新CI的基本网址。空字符串可以。

$config['base_url'] = '';

希望有所帮助。

链接:
https://httpd.apache.org/docs/current/rewrite/flags.html#flag_p