2009-07-22 16 views
6

Estoy tratando de escribir un conjunto de reglas mod_rewrite que permiten a mis usuarios utilizar una sola carpeta para desarrollar en diferentes proyectos, y no tener que meterse con agregar fantasmas para cada proyecto individual.Apache mod_rewrite un subdominio a una subcarpeta (a través de redirección interna)

Mi idea para lograr esto, es configurar un "Global VHost" para cada usuario que necesita esta capacidad (solo 3-4), el vhost sería algo así como: .my-domain.com. Desde allí, quiero promocionar a mis usuarios para que escriban código como si estuviera en un dominio y no en una subcarpeta. Por ejemplo, si bob estaba trabajando en un proyecto llamado 'gnome', me gustaría que la URL bob (y cualquier otra persona en nuestra red interna) cargue para llegar a este proyecto: http://gnome.bob.my-domain.com. Pero, lo que me gustaría que Apache hiciera, es reconocer que "gnome" es un "proyecto" y así mapear la solicitud, internamente, a bob.my-domain.com/gnome/.

Tengo lo que pensé que funcionaría, y es bastante simple, pero ... ¡no funciona! La solicitud simplemente entra en un ciclo infinito y mantiene el prefijo del subdominio en el URI de solicitud reescrito.

El código de reescritura mod que tengo es:

RewriteEngine On 

RewriteCond %{HTTP_HOST} ^([^.]+)\.bob\.my-domain\.com 
RewriteCond %{REQUEST_URI} !^/%1.* 
RewriteRule ^(.*)$  /%1/$1 [L] 

Googled alrededor de un poco sobre esto, pero todavía tengo que encontrar soluciones reales que funcionan. Alguien ha intentado esto - o tal vez, ¿alguien tiene una mejor idea? Uno que no implique hacer un host virtual para cada proyecto (tengo diseñadores ... Creo que todos estarían de acuerdo en que un diseñador no debería crear hosts virtuales ...)

¡Gracias!

Aquí hay un fragmento de la rewrite_log:

