Laravel 5 –从网址中删除公开


240

我知道这是一个非常受欢迎的问题,但是我还没有找到适用于Laravel 5的有效解决方案。我已经尝试了很长时间从Codeigniter进行迁移,但是这种复杂的安装过程使我望而却步。

我不想运行虚拟机,在项目之间切换时这似乎很尴尬。

我不想将我的文档根目录设置为公用文件夹,这在项目之间切换时也很麻烦。

我已经尝试过.htaccess mod_rewrite方法

<IfModule mod_rewrite.c>
  RewriteEngine On
  RewriteRule ^(.*)$ public/$1 [L]
</IfModule>

这只是在74.10行中给了我一个Laravel NotFoundHttpException。

前一段时间尝试L4时,我使用了将公用文件夹的内容移到根目录中的方法。L5的结构完全不同,按照相同的步骤完全破坏了Laravel(服务器将仅返回空白页)。

在开发环境中是否有消除“公共”的不错方法,该方法是:

  1. 与L5搭配使用
  2. 使我可以轻松地在项目之间切换(我通常一次可以处理2或3个项目)。

谢谢

**我正在使用MAMP和PHP 5.6.2


1
指南中的文件夹结构与我的不同,我想他不是在使用L5吗?我忽略了他对Bootstrap / Paths文件所做的更改,因为它不存在。该项目似乎正在运行。你觉得还好吗
user1537360 2015年

我的错误让我为L5添加了答案
kamlesh.bar 2015年

尝试相同的方法没有成功
kamlesh.bar 2015年

1
它似乎可以通过修改index.php文件中的路径来工作,但是我对Laravel并不陌生,因此显然不能评论它是否稳定/安全。
user1537360 2015年

其他文件夹/文件应该位于文档根目录下。
MikeRockétt,2015年

Answers:


430

对于Laravel 5:

  1. server.php在您的Laravel根文件夹中重命名为index.php
  2. .htaccess文件从/public目录复制到Laravel根文件夹。

而已!


104
这样做可能是不安全的,请确保没有人可以请求您的.env文件,除非您
同意其他

48
如果您使用来自root即的相对路径来引用资产,则此方法将无效。“ /assets/styles.css”等。我仍在努力寻找在服务器上部署它的最佳方法
Ghazanfar Mir

1
这行得通...但是使用此功能有什么后果/缺点吗?许多人建议设置虚拟主机,或手动复制文件,等等。
博格兹,2015年

1
@GabLeRoux <Files "log.txt">Order Allow,DenyDeny from all</Files>解决了您解决的问题。现在安全还是有更多风险?
蝴蝶

1
@Butterflyit取决于您的服务器配置。上面只会阻止log.txt。只要确保您阻止公开的敏感数据即可。如果您使用Laravel并仔细阅读文档,则您的webroot看起来像project/public。看一下这个stackoverflow讨论qa。设置您的网络服务器,https://example.com/.env以防万一。如果您看到密码,请考虑所有受到威胁的内容并更改所有密码。
GabLeRoux '18

126

我已经使用2个答案解决了这个问题:

  1. 将server.php重命名为index.php(无修改)
  2. 将.htaccess从公用文件夹复制到根文件夹(如下面的rimon.ekjon所示)
  3. 对.htaccess进行如下更改以获取静态信息:

    RewriteEngine On
    
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule ^(.*)/$ /$1 [L,R=301]
    
    RewriteCond %{REQUEST_URI} !(\.css|\.js|\.png|\.jpg|\.gif|robots\.txt)$ [NC]
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
    
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_URI} !^/public/
    RewriteRule ^(css|js|images)/(.*)$ public/$1/$2 [L,NC]

    如果需要其他静态文件,只需将扩展名添加到先前声明的列表中


1
你好@KA_lin 如何防止某人像localhost / oap / .env
Fokwa Best,

8
嗯...尝试RewriteRule ^.env - [F,L,NC]
ka_lin

2
或者 <Files ~ "\.env$"> Order allow,deny Deny from all </Files>
ka_lin 2015年

非常感谢@ka_lin,是否可以通过/ public /删除访问权限?像www.yoursite.com一样有效,但是www.yoursite.com/public也可以,是否可以删除最后一个?
adaba

8
它正在工作,但是css,js和图像未加载
Chetan Khandla

93

在Laravel 5.5中,在您的根目录中创建.htacess文件并放置以下代码:- 参考链接

