A computer as a webserver
I have an old computer at my home acting as a local server.
I’ve used it mainly as a backup solution with rsync, and recently I wanted to "host" other content.
While normally I am more than happy to use ssh
, sshfs
, and sftp
to see what’s on the machine, I wanted to provide some HTML pages with some information, in particular copies of webpages that do not exist anymore, wikis, and so on.
Choose a machine
More or less any machine can be used as a server; a computer, laptop, phone, raspberry… probably even the device you are using right now, it does not even need to be a separate machine.
Using a phone has the benefit that it has an integrated UPS solution (unless you removed the battery), but it might not be the friendliest environment (Android might kill your server just because it can 😑).
Any computer/laptop built in the last decade should be powerful enough to serve static pages, or even pages that require PHP, some other language used serverside, a database, and who knows what, as long as the number of users connecting to it is limited.
Choose a web server
The most used ones are probably The Apache HTTP Server Project and nginx, but there are other alternatives like caddy. In those notes, I am going to use lighttpd.
On Debian-based systems, install it with apt install lighttpd
, and you are ready to go.
Point your browser to localhost
, and if everything works correctly, you should see some content.
You can now edit the webpage at /var/www/html/index.html
.
Congratulations, you are a webmaster!
Warning ⚠️ | This is not a guide for setting up a public server. It is a short introduction for a home server, reachable from other machines on the same network, or just localhost. In particular, it does not handle securing your system, certificates, https, and so on. |
Reverse proxy
In my case, I did not only want to serve some content, I wanted to serve content from different services.
One of the services is kiwix
.
This software is mostly known for providing an easy-to-use system for downloading and viewing Wikipedia offline.
With kiwix-serve
(apt install kiwix-tools
), it is possible to start a process that listens at a given port; for example
kiwix-serve --port=2022 --library /home/ubackup/kiwix/library.xml
While kiwix-serve
is running, if you point your browser at localhost:2022
, you’ll see the content served by kiwix-serve
.
But I did not want to have multiple ports; who is going to remember that localhost:2022
is for the content served from kiwix?
Wouldn’t it be much better if localhost/kiwix
points to the content of kiwix?
This is what normally a Reverse proxy does.
Fortunately, lighttpd
supports this functionality out-of-the-box, without the need to install a separate program.
For configuring lighttpd
, create the file
# https://redmine.lighttpd.net/projects/lighttpd/wiki/Mod_proxy
server.modules += ( "mod_proxy" )
$HTTP["url"] =~ "^/kiwix" {
proxy.balance = "hash"
proxy.server = ( "" => ( ( "host" => "localhost", "port" => 2022 ) ) )
}
and after saving the file, execute
lighty-enable-mod kiwix
service lighttpd force-reload
Once lighttpd
has been reloaded, all requests beginning with kiwix
will be redirected to port 2022
.
Unfortunately, this is not enough.
The HTML page that can be downloaded at localhost/kiwix
, contains absolute URLs; for example /style.css
.
Thus even if the page can be reached, other resources, like images, CSS files, and JavaScript, will not load correctly, as theyr URL does not begin with kiwix
.
Fortunately kiwix-serve
has an appropriate flag: --urlRootLocation
Thus if one starts kiwix-serve
with
kiwix-serve --port=2022 --library /home/ubackup/kiwix/library.xml --urlRootLocation kiwix
At this point, all absolute URLs will begin with kiwix
, and lighttpd
can redirect all requests correctly.
Programmatically add wikis
For completeness, a quick description on how to add programmatically wikis.
Wikis can be download from the project website, wikimedia, archive.org and other places.
Once you have downloaded the zim
archive you are interested in, you can add it to a library with kiwix-manage
.
This library file is then used by kiwix-serve
.
mkdir /opt/kiwix
cd /opt/kiwix
wget https://download.kiwix.org/zim/wikipedia/wikipedia_en_all_mini_2024-01.zim
kiwix-manage ~/kiwix/library.xml add /opt/kiwix/wikipedia_en_all_mini_2024-01.zim
kiwix-serve --port=2022 --library ~/kiwix/library.xml --urlRootLocation kiwix
Start a service during boot
While lighttpd
installed from the Debian repository starts by default when the system starts, the same cannot be said for kiwix-serve
, and in general other services.
There are two main methods for starting a program during system boot: systemd
and cron
For systemd
, create a file similar to the following
[Unit]
Description=Serve all the ZIM files
[Service]
Restart=always
RestartSec=15
User=www-data
ExecStart=/usr/bin/kiwix-serve --port=2022 --library /home/ubackup/kiwix/library.xml --urlRootLocation kiwix
[Install]
WantedBy=multi-user.target
If your cron
supports @reboot
, it is possible to create a file similar to the following
# start kiwix-serve on boot
@reboot www-data /usr/bin/kiwix-serve --port=2022 --library /home/ubackup/kiwix/library.xml --urlRootLocation kiwix
In both cases, www-data
is the (non-login) account that executes your webserver (lighttpd, nginx, …) on Debian systems, so it sounds like a reasonable choice to use the same user for other services too.
PHP support
On Debian-based systems, install php-fpm
, and create the following file
<?php
phpinfo();
After saving it, point the browser to localhost/phpinfo.php
, it should load a page containing all information about the installed PHP version.
Directory listing
If you have a folder and want to make it navigable from a browser, you either need to create a webpage that lists the files or directories, or tell your server to do so for you.
In the case of lighttpd, for showing the content of a particular directory, it is possible to create a configuration file similar to
# https://redmine.lighttpd.net/projects/lighttpd/wiki/Mod_dirlisting
$HTTP["url"] =~ "^/data" {
dir-listing.activate = "enable"
dir-listing.encoding = "utf-8"
}
The documentation states that performance could be an issue, an alternate scalable approach would be to generate a static page when a file changes, it has also the advantage of providing a more granular control of the content of the page.
Redirects
It is not uncommon to define redirects on a server.
For example, you want to upgrade the connection to https, or you moved something on your host, but you still want to support old url and redirect to the new location, or you have a script that acts as router
The syntax
# https://redmine.lighttpd.net/projects/lighttpd/wiki/Mod_rewrite
server.modules += ( "mod_rewrite" )
url.rewrite-if-not-file = ( "/novagallery/.*" => "/novagallery/router.php" )
Change the document root location of the server from /var/www
/var/www
is owned by root
, which means that by default a "normal" user is not able to change any content without sudo
or admin privileges, which is not very practical for prototyping or testing things out.
The location of the directory can be configured in /etc/lighttpd/lighttpd.conf
, by changing the value of server.document-root
, which by default points to /var/www/html
An alternative approach would be to use a symlink or mount point, which has the advantage that it should work with all web servers.
You should ensure that the user www-data
can see the files in the new location, not only the user account for editing the content.
Do you want to share your opinion? Or is there an error, some parts that are not clear enough?
You can contact me anytime.