# [SOLVED] Apache public&private vhosts w/ IP alias

## midnite

Thanks for coming in. i really need help. i have been working on it for days, digging into dozen pages of documentation and i still have no clue. And what even worst is, after i have just typed my question here, my browser needs restart so i have lost all what i have typed. Here's my re-type. This inspired me the importance of saving users' drafts when i build my own forum. Okay, we can discuss that later.

Here's my network construction:

- i have a domain http://www.mydomain.com pointing to my IP 12.34.56.78

- i have a router at 12.34.56.78

- i have several computers under my router and my server is at 192.168.0.2

- In my router setting, requests to port 80, 8080 (and some more else) are pointed to 192.168.0.2

- In my local computers, i have set in the hosts file that to resolve http://www.mydomain.com as 192.168.0.2

In my Apache, i want to have some virtual hosts for public access (worldwide, by http://www.mydomain.com) and some for private only (within local network, by 192.168.0.2)

What i want to achieve are:

Within local network, request to http://www.mydomain.com returns /www/public

Within local network, request to http://www.mydomain.com:8080 returns /www/private

Worldwide, request to http://www.mydomain.com returns /www/public

Worldwide, request to http://www.mydomain.com:8080 returns error as if such port is not open (most desirable), forbidden or anything else is also great (except /www/private of course  :Wink: )The simplest way is not to forward the port 8080 in my router setting. But sooner of later, i am planning to take away my router and put my server at 12.34.56.78

Got a solution already? If yes, you are really my STAR and please press "post reply" and share!! Don't scroll down and let my crap code to distract your brilliant idea  :Wink: 

Here's my Apache vhost's setting:

```
Listen 80

Listen 192.168.0.2:8080

NameVirtualHost *:80

<VirtualHost *:80>

        ServerName www.mydomain.com

        DocumentRoot "/www/public"

        <Directory "/www/public">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>

<VirtualHost 192.168.0.2:8080>

        ServerName www.mydomain.com

        DocumentRoot "/www/private"

        <Directory "/www/private">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>
```

With this setting, point 1, 2, 3 are satisfied. Yet accessing to http://www.mydomain.com:8080 from worldwide will also return /www/private!! (Point 4 failed)

i can change the second virtual host such that requests other than 192.168.0.x return forbidden:

```
<VirtualHost 192.168.0.2:8080>

        ServerName www.mydomain.com

        DocumentRoot "/www/private"

        <Directory "/www/private">

                Order deny,allow

                Deny from all

                Allow from 192.168.0.

        </Directory>

</VirtualHost>
```

But if i can achieve by only Listen, NameVirtualHost and <VirtualHost> directives, it will be more secure. And it should be faster also.

i tried to follow the example of IP-based virtual hosting, and change the Apache setting to:

```
Listen 80

<VirtualHost 12.34.56.78>

        ServerName www.mydomain.com

        DocumentRoot "/www/public"

        <Directory "/www/public">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>

<VirtualHost 192.168.0.2>

        ServerName www.mydomain.com

        DocumentRoot "/www/private"

        <Directory "/www/private">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>
```

However both requests to http://www.mydomain.com from external or internal returns /www/private. So i suspect if it is because of my router settings and let my server to treat all requests as 192.168.0.2 Yet i found in the access_log the %V argument (The server name according to the UseCanonicalName setting, in fact i dont know what "canonical name" means) are showing www.mydomain.com and 192.168.0.2 respectively (supposed to be working for IP-based?).

Really THANKS a lot!!!

Finally, some documentations and examples (i was digging into these days) for you quick references:

Apache Virtual Host documentation (index page) http://httpd.apache.org/docs/2.2/vhosts/

Name-based Virtual Host http://httpd.apache.org/docs/2.2/vhosts/name-based.html

IP-based virtual http://httpd.apache.org/docs/2.2/vhosts/ip-based.html (not much explained about the IP based)

VirtualHost Examples http://httpd.apache.org/docs/2.2/vhosts/examples.html (quite a lot of examples, but i still cant find my solution. Stupid me)

Directives:

Listen http://httpd.apache.org/docs/2.2/mod/mpm_common.html#listen

NameVirtualHost http://httpd.apache.org/docs/2.2/mod/core.html#namevirtualhost

<VirtualHost> http://httpd.apache.org/docs/2.2/mod/core.html#virtualhost

ServerName http://httpd.apache.org/docs/2.2/mod/core.html#servername

And, do we need these? i believe if the above works, it will be fine enough, for the sake of performance consideration.

Mapping URLs to Filesystem Locations http://httpd.apache.org/docs/2.2/urlmapping.html

mod_vhost_alias http://httpd.apache.org/docs/2.2/mod/mod_vhost_alias.html

Best wishes,

midnite

----------

## nokilli

Excellent help request.  I don't know that I can help on the vhost settings, but it does seem that mod_rewrite offers a simple way out of this predicament.

----------

## Mad Merlin

One important point that you seem to be missing at the moment, is that for both IP based virtual hosting and locking out users using the Listen directive, you need to have (at least) two distinct network connections on that machine, each with their own IPs. The easiest way to have two distinct network connections to a machine is to have two distinct network cards, both of which are plugged into the network simultaneously, but you can probably achieve similar results using IP aliasing[1] (where a single ethernet port takes on several IPs).

So, if you turn your server into your router as well, you'll probably have two network cords plugged into it, one which goes to the Internet, and one that goes to your LAN, and each will have a different IP address. In this case, you can have :8080 listen on the local IP only, and :80 listen on both. The situation is quite similar for IP aliasing, and is left as an exercise to the reader.

[1] http://gentoo-wiki.com/HOWTO_IP_Aliasing

----------

## xtz

U must decide whether to use name-based virtual hosting, or ip-based one. In the first case u don't need IP aliasing, as the virtual hosts work on one IP, in the second one u need an IP address for every virtual host u need.

----------

## midnite

Thanks nokilli for your suggestion  :Wink: 

Thanks Mad Merlin!! i really didn't know about that. i thought both IPs - 192.168.0.2 and 12.34.56.78 - can access my server, then i can use IP-based virtual hosting. i will study and try that later  :Wink: 

Thanks xtz for your reply  :Wink: 

i can't use both name-based and IP-based? i remember somewhere in the online documentation says it can: Name-based hosts on more than one IP address, Mixed port-based and ip-based virtual hosts, Mixed name-based and IP-based vhosts. But my situation is something like mixed IP-based, port-based and name based. i really don't know which (or none) is applicable to my case. Do you have any idea?

Best wishes,

midnite

----------

## Mad Merlin

 *midnite wrote:*   

> Thanks Mad Merlin!! i really didn't know about that. i thought both IPs - 192.168.0.2 and 12.34.56.78 - can access my server, then i can use IP-based virtual hosting. i will study and try that later 

 

They can, but because you're behind a NAT right now, when you access your server via 12.34.56.78, the router simply passes the data along to your system for you, at 192.168.0.2.

----------

## midnite

 *Mad Merlin wrote:*   

>  *midnite wrote:*   Thanks Mad Merlin!! i really didn't know about that. i thought both IPs - 192.168.0.2 and 12.34.56.78 - can access my server, then i can use IP-based virtual hosting. i will study and try that later  
> 
> They can, but because you're behind a NAT right now, when you access your server via 12.34.56.78, the router simply passes the data along to your system for you, at 192.168.0.2.

 Oops? i am quite confused. There's really a lot more for me to learn about networking. Do you mean when someone access my server via 12.34.56.78, my server will not know and it will only think requesting 192.168.0.2 by my router?

Really thanks a lot, guru  :Wink: 

----------

## Mad Merlin

 *midnite wrote:*   

>  *Mad Merlin wrote:*    *midnite wrote:*   Thanks Mad Merlin!! i really didn't know about that. i thought both IPs - 192.168.0.2 and 12.34.56.78 - can access my server, then i can use IP-based virtual hosting. i will study and try that later  
> 
> They can, but because you're behind a NAT right now, when you access your server via 12.34.56.78, the router simply passes the data along to your system for you, at 192.168.0.2. 
> 
> Oops? i am quite confused. There's really a lot more for me to learn about networking. Do you mean when someone access my server via 12.34.56.78, my server will not know and it will only think requesting 192.168.0.2 by my router?
> ...

 

Kinda sorta. Your server will know the remote address is foreignhost.com (or whatever it happens to be), but it won't know about the intermediate step it took to the router at 12.34.56.78, and thus, will have no way to differentiate between a local and a remote connection, except by guessing based on the remote address.

To clarify, your server may be accessable (on certain ports) via 12.34.56.78, but 12.34.56.78 is not an IP for your server, it is an IP for your router (as is 192.168.0.1, probably).

You might want to read up on NAT.

----------

## midnite

Thanks again Mad Merlin, i have studied http://gentoo-wiki.com/HOWTO_IP_Aliasing and http://en.wikipedia.org/wiki/Network_address_translation. i guess i understand how the mechanism works. What you meant i need IP Aliasing is that ....

What i understand is: (see if i am correct)

Requests are just like posting letters in the human world. IP addresses (and ports) are written on the envelopes as if postal addresses. When someone requests http://www.mydomain.com, 12.34.56.78 (with port 80) will be on the envelope. The letter reaches my router and will further forwarded to my server because of the post 80. Yet, before IP Aliasing, my server knows only itself is 192.168.0.2. So, what you meant i need IP Aliasing is that my server can recognize itself as 12.34.56.78 also. Then further process the request. Am i right?

i changed /etc/conf.d/net to:

```
config_eth0=( "192.168.0.2 netmask 255.255.255.0 brd 192.168.0.255"

              "12.34.56.78 netmask 255.255.255.0 brd 192.168.0.255" )

routes_eth0=( "default via 192.168.0.1" )
```

with my virtual hosts settings unchanged:

```
Listen 80

Listen 192.168.0.2:8080

NameVirtualHost *:80

<VirtualHost *:80>

        ServerName www.mydomain.com

        DocumentRoot "/www/public"

        <Directory "/www/public">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>

<VirtualHost 192.168.0.2:8080>

        ServerName www.mydomain.com

        DocumentRoot "/www/private"

        <Directory "/www/private">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>
```

After /etc/init.d/net.eth0 restart, sadly no surprises  :Sad:  What even worst is that i can not access my server outside my router anymore (inside is ok). No matter at which ports, simply wait and end up with connection timeout.

i noticed that said in the gentoo-wiki the above does not work on 2.6.15-gentoo-r5, so i tried this also (mine is linux-2.6.23-hardened-r7):

```
iface_eth0="192.168.0.2 netmask 255.255.255.0 brd 192.168.0.255"

gateway="eth0/192.168.0.1"

alias_eth0=("12.34.56.78")

broadcast_eth0=("192.168.0.255")

netmask_eth0=("255.255.255.0")
```

Yet i got this warning upon restart eth0

```
 * Starting eth0

 *   You are using a deprecated configuration syntax for eth0

 *   You are advised to read /etc/conf.d/net.example and upgrade it accordingly
```

And i see only 192.168.0.2 while ifconfig. So i guess i should stick to the previous syntax.

Then i altered my vhost settings a bit (just like the Mixed port-based and ip-based virtual hosts):

```
Listen 12.34.56.78:80

Listen 192.168.0.2:8080

<VirtualHost 12.34.56.78:80>

        ServerName www.mydomain.com

        DocumentRoot "/www/public"

        <Directory "/www/public">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>

<VirtualHost 192.168.0.2:8080>

        ServerName www.mydomain.com

        DocumentRoot "/www/private"

        <Directory "/www/private">

                Order allow,deny

                Allow from all

        </Directory>

</VirtualHost>
```

Now i can only access my server within my router network at port 8080 (port 80 is no longer ok). Yet requests from outside are still connection timeout.

Best wishes,

midnite

----------

## Mad Merlin

 *midnite wrote:*   

> 
> 
> ```
> 
> config_eth0=( "192.168.0.2 netmask 255.255.255.0 brd 192.168.0.255" 
> ...

 

Ah, you want another local IP for the alias on your server, not the external IP, trying to alias your external IP on another local machine won't work very well (and will probably give unpredictable results). So, your server should have primary IP of 192.168.0.2 and alias of 192.168.0.3. Then, forward port 80 and port 8080* on your router to 192.168.0.3, and have all of your local machines resolve www.mydomain.com to 192.168.0.2. Now you can listen on *:80 and 192.168.0.2:8080, and you'll only need named virtual hosting, which should look something vaguely like:

```

Listen 80

Listen 192.168.0.2:8080

NameVirtualHost *:80

NameVirtualHost *:8080

<VirtualHost *:80>

   ServerName www.mydomain.com

   DocumentRoot "/www/public"

   <Directory "/www/public">

      Order allow,deny

      Allow from all

   </Directory>

</VirtualHost>

<VirtualHost *:8080>

   ServerName www.mydomain.com

   DocumentRoot "/www/private"

   <Directory "/www/private">

      Order allow,deny

      Allow from all

   </Directory>

</VirtualHost>

```

This works because it simulates the situation you presumably will have soon after you remove your router, with two distinct connections, one of which leads to the Internet and the other of which leads to your local network. Requests from the Internet come to your server via 192.168.0.3, while requests to your server from the local network come to 192.168.0.2, and because your private vhost is only listening on 192.168.0.2, it's not visible to the outside world.

* Forwarding 8080 isn't strictly necessary, it's for testing that things are working correctly.

----------

## midnite

 *Mad Merlin wrote:*   

> This works because it simulates the situation you presumably will have soon after you remove your router, with two distinct connections, one of which leads to the Internet and the other of which leads to your local network. Requests from the Internet come to your server via 192.168.0.3, while requests to your server from the local network come to 192.168.0.2, and because your private vhost is only listening on 192.168.0.2, it's not visible to the outside world.

 very clear and it works very well!! Thanks a lot, Mad Merlin!!  :Wink: 

----------