<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    RewriteCond %{REQUEST_FILENAME} -d [OR]
    RewriteCond %{REQUEST_FILENAME} -f
    RewriteRule ^ ^$1 [N]

    RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
    RewriteRule ^(.*)$ public/$1 

    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ server.php

</IfModule>

5
最好的答案!在我的示例中,只有一个工作,它肯定有更多的票数
FiliusBonacci

谢谢,这对我来说是工作。但是我想知道它是否存在任何安全问题。
rahul singh Chauhan

@rahulsinghChauhan,我很高兴。亲爱的我不知道安全问题,但是应该是安全的。
拉罕

2
这条规则是RewriteRule ^ ^$1 [N做什么的?
贡佐

这是唯一为我工作的人...非常感谢
Arshad Ameen

84

别!

您真的不应该server.php在Laravel根文件夹中重命名index.php 并将其.htaccess/public目录复制到Laravel根文件夹中!!!

这样,每个人都可以访问您的某些文件(.env例如)。自己尝试。你不要那个!


相反,您应该.htaccess像这样在根目录中创建一个文件:

RewriteEngine On
RewriteCond %{REQUEST_URI} !^/public/
RewriteRule ^(.*)$ /public/$1 [L,QSA]

这将以静默方式将所有基本URI重写到该/public文件夹。甚至所有标(例如HTTP Authorization Header)和所有可选的URI参数也将无提示地传递到该/public文件夹。

就这样

在使用Docker设置Laravel项目时,请注意:您不需要这样做。


2
它在生产中运行良好,但在本地没有任何建议吗?
Haritsinh Gohil

2
这是完美的工作!本地和服务器感谢您的安全帮助!
Ghanshyam Nakiya,

1
您好,@DerkJanSpeelman我正在尝试将laravel文件上传到托管主机的子文件夹中,例如:(example.com/projects/laravel/blog),在这种情况下,访问者必须访问example.com/projects/laravel/blog/公用,因此我将带有您的代码的.htaccess文件放在博客文件夹的根目录中,并希望它重定向到公用文件夹。但这不起作用。这是发生的错误:在此服务器上找不到请求的URL / public /。我该如何解决?
Shovon Das

1
这个答案被低估了。为粗体投票,并突出显示“不要”。一切正常。
Varun Ved

2
完美答案
alnassre19年

43

从laravel 5 url中删除public的简单方法。您只需要从公共目录中剪切index.php和.htaccess并将其粘贴到根目录中,就可以了,并将index.php中的两行替换为

require __DIR__.'/bootstrap/autoload.php';
$app = require_once __DIR__.'/bootstrap/app.php';

注意:上面的方法仅适用于初学者,因为他们可能会在设置虚拟主机时遇到问题,最好的解决方案是在本地计算机上设置虚拟主机并将其指向项目的公共目录。


1
在css无法加载之后,bcoz所有css都已公开,并且从URL中删除了公众
Tomar先生,2016年

1
您可以在加载时在js或css文件之前放置“ public /”,例如Html :: script(“ public / js / .....”); -但是最好的解决方案是虚拟主机...
Muhammad Sadiq

39

@ rimon.ekjon说:

将Laravel根文件夹中的server.php重命名为index.php并将.htaccess文件从/ public目录复制到Laravel根文件夹中。 - 而已 !!:)

那对我有用。但是/ public目录中的所有资源文件都找不到,并且无法请求url,因为我使用了asset()帮助器。

我更改了/Illuminate/Foundation/helpers.php/asset()函数,如下所示:

function asset($path, $secure = null)
{
    return app('url')->asset("public/".$path, $secure);
}

现在一切正常:)

谢谢@ rimon.ekjon和大家。


3
这不是解决此问题的好方法,因为您尝试在vendors目录中进行更新,这不是一个好习惯。
莎德曼(Shadman)

1
您只需要添加RewriteRule ^(.*)$ public/$1 [L]从公共目录复制的.htaccess文件,只需 删除此行RewriteRule ^(.*)/$ /$1 [L,R=301]
即可-Shadman

29

只需在根目录下创建.htaccess文件,然后向其中添加这些行

<IfModule mod_rewrite.c>
    RewriteEngine On

    RewriteRule ^(.*)$ public/$1 [L]
</IfModule>

而已!

上面的代码适用于根public_html文件夹。话虽如此,如果您的目录看起来像public_html / laravelapp / public,并且您将上述代码放在laravelapp中,则您的核心laravel文件应位于public_html文件夹中。因此,您必须将所有核心文件复制到public_html并将.htaccess文件放在此处。