[rid#838dc88/initial] (3) [perdir /home/bob/http/] strip per-dir prefix: /home/bob/http/index.html -> index.html 
[rid#838dc88/initial] (3) [perdir /home/bob/http/] applying pattern '^(.*)$' to uri 'index.html' 
[rid#838dc88/initial] (4) [perdir /home/bob/http/] RewriteCond: input='gnome.bob.my-domain.com' pattern='^([^.]+)\.bob\.my-domain\.com' => matched 
[rid#838dc88/initial] (4) [perdir /home/bob/http/] RewriteCond: input='/index.html' pattern='!^/%1.*' => matched 
[rid#838dc88/initial] (2) [perdir /home/bob/http/] rewrite 'index.html' -> '/gnome/index.html' 
[rid#838dc88/initial] (1) [perdir /home/bob/http/] internal redirect with /gnome/index.html [INTERNAL REDIRECT] 
[rid#8392f30/initial/redir#1] (3) [perdir /home/bob/http/] strip per-dir prefix: /home/bob/http/gnome/index.html -> gnome/index.html 
[rid#8392f30/initial/redir#1] (3) [perdir /home/bob/http/] applying pattern '^(.*)$' to uri 'gnome/index.html' 
[rid#8392f30/initial/redir#1] (4) [perdir /home/bob/http/] RewriteCond: input='gnome.bob.my-domain.com' pattern='^([^\.]+)\.bob\.my-domain\.com' => matched 
[rid#8392f30/initial/redir#1] (4) [perdir /home/bob/http/] RewriteCond: input='/gnome/index.html' pattern='!^/%1.*' => matched 
[rid#8392f30/initial/redir#1] (2) [perdir /home/bob/http/] rewrite 'gnome/index.html' -> '/gnome/gnome/index.html' 
[rid#8392f30/initial/redir#1] (1) [perdir /home/bob/http/] internal redirect with /gnome/gnome/index.html [INTERNAL REDIRECT] 
[rid#8397970/initial/redir#2] (3) [perdir /home/bob/http/] add path info postfix: /home/bob/http/gnome/gnome -> /home/bob/http/gnome/gnome/index.html 

Esto es sólo un fragmento, hay algunos 10 o 100 o más líneas de Apache reescritura básicamente a /gnome/index.html/gnome/gnome /gnome/gnome/gnome/index.html, etc antes de Apache llega a su límite de reescritura, se da por vencido, y tiros de error 500

+0

Agregué más información de los registros de reescritura, espero que alguien haya intentado esto antes, o tiene alguna información sobre cómo puedo hacer esto. Gracias chicos (y chicas) –

Respuesta

5

Después de algunos años de ignorar este problema y volver a en varios puntos, finalmente encontré una solución viable.

RewriteEngine on 
RewriteCond %{HTTP_HOST} ^([^.]+)\.bob\.my-domain\.com 
RewriteCond %1::%{REQUEST_URI} !^(.*?)::/\1/ 
RewriteRule ^(.*)$ /%1/$1 [L] 

Lo que encontré fue que las copias de referencias para RewriteCond direcciones anteriores no están disponibles en el parámetro ConditionPattern de futuros RewriteConditions. Si desea utilizar una referencia retrospectiva de una directiva anterior RewriteCond, solo puede usarla en el parámetro TestString.

Las directivas anteriores anteponen el subdominio coincidente en la directiva 1 RewriteCond al RequestURI, delimitado por ::. Lo que hacemos luego en el RewriteCond Cadena de prueba (regex) es volver a capturar el nombre del subdominio, luego verificamos que nuestro RequestURI real no comience con ese subdominio como una carpeta usando una referencia retrospectiva dentro del mismo regex .

Esto suena mucho más confuso de lo que realmente es, y no me puedo atribuir el mérito de descubrir la respuesta. Encontré la respuesta como respuesta a otra pregunta aquí, %N backreference inside RewriteCond. Gracias a Jon Lin por responder esa pregunta, y desconocido para él, ¡mi pregunta también!

+0

Solo una nota que tuve que eliminar el final/en el segundo RewriteCond para que funcione correctamente para mí. Pude cargar mi URL con ella (una instalación de gallery3), pero los recursos de CSS no se cargaban correctamente. Quitándose la barra posterior lo arregló. Parecía que terminaba con // en la URL con eso allí. – stuckj

0

Algunas preguntas:

dijiste "mapa interno" - uSTED NO ¿Quieres usar un redireccionamiento?

¿Está utilizando el mismo VirtualHost para gnome.bob.mysite.com y bob.mysite.com

¿Se acordó crear un ServerAlias ​​para *.bob.mysite.com?


Aquí hay una versión aproximada que puede modificar para que funcione. Capturará el subdominio y la URL solicitada, y redirigirá al dominio principal con el subdominio como la primera parte de la ruta, seguido de la ruta solicitada, seguida de la cadena de consulta.

ServerName www.mysite.com 
ServerAlias *.mysite.com 

RewriteCond %{HTTP_HOST} ^([a-zA-Z0-9-]+)\\.mysite.com$ 
RewriteRule ^/(.*)  http://www.mysite.com/%1/$1  [R=301,L]',  
+0

Definitivamente quiero una redirección interna. todo el propósito de esto es poder usar rutas absolutas en enlaces, css, img srcs, etc. Existe/habrá un host virtual para .my-site.com con un alias para *. .my-site.com, por lo que cualquier dominio solicitado de .my-site.com o inferior será recogido por ese vhost –

0

¿Ha intentado utilizar otra regla de reescritura para procesar la anterior?

RewriteEngine On 

RewriteCond %{HTTP_HOST}      ^([^.]+)\.bob\.my-domain\.com 
RewriteCond %{REQUEST_URI}      !^/%1.* 
RewriteRule ^(.*)$        /%1/$1 [C]  
RewriteRule ^/(.*)\.bob\.my-domain\.com/(.*) /$1/$2 [L] 

pero creo que el mayor problema es el hecho de que el servidor no entiende que se está servida con un nombre diferente.

Cree que se está ejecutando en el directorio/gnome/mientras el navegador funciona en el directorio /. Entonces, cualquier URL relativa que tengas va a causar problemas.

Lo que necesita es un filtro que ejecutará todas las URL de su página a través de un procesador y las cambiará de/gnome/a /.

+0

, la idea es desalentar las URL relativas, pero bajo esta estructura, también deberían funcionar. –

+0

también, estoy bastante seguro de que el host HTTP no se usa en RewriteRule, solo el URI –

Cuestiones relacionadas