Turn a Raspberry Pi Into a Web Server

Chris Grime
5 min readJul 1, 2023

--

A few years ago this site was running off a Raspberry Pi in my room and it worked well! Over time I had to move my site over to a web hosting provider due to the internet provider I had. My connections slow upload speeds were not enough to reliably serve my site to visitors. I hope to one day bring my site back home to my own hardware in the future.

Every developer should be able to set up the hardware their applications will be running on so we will be walking through how to install a web server on a Raspberry Pi.

Installing Raspberry Pi Os Lite

I recommend starting with downloading the Raspberry Pi Imager https://www.raspberrypi.com/software/ this makes it easy to create an image and allows you to easily change some installation options and it works on Windows, Mac, and Linux.

The image I will be using is the Raspberry Pi Os Lite (64 Bit).
I like to use the tool to enable SSH, set up the wireless connection, and set the locale settings.

I choose the lite version for a few reasons. The Pi isn't very powerful in the first place I like to squeeze as much performance as possible out of it. Since I will be using SSH to connect to the Pi there isn’t a need to have a GUI running in the background.

Now the memory card can be put into the Pi and Raspberry Pi Os will boot. If the WiFi and SSH settings were set we can log in to the Pi on another computer through SSH. On Linux we can open up the terminal and run:

ssh username@host

for example:

ssh cgrime@192.168.0.182

You can find your Raspberry Pi’s IP from your router admin page. If you have a keyboard and screen connected to your pi, on your Pi, you can run

hostname -I

Installing the web server

There are a handful of web server application that can be used. Two of the most popular web server applications are Apache and NGINX. For my Pi server I chose NGINX. NGINX is full of features and performs better than Apache, which I find important when working with the constraints of the Raspberry Pi.

On the Pi run the following to install NGINX:

sudo apt install nginx

Now that NGINX is installed we can start the server and test that its running.

sudo systemctl start nginx
sudo systemctl enable php7.4-fpm.service

On another computer, in a web browser, go to the address of your Pi. For example my Pi’s IP is 192.168.0.182. I go to http://192.168.0.182/

Installing supporting software

Now if the plan is to use PHP or Node to run server side applications, those will need to be installed. PHP is a simple install while Node will require adding an additional repository.

sudo apt install php7.4 php7.4-fpm

curl -fsSL https://deb.nodesource.com/setup_current.x | sudo -E bash -
sudo apt install nodejs

Check that they are installed:

php -v
node -v

We should also install a database. I am choosing SQLite, since it is light weight

sudo apt install sqlite3

Lets test out the web server with a custom file. Make a directory and new file in the home folder. Replace <user> with the user on your Pi.

mkdir /home/<user>/testsite
sudo nano /home/<user>/testsite/index.php

Inside the file add <?php echo “hello world”; ?>

Next edit the configuration file

sudo nano /etc/nginx/sites-available/default

Change the following two lines from:

root /var/www/html;
index index.html index.htm index.nginx-debian.html;

to

root /home/<user>/testsite;
index index.html index.htm index.nginx-debian.html index.php;

and un-comment the following lines:

        location ~ \.php$ {
include snippets/fastcgi-php.conf;

# With php-fpm (or other unix sockets):
fastcgi_pass unix:/run/php/php7.4-fpm.sock;
# With php-cgi (or other tcp sockets):
# fastcgi_pass 127.0.0.1:9000;
}

Restart NGINX

sudo systemctl restart nginx

Now back in the web browser refresh the page.

Accessing the Server

To access the server from outside the local network a few steps need to be taken.

1. The Pi needs to have a static IP within the network.
2. Port forwarding needs to be enabled on the local network’s router
3. If the the internet connection being used does not have a static IP we need to have a way to update the DNS record of our domain so that the site knows where to find the Raspberry Pi.

To give the Raspberry Pi a static IP we need to gather some information. We need the network type of the Pi either wlan0 or eth0 depending on if the Pi is connected through WiFi or Ethernet. We need the IP of the Pi (192.168.0.128 in this example), the router IP (192.168.0.1 in my example), and the DNS IP which is typically the same as the router IP.

Once those are IPs are collected the Pi’s dhcpcd.conf needs to be edited

sudo nano /etc/dhcpcd.conf

Add the following lines:

face wlan0
static ip_address=<Pi's IP>
static routers=<Routers IP>
static domain_name_servers=<Dns IP>

example:

interface wlan0
static ip_address=192.168.0.128/24
static routers=192.168.0.1
static domain_name_servers=192.168.0.1

Reboot the Pi and check the IP. It should be the IP set. You may also need to set the static IP for the Pi in the router admin settings as well.

Additionally in the router admin settings, Port Forwarding needs to be enabled. Port 80 for regular web traffic and port 443 for ssl encrypted traffic needs to be forwarded to the Raspberry Pi. Now regular requests to the networks public IP will be forwarded to the Pi and will display the Hello World page that was perviously set up.

Lastly, we want to set up a domain names so when users go to domain.com they can see whatever the Raspberry Pi is hosting. The DNS settings for the domain name need to be set up at the domain registrar to point users to the Pi.

Most home networks do not have a static IP. The IP can actually be changed overtime. If the network the Pi is on is not static then there needs to be a way to update the DNS record of whereever the Pi is located. Previously I used a service called noip to do that. Now I use a script that makes use of my domain registrars API to update the DNS settings when my public IP changes. Either method works great. A guide for setting up noip]

Now the Raspberry Pi has been put to a good use as a complete web server!

Picture credit: Harrison Broadbent

--

--