如果要将代码保留在子目录中,则可以创建一个子域,那么该代码也将适用于该子域。


在阅读您的答案之前,我已在下面回答,这必须是被接受的答案。没有文件更改:只是一个简单,巧妙的规则。
布里戈

@Raham您当前的网址是什么?
Abhinav Saraswat

2
只想在这位先生的工作之上添加简短说明。上面的代码在根public_html文件夹上有效(我也遇到了问题)。说了您的核心laravel文件应该在public_html文件夹中,如果您将上面的代码放在laravelapp中,我的目录看起来像public_html / laravelapp / public,我犯了一个错误。因此,您必须将所有核心文件复制到public_html并将.htaccess文件放在此处。参考laravel的centOS和Cpanel托管。
Deepesh Thapa '18

使用此方法有何缺陷?
Script47

1
对我而言,这就像是一种魅力,我只有cPanel webshost,无法更改Apache的RootDirectory。谢谢 !最简单,最安全。这将不允许查看您的根文件夹内容
Vincent Decaux

27

.htaccess目录中创建文件,然后将代码放置如下。

<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    RewriteCond %{REQUEST_FILENAME} -d [OR]
    RewriteCond %{REQUEST_FILENAME} -f
    RewriteRule ^ ^$1 [N]

    RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
    RewriteRule ^(.*)$ public/$1 

    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ server.php
</IfModule>

1
我真的推荐这个解决方案。
TheLastCodeBender

1
我也建议使用此解决方案
iglesiasedd,

非常感谢。这是完美的(y)
伊斯兰教的回教王子

3
它工作正常,但仍然可以直接从URL访问.env文件。
Manoj Singh,

这是一个安全的解决方案吗?
高级PHP程序员团队负责人

23

1)我还没有找到在L5中移动公共目录的有效方法。虽然您可以在引导程序中修改某些内容index.php,但似乎有一些辅助功能是基于该公共目录存在的假设。老实说,您真的不应该移动公共目录。

2)如果您使用MAMP,则应该为每个项目创建新的虚拟主机,每个虚拟主机都服务于该项目的公共目录。创建完成后,您可以通过定义的服务器名称访问每个项目,如下所示:

http://project1.dev
http://project2.dev

15

可以在laravel5中删除公共 URL。跟着这些步骤:

步骤1.从公共目录复制所有文件并粘贴到目录

步骤2.打开index.php文件替换为

 require __DIR__.'/../bootstrap/autoload.php';

 require __DIR__.'/bootstrap/autoload.php';

$app = require_once __DIR__.'/../bootstrap/app.php';

$app = require_once __DIR__.'/bootstrap/app.php';

并删除所有缓存和cookie。


嗨,我已经尝试过您的方法,执行上述步骤,但显示以下错误:警告:require_once(D:\ Projects \ laravel / public / index.php):无法打开流:D中没有此类文件或目录:第21行的\ Projects \ laravel \ server.php致命错误:require_once():无法打开所需的'D:\ Projects \ laravel / public / index.php'(include_path ='.; C:\ xampp \ php \ PEAR' ),在第21行的D:\ Projects \ laravel \ server.php中
阿里·

这不是一个完美的答案,而是一种非常不安全的方法。
罗希特

11

假设您将所有其他文件和目录放置在名为“ locale”的文件夹中。

在此处输入图片说明

只需转到index.php并找到这两行:

require __DIR__.'/../bootstrap/autoload.php';

$app = require_once __DIR__.'/../bootstrap/app.php';

并将其更改为此:

require __DIR__.'/locale/bootstrap/autoload.php';

$app = require_once __DIR__.'/locale/bootstrap/app.php';

11

这是截至2018年5月适用于Laravel 5.5的最佳和最短解决方案

  1. 只需将.htaccess文件从/ public目录剪切到目录,并将其内容替换为以下代码:

    <IfModule mod_rewrite.c>
        <IfModule mod_negotiation.c>
           Options -MultiViews
        </IfModule>
    
        RewriteEngine On
    
        RewriteCond %{REQUEST_FILENAME} !-d
        RewriteRule ^(.*)/$ /$1 [L,R=301]
    
        RewriteCond %{REQUEST_URI} !(\.css|\.js|\.png|\.jpg|\.gif|robots\.txt)$ [NC]
        RewriteCond %{REQUEST_FILENAME} !-d
        RewriteCond %{REQUEST_FILENAME} !-f
        RewriteRule ^ server.php [L]
    
        RewriteCond %{REQUEST_FILENAME} !-d
        RewriteCond %{REQUEST_FILENAME} !-f
        RewriteCond %{REQUEST_URI} !^/public/
        RewriteRule ^(css|js|images)/(.*)$ public/$1/$2 [L,NC]
    </IfModule>
  2. 只需保存.htaccess文件即可。

  3. server.php文件重命名 为index.php。就是所有的享受!


