it-swarm.com.de

.htaccess Leiten Sie bei Verwendung von Framework etc. alle Anfragen an Public dir um

Ich benutze diesen .htaccess Code, um alle Anfragen an das öffentliche Verzeichnis zu leiten:

    <IfModule mod_rewrite.c>
        RewriteEngine On

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

Seitenstruktur:

Public_html/
  app/
  public/
    app/
    css/
    index.php
  index.php

Dieser Code funktioniert einwandfrei, schlägt jedoch fehl, wenn ich in root auf vorhandene Verzeichnisse tippe:

  • www.example.com/css -> public_html/public/css - funktioniert in Ordnung
  • www.example.com/app -> public_html/app - nicht ok, muss public_html/public/app sein

So ignorieren Sie vorhandene Verzeichnisse und schreiben alles in das Verzeichnis public

5
DariusJu

Dieser Code funktioniert gut

Sie müssen noch etwas anderes haben ... Der von Ihnen veröffentlichte Code würde zu einer Überschreibungsschleife (500 Internal Server Error) für all -Anfragen führen.

Aber Sie müssen auch nichts Besonderes tun, um "vorhandene Verzeichnisse zu ignorieren und alles in das öffentliche Verzeichnis zu schreiben". Also nochmal, es muss noch etwas hier los sein?

Was Sie jedoch tun müssen, um eine Umschreibeschleife zu vermeiden, ist die Aufnahme einer Bedingung, um ein Umschreiben in das Unterverzeichnis "public" zu vermeiden, wenn Sie bereits in das Unterverzeichnis "public" umgeschrieben haben. Zum Beispiel:

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

Ohne die RewriteCond Direktive würde /something umgeschrieben werden in /public/something zu /public/public/something zu /public/public/public/something, etc ...

Im Übrigen benötigen Sie keine Anker (^ und $), wenn Sie mit der gesamten Zeichenfolge übereinstimmen. Daher sind ^(.*)$ und (.*) identisch.

<IfModule mod_rewrite.c>

Nebenbei: Sofern Ihre Site nicht ohne mod_rewrite "funktionieren" soll, sollten Sie den Wrapper <IfModule...> entfernen.

PDATE:

Comment: Der vorhandene .htaccess stammt von laravel Entwicklern:

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

    RewriteEngine On

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

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

Ok, das macht mehr Sinn, ist aber auch Teil des "Problems". Sie können nicht einfach die Anweisung another hinzufügen und damit rechnen, dass sie funktioniert. Sie müssen mit ​​den vorhandenen Anweisungen arbeiten (wenn das die Absicht ist). Die Reihenfolge der mod_rewrite-Direktiven ist wichtig.

Dies wird komplexer, da Sie vorhandene Dateien und Verzeichnisse im Dokumentstamm ignorieren möchten (gemäß Ihrer Frage). Außerdem muss das /public -Unterverzeichnis vermutlich privat gehalten werden, da wir es sonst einfach umleiten könnten. Die "Redirect Trailing Slashes" werden dann etwas knifflig, da wir nicht in das Verzeichnis /public umleiten können (da dies offensichtlich das versteckte Verzeichnis freigibt), sondern die Existenz von Verzeichnissen in diesem Verzeichnis überprüfen müssen Dokumentenstamm (in dem wir uns gerade befinden). Sie müssen auch den direkten Zugriff auf das Verzeichnis /public blockieren (oder vielmehr zurück zum Stammverzeichnis leiten).

Versuchen Sie Folgendes (nur die inneren mod_rewrite-Direktiven sind nach RewriteEngine enthalten):

# Prevent direct access to the "public" folder - redirect to root
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /public/
RewriteRule ^public/(.*) /$1 [R=302,L]

# Redirect Trailing Slashes If Not A Folder...
# - but look for the file in the "public" folder
#   (ensure we are not already in the "public" folder)
RewriteCond %{REQUEST_URI} !^/public/
RewriteCond %{DOCUMENT_ROOT}/public/$1 !-d
RewriteRule ^(.*)/$ /$1 [R=302,L]

# Rewrite "everything" to the "public" subdirectory if not already
# This ignores existing files/dirs in the document root
RewriteCond %{REQUEST_URI} ^/(.*)
RewriteRule !^public/ public/%1

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

Stellen Sie vor dem Testen sicher, dass Sie den Browser-Cache leeren, da die vorherigen (fehlerhaften) 301-Weiterleitungen vom Browser zwischengespeichert wurden.

Ändern Sie die (temporären) Weiterleitungen von 302 in 301, wenn Sie sicher sind, dass sie ordnungsgemäß funktionieren. (302s werden vom Browser nicht zwischengespeichert, wodurch das Testen einfacher wird.)

3
MrWhite