9

最好的办法: 我会建议不要删除公众,而不是on local computer create a virtual host point to public directoryon remote hosting change public to public_html and point your domain to this directory。原因是,您的整个laravel代码将是安全的,因为它的一级降至您的公共目录:)

方法1:

我只是重新命名server.php,以index.php和它的工作原理

方法2:

这适用于所有laravel版本...

这是我的目录结构,

/laravel/
... app
... bootstrap
... public
... etc

遵循以下简单步骤

  1. 将所有文件从公共目录移至根目录/ laravel /
  2. 现在,不需要公共目录,因此可以选择将其立即删除
  3. 现在打开index.php并进行以下替换

要求 DIR '/ .. /引导/ autoload.php';

需要DIR。'/ bootstrap / autoload.php';

$ app = require_once DIR。'/ .. / bootstrap / start.php';

$ app = require_once DIR。'/ bootstrap / start.php';

  1. 现在打开bootstrap / paths.php并更改公共目录路径:

'public'=> DIR。'/ .. / public',

'public'=> DIR。'/ ..',

就是这样,现在尝试http:// localhost / laravel /


一切正常。但是artisan命令不起作用,只是显示“无法打开输入文件:artisan”。有什么建议吗?
卡比尔·侯赛因

如果您可以向用户公开数据库凭据,则此方法有效。localhost / laravel / .env
MasoodUrRehman

8

从网址中删除公开的4种最佳方法。

如果您使用其他任何技巧从URL中删除公共对象,例如将server.php的名称更改为index.php并更改为核心文件路径。显然,不要那样做。那为什么Laravel不提供这样的解决方案,因为这不是这样做的正确方法。

1)使用Laravel中的htaccess从URL中删除公共

通过将.htaccess文件添加到根目录中,您无需公开即可访问该网站

<ifmodule mod_rewrite.c>
    <ifmodule mod_negotiation.c>
        Options -MultiViews
    </ifmodule>

    RewriteEngine On

    RewriteCond %{REQUEST_FILENAME} -d [OR]
    RewriteCond %{REQUEST_FILENAME} -f
    RewriteRule ^ ^$1 [N]

    RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
    RewriteRule ^(.*)$ public/$1 

    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ server.php

</ifmodule>

2)通过在本地创建虚拟主机来删除公共

我在这里为Windows操作系统提供演示。但是,我将尝试定义一个步骤,以便任何人都可以轻松地遵循该步骤。您也可以针对特定的操作系统在Google上进行相同的研究。

步骤1:转到C:\ Windows \ system32 \ drivers \ etc \以管理员模式打开“主机”文件。

步骤2:向其中添加以下代码。在这里,我为您演示了projectname.local域名演示,您可以随意指定。只要使它在每个地方都恒定即可。

127.0.0.1  projectname.local

步骤3:现在,C:\xampp\apache\conf\extra对于xampp用户和wamp用户"C:\wamp\bin\apache\Apache2.4.4\conf\extra",打开"httpd-vhosts.conf"文件。现在,将以下代码添加到其中。

注意:根据项目更改文档根目录,还将定义的域名添加到“主机”文件中。

<VirtualHost projectname.local>
      ServerAdmin projectname.local
      DocumentRoot "C:/xampp/htdocs/projectdir"
      ServerName projectname.local
      ErrorLog "logs/projectname.local.log"
      CustomLog "logs/projectname.local.log" common
 </VirtualHost>

步骤4:最后但重要的一步是重新启动Xampp或Wamp并像那样访问URL http://projectname.local,Laravel将在没有公共URL的情况下响应。


3)通过在Laravel中运行命令来移除公众

如果您在本地工作,则无需执行任何操作,只需从终端或命令行工具运行以下命令即可。之后,您可以通过命令行通过提供的URL访问您的网站。

   > php artisan serve

如果您愿意在特定IP上运行项目,则需要运行以下命令。如果您在LAN上工作,那么如果要允许其他人从本地访问您的网站,则只需在使IP地址按照命令运行之后,通过运行“ ipconfig”来使用命令行检查IP地址即可。

> php artisan serve --host=192.168.0.177

如果您愿意在具有特定端口的特定IP上运行项目,则需要执行以下命令。

> php artisan serve --host=192.168.0.177 --port=77

4)移除托管服务器或面板上的公共对象

在此处输入图片说明

项目完成后,您需要将项目托管在服务器上,然后只需将域中的文档根目录设置为公用文件夹。检查以下屏幕截图。

根据屏幕截图,如果您在public_html中没有任何项目文件夹,则只需将文档根目录设置为 "public_html/public"

参考来自这里


1
四种方法都很好,但是我已经通过使用第一个解决方案解决了我的问题。
马尼沙

7

我想添加到@Humble Learner并注意,“修复”资产的url路径的正确位置是/Illuminate/Routing/UrlGenerator.php/asset()。

更新方法以匹配:

public function asset($path, $secure = null)
{
    if ($this->isValidUrl($path)) return $path;
    $root = $this->getRootUrl($this->getScheme($secure));
    return $this->removeIndex($root).'/public/'.trim($path, '/');
}

这将修复脚本,样式和图像路径。任何资产路径。


6

对于XAMPP用户而言,无需触摸laravel默认文件系统即可从网址中删除公共文件是为您的应用程序设置虚拟主机来执行此jsut,请按照以下步骤操作

  1. 打开XAMPP控制面板应用程序,然后停止Apache。请注意,较晚的Windows机器可能会将其作为服务运行,因此请选中Apache模块左侧的框。

  2. 导航到C:/xampp/apache/conf/extraXAMPP文件所在的位置。

  3. 使用文本编辑器打开名为httpd-vhosts.conf的文件。

  4. 在第19行附近找到#NameVirtualHost *:80并取消注释或删除哈希。

  5. 在文件的最底部粘贴以下代码:

<VirtualHost *>
    ServerAdmin admin@localhost.com
    DocumentRoot "C:/xampp/htdocs" # change this line with your htdocs folder
    ServerName localhost
    ServerAlias localhost
    <Directory "C:/xampp/htdocs">
        Options Indexes FollowSymLinks Includes ExecCGI
        Order allow,deny
        Allow from all
    </Directory>
</VirtualHost>
  1. 现在,您可以复制并粘贴下面的代码以添加虚拟主机目录。例如,我正在一个名为Eatery Engine的网站上工作,因此以下代码段将允许我在本地安装中使用子域:
<VirtualHost eateryengine.dev>
    ServerAdmin admin@localhost.com
    DocumentRoot "C:/xampp/htdocs/eateryengine" # change this line with your htdocs folder
    ServerName eateryengine.dev
    ServerAlias eateryengine.dev
    <Directory "C:/xampp/htdocs/eateryengine">
        Order allow,deny
        Allow from all
    </Directory>
</VirtualHost>
  1. 接下来转到Windows主机文件以编辑主机。该文件将位于C:/Windows/System32/drivers/etc/hosts,其中hosts是文件。用记事本打开它。
  2. 查找#localhost名称解析是在DNS本身内部处理的。

127.0.0.1 localhost

本地主机名称解析是在DNS本身内处理的。

127.0.0.1       localhost
127.0.0.1       eateryengine.dev #change to match your Virtual Host.
127.0.0.1       demo.eateryengine.dev #manually add new sub-domains.
  1. 重新启动Apache并测试所有内容。

原始文章可以在这里找到


5

在Laravel设置中总是有一个公共文件夹的原因,所有与公共相关的资料都应存在于公共文件夹中,

不要将您的IP地址/域指向Laravel的根文件夹,而是将其指向公用文件夹。将服务器IP指向根文件夹是不安全的,因为除非您在中编写限制,否则.htaccess一个人可以轻松访问其他文件。

只需在.htaccess文件中写入重写条件并安装重写模块并启用重写模块,即可解决在路由中添加公用的问题。


3

我知道有很多解决此问题的方法。最好和最简单的解决方案是在目录中添加.htaccess文件。

我尝试了为此问题提供的答案,但是在Laravel中使用auth:api Guard遇到一些问题。

这是更新的解决方案:

<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On
    RewriteCond %{HTTP:Authorization} ^(.*)
    RewriteRule .* - [e=HTTP_AUTHORIZATION:%1]

    RewriteCond %{REQUEST_FILENAME} -d [OR]
    RewriteCond %{REQUEST_FILENAME} -f
    RewriteRule ^ ^$1 [N]

    RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
    RewriteRule ^(.*)$ public/$1

    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ server.php
</IfModule>

在您的根目录中创建.htaccess文件,然后添加此代码。一切顺利


2

Laravel 5.5

首次安装Laravel之后,我遇到了著名的“公用文件夹问题”,然后我想到了这个解决方案,以我个人的观点,它比在Web上找到的其他解决方案更“干净”。


成就成就

  • publicURI中没有字
  • 保护.env文件免受好奇的人

只需编辑.htaccess使用mod_rewrite规则和四个简单规则即可完成所有操作。


脚步

  1. .htaccess文件移入public/.htaccess主根目录
  2. 如下编辑

我评论了所有内容,所以对于那些从未使用过的用户mod_rewrite(不是我是专家,反之亦然)也应该很清楚(我希望)。另外,要了解规则,必须明确的是,如果Bill连接到https://example.comhttps://example.com/index.php则在Laravel中已加载。该文件仅包含命令header("refresh: 5; https://example.com/public/"),该命令将请求发送到https://example.com/public/index.php。此秒index.php负责加载控制器和其他内容。

# IfModule prevents the server error if the app is moved in an environment which doesn’t support mod_rewrite
<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    # RULES ORIGINALLY IN public/.htaccess ---
    # Redirect Trailing Slashes If Not A Folder...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_URI} (.+)/$
    RewriteRule ^ %1 [L,R=301]

    # Handle Front Controller...
#    RewriteCond %{REQUEST_FILENAME} !-d
#    RewriteCond %{REQUEST_FILENAME} !-f
#    RewriteRule ^ index.php [L]

    # Handle Authorization Header
    RewriteCond %{HTTP:Authorization} .
    RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
    # --- END

    # PERSONAL RULES ---
    # All the requests on port 80 are redirected on HTTPS
    RewriteCond %{SERVER_PORT} ^80$
    RewriteRule .* https://%{SERVER_NAME}%{REQUEST_URI} [R,L]

    # When .env file is requested, server redirects to 404
    RewriteRule ^\.env$ - [R=404,L,NC]

    # If the REQUEST_URI is empty (means: http://example.com), it loads /public/index.php
    # N.B.: REQUEST_URI is *never* actually empty, it contains a slash that must be set as match as below
    # .* means: anything can go here at least 0 times (= accepts any sequence of characters, including an empty string)
    RewriteCond %{REQUEST_URI} ^/$
    RewriteRule ^(.*) /public/index.php [L]

    # If the current request is asking for a REQUEST_FILENAME that:
    # a) !== existent directory
    # b) !== existent file
    # => if URI !== css||js||images/whatever => server loads /public/index.php, which is responsible to load the app and the related controller
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule !^(css|js|images|media)/(.*)$ /public/index.php [L,NC]

    # If the current request is asking for a REQUEST_FILENAME that:
    # a) !== existent directory
    # b) !== existent file
    # => if URI == css||js||images[=$1]/whatever[=$2] => server loads the resource at public/$1/$2
    # If R flag is added, the server not only loads the resource at public/$1/$2 but redirects to it
    # e.g.: bamboo.jpg resides in example.com/public/media/bamboo.jpg
    #       Client asks for example.com/media/bamboo.jpg
    #       Without R flag: the URI remains example.com/media/bamboo.jpg and loads the image
    #       With R flag: the server redirects the client to example.com/public/media/bamboo.jpg and loads the image
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^(css|js|images|media)/(.*)$ /public/$1/$2 [L,NC]
    # --- END

</IfModule>

public/.htaccess可以删除以下规则(最初在中)。实际上,在最后两个规则中更详细地阐明了相同的规则。

# Handle Front Controller...
#    RewriteCond %{REQUEST_FILENAME} !-d
#    RewriteCond %{REQUEST_FILENAME} !-f
#    RewriteRule ^ index.php [L]

编辑:我想念Abhinav Saraswat的解决方案,他的回答应该是被接受的。只需一条简单明了的规则即可将所有流量重定向到公用文件夹,而无需修改任何文件。


2

首先,您可以使用以下步骤

对于Laravel 5:

1。将Laravel根文件夹中的server.php重命名为index.php

2。将.htaccess文件从/ public目录复制到Laravel根文件夹。

资源: https //stackoverflow.com/a/28735930

完成这些步骤之后,您需要更改所有的CSS和脚本路径,但这会很累人。

解决方案:仅需对产品进行少量更改helpers::asset功能即可。

为此

  1. 打开 vendor\laravel\framework\src\Illuminate\Foundation\helpers.php

  2. 转到第130行

  3. "public/".$path的不是$path

    function asset($path, $secure = null){
       return app('url')->asset("public/".$path, $secure);
    }

2
规则编号1:切勿编辑核心文件。即使现在看起来很轻松漂亮,您稍后也要付款。
Janaka Dombawela '18

@JanakaDombawela我不这么认为是因为:
FerhatKOÇER18年

@JanakaDombawela我不这么认为是因为:Senerio 1:如果有经验的开发人员:开源代码适合此工作Senerio 2:如果开发人员是初级,开发人员必须对源代码进行编辑以获取经验
FerhatKOÇER

2
<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews -Indexes
    </IfModule>

    RewriteEngine On

    # Handle Authorization Header
    RewriteRule ^(.*)$ public/$1 [L]
    RewriteCond %{HTTP:Authorization} .
    RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]

    # Redirect Trailing Slashes If Not A Folder...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_URI} (.+)/$
    RewriteRule ^ %1 [L,R=301]

    # Handle Front Controller...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
</IfModule>

使用以下命令激活mod_rewrite模块

sudo a2enmod rewrite

然后重新启动Apache

sudo service apache2 restart

要从.htaccess文件中使用mod_rewrite(这是一种很常见的用例),请使用

sudo nano /etc/apache2/sites-available/000-default.conf

在“ DocumentRoot / var / www / html”下方,添加以下行:

<Directory "/var/www/html">
AllowOverride All
</Directory>

再次重新启动服务器:

sudo service apache2 restart

1

我之前已经读过一些文章,它可以正常工作,但真的不知道是否安全

    a. Create new folder local.
    b. Move all project into the local folder expect public folder.
    c. Move all the content of public folder to project root.
    d. Delete the blank public folder
    f. Edit the index file. 

编辑index.php

require __DIR__.'/../bootstrap/autoload.php';
$app = require_once __DIR__.'/../bootstrap/app.php';

require __DIR__.'/local/bootstrap/autoload.php';
$app = require_once __DIR__.'/local/bootstrap/app.php';

1

即使我不建议将Laravel放在根文件夹中,在某些情况下也无法避免;对于这些情况,上述方法不适用于资产,因此我快速更改了htaccess:将server.php复制到index.php之后,编辑.htaccess文件,如下所示:

<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    ### fix file rewrites on root path ###
    #select file url
    RewriteCond %{REQUEST_URI} ^(.*)$
    #if file exists in /public/<filename>
    RewriteCond %{DOCUMENT_ROOT}/public/$1 -f
    #redirect to /public/<filename>
    RewriteRule ^(.*)$ public/$1 [L]
    ###############

    # Redirect Trailing Slashes If Not A Folder...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteRule ^(.*)/$ /$1 [L,R=301]

    # Handle Front Controller...

    #RewriteCond %{REQUEST_FILENAME} -d # comment this rules or the user will read non-public file and folders!
    #RewriteCond %{REQUEST_FILENAME} -f #
    RewriteRule ^ index.php [L]
</IfModule>

这是我必须进行的快速修复,因此欢迎任何人对其进行升级。


1

问题是,如果您键入/ public,它仍将在url中可用,因此我创建了一个修复程序,应将其放置在public / index.php中

  $uri = urldecode(
     parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH)
  );

  if(stristr($uri, '/public/') == TRUE) {

    if(file_exists(__DIR__.'/public'.$uri)){

    }else{

      $actual_link = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://{$_SERVER['HTTP_HOST']}{$_SERVER['REQUEST_URI']}";
      $actual_link = str_replace('public/', '',$actual_link);
      header("HTTP/1.0 404 Not Found");
      header("Location: ".$actual_link."");
      exit();
      return false;
   }}

这种和平的代码将从URL中删除public,并给出一个404,然后在没有public的情况下重定向到该URL


0

我使用的另一种方法是使用htdocs或www中的ln命令创建符号链接(在Linux中,不了解Win),ln projectname/public project 因此可以通过localhost / project访问该站点。


0

您可以使用多种方法从网址中删除公共关键字。

1)如果您正在使用专用主机并且具有root用户访问权限,则可以使用虚拟主机从url中删除public关键字。您应该给public提供DocumentRoot路径。因此,这将从公共目录开始索引,并将其从url中删除。

<VirtualHost *:80>
    ServerAdmin info@example.com
    ServerName example.com
    ServerAlias www.example.com
    DocumentRoot /var/www/html/{yoursourcedirectory}/public

    ErrorLog ${APACHE_LOG_DIR}/error.log
    CustomLog ${APACHE_LOG_DIR}/access.log combined
</VirtualHost>

2)如果您没有主机的root访问权限,则应在根目录中添加一个新的.htaccess文件,并将代码如下所示

<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
    Options -MultiViews
</IfModule>

RewriteEngine On

RewriteCond %{REQUEST_FILENAME} -d [OR]
RewriteCond %{REQUEST_FILENAME} -f
RewriteRule ^ ^$1 [N]

RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
RewriteRule ^(.*)$ public/$1 

RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ server.php
</IfModule>

您可以在此处获得更多参考


0

在根目录中创建.htaccess文件,并按如下所示放置代码。

<IfModule mod_rewrite.c>
 #Session timeout

<IfModule mod_negotiation.c>
    Options -MultiViews
</IfModule>

RewriteEngine On

RewriteCond %{REQUEST_FILENAME} -d [OR]
RewriteCond %{REQUEST_FILENAME} -f
RewriteRule ^ ^$1 [N]

RewriteCond %{REQUEST_URI} (\.\w+$) [NC]
RewriteRule ^(.*)$ public/$1

RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ server.php

</IfModule>

在/ public目录中创建.htaccess文件,并按如下所示放置代码。

<IfModule mod_rewrite.c>
  <IfModule mod_negotiation.c>
    Options -MultiViews -Indexes
  </IfModule>

RewriteEngine On

# Handle Authorization Header
RewriteCond %{HTTP:Authorization} .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]

# Redirect Trailing Slashes If Not A Folder...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} (.+)/$
RewriteRule ^ %1 [L,R=301]

# Handle Front Controller...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
</IfModule>

-1

我找到了这个问题的最有效的解决方案。

只需.htaccess文件夹中编辑,然后编写以下代码。不需要其他

RewriteEngine on
RewriteCond %{REQUEST_URI} !^public
RewriteRule ^(.*)$ public/$1 [L]

<IfModule php7_module>
   php_flag display_errors Off
   php_value max_execution_time 30
   php_value max_input_time 60
   php_value max_input_vars 1000
   php_value memory_limit -1
   php_value post_max_size 8M
   php_value session.gc_maxlifetime 1440
   php_value session.save_path "/var/cpanel/php/sessions/ea-php71"
   php_value upload_max_filesize 2M
   php_flag zlib.output_compression Off
</IfModule>

-1

我在这里尝试了一些解决方案,并发现适用于laravel 5.2的htaccess,如下所示:

RewriteEngine On

RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)/$ /$1 [L,R=301]



RewriteCond %{REQUEST_URI} !(\.css|\.js|\.png|\.jpg|\.gif|robots\.txt)$ [NC]
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ server.php

RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_URI} !^/public/
RewriteRule ^(css|js|images)/(.*)$ public/$1/$2 [L,NC]
RewriteRule ^.env - [F,L,NC]
RewriteRule ^app - [F,L,NC]
RewriteRule ^bootstrap - [F,L,NC]
RewriteRule ^config - [F,L,NC]
RewriteRule ^database - [F,L,NC]
RewriteRule ^resources - [F,L,NC]
RewriteRule ^vendor - [F,L,NC]

当您有另一个要禁止的文件或文件夹时,只需添加

RewriteRule ^your_file - [F,L,NC]

-1

您不需要做很多事情,只需在根目录上创建一个.htaccess文件,然后粘贴/保存以下内容即可;

<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule ^(.*)$ public/$1 [L]
</IfModule>

这将我重定向到/ public / public
zanderwar,

@zanderwar,请问Laravel是什么版本?另外,希望您不要将项目放在主目录的子目录中?
维克多·Ifeanyi Ejiogu

项目是根目录,版本是5.6。*-尽管它在子域中,在共享主机上;不幸的是,此cPanel安装迫使子域在public_html中拥有一个文件夹
zanderwar
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.