Difference between revisions of "Lighttpd"

From ArchWiki
Jump to: navigation, search
(Added link to the lighttpd docs, thus explaining why a default ssl.pemfile is required for SNI. Reformatted code examples.)
m (Enabling https via SSL: codeline)
 
(63 intermediate revisions by 31 users not shown)
Line 1: Line 1:
 +
[[Category:Web server]]
 
[[cs:Lighttpd]]
 
[[cs:Lighttpd]]
 
[[de:Lighttpd]]
 
[[de:Lighttpd]]
 
[[es:Lighttpd]]
 
[[es:Lighttpd]]
 +
[[ja:Lighttpd]]
 
[[ru:Lighttpd]]
 
[[ru:Lighttpd]]
 
[[zh-CN:Lighttpd]]
 
[[zh-CN:Lighttpd]]
 
[[zh-TW:Lighttpd]]
 
[[zh-TW:Lighttpd]]
[[Category:Web Server]]
 
 
 
[http://www.lighttpd.net/ Lighttpd] is "a secure, fast, compliant, and very flexible [[Wikipedia:Web server|web-server]] that has been optimized for high-performance environments. It has a very low memory footprint compared to other webservers and takes care of cpu-load. Its advanced feature-set ([[Wikipedia:FastCGI|FastCGI]], [[Wikipedia:Common Gateway Interface|CGI]], Auth, Output-Compression, URL-Rewriting and many more) make lighttpd the perfect webserver-software for every server that suffers load problems."
 
[http://www.lighttpd.net/ Lighttpd] is "a secure, fast, compliant, and very flexible [[Wikipedia:Web server|web-server]] that has been optimized for high-performance environments. It has a very low memory footprint compared to other webservers and takes care of cpu-load. Its advanced feature-set ([[Wikipedia:FastCGI|FastCGI]], [[Wikipedia:Common Gateway Interface|CGI]], Auth, Output-Compression, URL-Rewriting and many more) make lighttpd the perfect webserver-software for every server that suffers load problems."
  
 
==Installation==
 
==Installation==
Install the {{pkg|lighttpd}} package from the official repositories.
+
[[Install]] the {{pkg|lighttpd}} package.
  
 
==Configuration==
 
==Configuration==
===Basic Setup===
+
===Basic setup===
 
The lighttpd configuration file is: {{ic|/etc/lighttpd/lighttpd.conf}}. By default it should produce a working test page.  
 
The lighttpd configuration file is: {{ic|/etc/lighttpd/lighttpd.conf}}. By default it should produce a working test page.  
  
Line 20: Line 20:
 
  $ lighttpd -t -f /etc/lighttpd/lighttpd.conf
 
  $ lighttpd -t -f /etc/lighttpd/lighttpd.conf
  
The default configuration file specifies {{ic|/srv/http/}} as the document directory served.
+
The default configuration file specifies {{ic|/srv/http/}} as the document directory served. To test the installation, create a dummy file:
  
It may be necessary to add a user and group for {{ic|http}} if you do not already have one. That user needs to have write permissions to {{ic|/var/log/lighttpd}} as well, so we will make it the owner of the folder:
+
{{hc|/srv/http/index.html|Hello world!}}
# groupadd http
+
# useradd http
+
# chown -R http /var/log/lighttpd
+
  
To test the install:
+
Then [[start/enable]] the {{ic|lighttpd.service}} and point your browser to {{ic|localhost}}, where you should see the test page.
# echo 'TestMe!' >> /srv/http/index.html
+
# chmod 755 /srv/http/index.html
+
  
To start the server:
+
Example configuration files are available in {{ic|/usr/share/doc/lighttpd/}}.
# systemctl start lighttpd
+
  
Then point your browser to {{ic|localhost}}, and you should see the test page.
+
==== Basic logging ====
 +
Lighttpd can write out both errors and access to log files.  To enabled both or of the logging options, simply edit {{ic|/etc/lighttpd/lighttpd.conf}} as follows:
 +
server.modules = (
 +
    "mod_access",
 +
    "mod_accesslog",
 +
)
 +
 +
server.errorlog  = "/var/log/lighttpd/error.log"
 +
accesslog.filename = "/var/log/lighttpd/access.log"
  
To start the server on every boot:
+
==== Enabling https via SSL ====
  
# systemctl enable lighttpd
+
{{Warning|Users planning to implementing SSL/TLS, should know that some variations and implementations are [https://weakdh.org/#affected still] [[wikipedia:Transport_Layer_Security#Attacks_against_TLS.2FSSL|vulnerable to attack]]. For details on these current vulnerabilities within SSL/TLS and how they apply to Lighttpd and other services (such as email) visit http://disablessl3.com/ and https://weakdh.org/sysadmin.html}}
  
Example configuration files are available in {{ic|/usr/share/doc/lighttpd/}}.
+
Self-signed SSL Certificates can be generated assuming {{Pkg|openssl}} is installed on the system as follows:
 +
# mkdir /etc/lighttpd/certs
 +
# openssl req -x509 -nodes -days 7300 -newkey rsa:2048 -sha256 -keyout /etc/lighttpd/certs/server.pem -out /etc/lighttpd/certs/server.pem
 +
# chmod 600 /etc/lighttpd/certs/server.pem
 +
 
 +
Modify {{ic|/etc/lighttpd/lighttpd.conf}} adding the following lines to enable https:
 +
$SERVER["socket"] == ":443" {
 +
    ssl.engine                  = "enable"
 +
    ssl.pemfile                = "/etc/lighttpd/certs/server.pem"
 +
  }
 +
 
 +
==== Password protecting a directory ====
 +
 
 +
A passwd file which is lighttpd's equivalent to the system's {{ic|/etc/passwd}} is needed for user authentication.  The setup requires a specific format and md5sum hashed password but users can quickly and easily create an entry using the following as an example:
 +
 
 +
$ user=foo
 +
$ password=b@R102
 +
$ realm='Password Required'
 +
$ hash=`echo -n "$user:$realm:$pass" | md5sum | cut -b -32`
 +
 +
# echo "$user:$realm:$hash" >> /etc/lighttpd/lighttpd.user
 +
 
 +
Modify {{ic|/etc/lighttpd/lighttpd.conf}} adding the following lines to enable the directory protection:
 +
 
 +
server.modules = (
 +
    "mod_auth",
 +
  )
 +
 +
auth.debug = 2
 +
auth.backend                = "htdigest"
 +
auth.backend.htdigest.userfile = "/etc/lighttpd/lighttpd.user"
 +
 +
# note this entry is relative to the server.document-root
 +
auth.require = ( "/secret" =>
 +
    (
 +
    "method" => "basic",
 +
    "realm" => "Password Required",
 +
    "require" => "user=foo"
 +
    )
 +
)
 +
 
 +
{{Note|The realm and user entered into {{ic|/etc/lighttpd/lighttpd.conf}} must match the values chosen in {{ic|/etc/lighttpd/lighttpd.user}} for authentication to work.}}
 +
===CGI===
 +
 
 +
[[Wikipedia:Common Gateway Interface|Common Gateway Interface]] (CGI) scripts work with Lighttpd out of box, you just need to enable the CGI module, include the configuration file and make sure your chosen programming language interpreter is installed. (i.e. for python you would install {{pkg|python}})
 +
 
 +
Create the file {{ic|/etc/lighttpd/conf.d/cgi.conf}} Add the following to it:
 +
 
 +
server.modules += ( "mod_cgi" )
 +
 +
cgi.assign                = ( ".pl"  => "/usr/bin/perl",
 +
                                ".cgi" => "/usr/bin/perl",
 +
                                ".rb"  => "/usr/bin/ruby",
 +
                                ".erb" => "/usr/bin/eruby",
 +
                                ".py"  => "/usr/bin/python",
 +
                                ".php" => "/usr/bin/php-cgi" )
 +
 +
index-file.names          += ( "index.pl",  "default.pl",
 +
                                "index.rb",  "default.rb",
 +
                                "index.erb",  "default.erb",
 +
                                "index.py",  "default.py",
 +
                                "index.php",  "default.php" )
 +
 
 +
For PHP scripts you will need to make sure the following is set in {{ic|/etc/php/php.ini}}
 +
cgi.fix_pathinfo = 1
 +
 
 +
In your Lighttpd configuration file, {{ic|/etc/lighttpd/lighttpd.conf}} add:
 +
include "conf.d/cgi.conf"
  
 
===FastCGI===
 
===FastCGI===
Line 46: Line 115:
 
Install {{pkg|fcgi}}.
 
Install {{pkg|fcgi}}.
 
Now you have lighttpd with fcgi support. If it was that what you wanted you are all set. People that want Ruby on Rails, PHP or Python should continue.
 
Now you have lighttpd with fcgi support. If it was that what you wanted you are all set. People that want Ruby on Rails, PHP or Python should continue.
{{Box Note | New default user and group: Instead of group "nobody" lighttpd now runs as user/group "http" by default.}}
+
{{Note| New default user and group: Instead of group {{ic|nobody}} lighttpd now runs as user/group {{ic|http}} by default.}}
  
 
First copy the example config file form {{ic|/usr/share/doc/lighttpd/config/conf.d/fastcgi.conf}} to {{ic|/etc/lighttpd/conf.d}}
 
First copy the example config file form {{ic|/usr/share/doc/lighttpd/config/conf.d/fastcgi.conf}} to {{ic|/etc/lighttpd/conf.d}}
Line 83: Line 152:
 
If you get a similar output then php is installed correctly.
 
If you get a similar output then php is installed correctly.
  
{{Note|Please keep in mind if you receive errors like ''No input file found'' after attempting to access your php files then make sure {{ic|/etc/php/php.ini}} has the directives enabled:}}
+
Create a new configuration file:
cgi.fix_pathinfo=1
+
open_basedir = /srv/http/:/home/:/tmp/:/usr/share/pear/:/another/path:/second/path
+
And that the files are world readable,
+
# chmod -R 755
+
  
In {{ic|/etc/lighttpd/conf.d/fastcgi.conf}} add:
+
{{hc|/etc/lighttpd/conf.d/fastcgi.conf|<nowiki>
server.modules += ( "mod_fastcgi" )
+
# Make sure to install php and php-cgi. See:                                                           
+
# https://wiki.archlinux.org/index.php/Fastcgi_and_lighttpd#PHP
#server.indexfiles += ( "index.php" ) #this is deprecated
+
index-file.names += ( "index.php" )
+
+
fastcgi.server = (
+
    ".php" => (
+
      "localhost" => (
+
        "bin-path" => "/usr/bin/php-cgi",
+
        "socket" => "/run/lighttpd/php-fastcgi.sock",
+
        "max-procs" => 4, # default value
+
        "bin-environment" => (
+
          "PHP_FCGI_CHILDREN" => "1", # default value
+
        ),
+
        "broken-scriptfilename" => "enable"
+
      ))
+
)
+
  
Then in {{ic|/etc/lighttpd/lighttpd.conf}}:
+
server.modules += ("mod_fastcgi")
include "conf.d/fastcgi.conf"
+
  
Finally reload the configuration
+
# FCGI server
# systemctl reload lighttpd
+
# ===========
 +
#
 +
# Configure a FastCGI server which handles PHP requests.
 +
#
 +
index-file.names += ("index.php")
 +
fastcgi.server = (
 +
    # Load-balance requests for this path...
 +
    ".php" => (
 +
        # ... among the following FastCGI servers. The string naming each
 +
        # server is just a label used in the logs to identify the server.
 +
        "localhost" => (
 +
            "bin-path" => "/usr/bin/php-cgi",
 +
            "socket" => "/tmp/php-fastcgi.sock",
 +
            # breaks SCRIPT_FILENAME in a way that PHP can extract PATH_INFO
 +
            # from it
 +
            "broken-scriptfilename" => "enable",
 +
            # Launch (max-procs + (max-procs * PHP_FCGI_CHILDREN)) procs, where
 +
            # max-procs are "watchers" and the rest are "workers". See:
 +
            # https://redmine.lighttpd.net/projects/1/wiki/frequentlyaskedquestions#How-many-php-CGI-processes-will-lighttpd-spawn
 +
            "max-procs" => 4, # default value
 +
            "bin-environment" => (
 +
                "PHP_FCGI_CHILDREN" => "1" # default value
 +
            )
 +
        )
 +
    ) 
 +
)
 +
</nowiki>}}
 +
 
 +
Make lighttpd use the new configuration file:
 +
 
 +
{{hc|/etc/lighttpd/lighttpd.conf|
 +
include "conf.d/fastcgi.conf"
 +
}}
 +
 
 +
{{Note|Remember that the order in which the modules are loaded is important, the correct order is listed in {{ic|/usr/share/doc/lighttpd/config/modules.conf}}. Any misconfiguration may cause ''lighttpd'' to crash.}}
 +
 
 +
[[Reload]] lighttpd.
 +
 
 +
{{Note|
 +
* If you receive errors like ''No input file found'' when attempting to access php files, there are several possible explanations. See [http://redmine.lighttpd.net/projects/1/wiki/frequentlyaskedquestions#I-get-the-error-No-input-file-specified-when-trying-to-use-PHP this FAQ] for more information.
 +
* Make sure that no other module (e.g. {{ic|mod_cgi}}) will try to handle the ''.php'' extension.
 +
}}
  
 
===== Using php-fpm =====
 
===== Using php-fpm =====
  
There is no adaptive spawning anymore in recent lighttpd releases. For dynamic management of PHP processes, you can use {{Pkg|php-fpm}}.
+
There is no adaptive spawning anymore in recent lighttpd releases. For dynamic management of PHP processes, you can install {{Pkg|php-fpm}} and then [[start]] and enable {{ic|php-fpm.service}}.
# pacman -S php-fpm
+
 
# rc.d start php-fpm
+
{{Note|You can configure the number of servers in the pool and tweak other configuration options by editing the file {{ic|/etc/php/php-fpm.conf}}.  More details on ''php-fpm'' can be found on the [http://php-fpm.org/ php-fpm website]. Remember that when you make changes to {{ic|/etc/php/php.ini}} you will need to restart {{ic|php-fpm.service}}.}}
{{Note|You can configure the number of servers in the pool and tweak other configuration options by editing the file {{ic|/etc/php/php-fpm.conf}}.  More details on ''php-fpm'' can be found on the [http://php-fpm.anight.org/ php-fpm website]. You should also note that when you make changes to /etc/php/php.ini you will need to restart php-fpm}}
+
  
 
In {{ic|/etc/lighttpd/conf.d/fastcgi.conf}} add:
 
In {{ic|/etc/lighttpd/conf.d/fastcgi.conf}} add:
Line 136: Line 225:
 
===== eAccelerator =====
 
===== eAccelerator =====
  
Install {{AUR|eaccelerator}} from the [[Arch User Repository|AUR]].
+
{{Note|As of November 2014, {{AUR|eaccelerator}}{{Broken package link|{{aur-mirror|eaccelerator}}}} cannot be compiled.}}
 +
 
 +
Install {{AUR|eaccelerator}}{{Broken package link|{{aur-mirror|eaccelerator}}}}.
  
 
Add own config file for eaccelerator:
 
Add own config file for eaccelerator:
Line 149: Line 240:
  
 
===== Try a php page =====
 
===== Try a php page =====
Create the following php page, name it index.php, and place a copy in both /srv/http/ and /srv/http-ssl/html/
+
Create the following php page, name it {{ic|index.php}}, and place a copy in both {{ic|/srv/http/}} and {{ic|/srv/http-ssl/html/}}
 
  <?php
 
  <?php
 
  phpinfo();
 
  phpinfo();
Line 166: Line 257:
 
Install and configure FastCGI (see [[#FastCGI]] above).
 
Install and configure FastCGI (see [[#FastCGI]] above).
  
Install [[ruby]] from [extra] and {{AUR|ruby-fcgi}} from [[AUR]].
+
Install [[ruby]] from [[official repositories]] and {{AUR|ruby-fcgi}}{{Broken package link|{{aur-mirror|ruby-fcgi}}}} from [[AUR]].
  
 
Follow instructions on [[RubyOnRails]].
 
Follow instructions on [[RubyOnRails]].
  
 
==== Python FastCGI ====
 
==== Python FastCGI ====
 +
{{Note|This method will not work with Python 3 because ''Flup'' library is only available for Python 2. If you want to use Python 3, you should refer to [[#CGI]] section.}}
 
Install and configure FastCGI (see [[#FastCGI]] above).
 
Install and configure FastCGI (see [[#FastCGI]] above).
  
Install flup:
+
Install {{Pkg|python2-flup}}.
# pacman -S python2-flup
+
 
 
Configure:
 
Configure:
 
  fastcgi.server = (
 
  fastcgi.server = (
Line 188: Line 280:
 
     )
 
     )
 
  )
 
  )
Put the test.py in the root of your server (don't forget to chmod +x it)
+
Put the test.py in the root of your server (do not forget to chmod +x it)
  
 
{{bc|1=
 
{{bc|1=
Line 205: Line 297:
 
[https://bbs.archlinux.org/viewtopic.php?pid=734173#p734173 Thanks to firecat53 for his explanation]
 
[https://bbs.archlinux.org/viewtopic.php?pid=734173#p734173 Thanks to firecat53 for his explanation]
  
=== SSL ===
+
===== Server name indication =====
Generate an SSL Cert, e.g. like that:
+
# mkdir /etc/lighttpd/certs
+
# openssl req -x509 -nodes -days 7300 -newkey rsa:2048 -keyout /etc/lighttpd/certs/www.example.com.pem -out /etc/lighttpd/certs/www.example.com.pem
+
# chmod 600 /etc/lighttpd/certs/www.example.com.pem
+
  
Edit {{ic|/etc/lighttpd/lighttpd.conf}}.
+
To use [[wikipedia:Server_Name_Indication|SNI]] with lighttpd, simply put additional ssl.pemfile configuration directives inside host conditionals. A default ssl.pemfile is [https://redmine.lighttpd.net/projects/1/wiki/Docs_SSL#Server-Name-Indication-SNI still required].
To make lighttpd SSL-only (you probably need to set the server port to 443 as well)
+
ssl.engine = "enable"
+
ssl.pemfile = "/etc/lighttpd/certs/www.example.com.pem"
+
To enable SSL in addition to normal HTTP
+
$SERVER["socket"] == ":443" {
+
    ssl.engine                  = "enable"
+
    ssl.pemfile                = "/etc/lighttpd/certs/www.example.com.pem"
+
  }
+
If you want to serve different sites, you can change the document root inside the socket conditional:
+
$SERVER["socket"] == ":443" {
+
    server.document-root = "/srv/ssl" # use your ssl directory here
+
    ssl.engine                = "enable"
+
    ssl.pemfile                = "/etc/lighttpd/certs/www.example.com.pem"  # use the path where you created your pem file
+
  }
+
or as alternative you can use the scheme conditional to distinguish between secure and normal requests.
+
$HTTP["scheme"] == "https" {
+
    server.document-root = "/srv/ssl" # use your ssl directory here
+
    ssl.engine                = "enable"
+
    ssl.pemfile                = "/etc/lighttpd/certs/www.example.com.pem"  # use the path where you created your pem file
+
  }
+
Note that you cannot use the scheme conditional around ssl.engine above, since lighttpd needs to know on what port to enable SSL.
+
 
+
===== Server Name Indication =====
+
 
+
To use [http://en.wikipedia.org/wiki/Server_Name_Indication SNI] with lighttpd, simply put additional ssl.pemfile configuration directives inside host conditionals. A default ssl.pemfile is [https://redmine.lighttpd.net/projects/1/wiki/Docs_SSL#Server-Name-Indication-SNI still required].
+
  
 
  $HTTP["host"] == "www.example.org" {
 
  $HTTP["host"] == "www.example.org" {
Line 246: Line 309:
 
  }
 
  }
  
==== Redirect HTTP requests to HTTPS ====
+
==== Redirect http requests to https ====
You should add "mod_redirect" in server.modules array in {{ic|/etc/lighttpd/lighttpd.conf}}:
+
You should add {{ic|"mod_redirect"}} in server.modules array in {{ic|/etc/lighttpd/lighttpd.conf}}:
server.modules += ( "mod_redirect" )
+
 
+
{{bc|<nowiki>
$SERVER["socket"] == ":80" {
+
server.modules += ( "mod_redirect" )
  $HTTP["host"] =~ "example.org" {
+
 
    url.redirect = ( "^/(.*)" => "https://example.org/$1" )
+
$SERVER["socket"] == ":80" {
    server.name                = "example.org"  
+
  $HTTP["host"] =~ "example.org" {
  }
+
    url.redirect = ( "^/(.*)" => "https://example.org/$1" )
}
+
    server.name                = "example.org"  
+
  }
$SERVER["socket"] == ":443" {
+
}
  ssl.engine = "enable"  
+
 
  ssl.pemfile = "/etc/lighttpd/ssl/server.pem"  
+
$SERVER["socket"] == ":443" {
  server.document-root = "..."  
+
  ssl.engine = "enable"  
}
+
  ssl.pemfile = "/etc/lighttpd/ssl/server.pem"  
 +
  server.document-root = "..."  
 +
}
 +
</nowiki>}}
  
 
To redirect all hosts to their secure equivalents use the following in place of the socket 80 configuration above:
 
To redirect all hosts to their secure equivalents use the following in place of the socket 80 configuration above:
$SERVER["socket"] == ":80" {
+
 
  $HTTP["host"] =~ "(.*)" {
+
{{bc|<nowiki>
    url.redirect = ( "^/(.*)" => "https://%1/$1" )
+
$SERVER["socket"] == ":80" {
  }
+
  $HTTP["host"] =~ ".*" {
}
+
    url.redirect = (".*" => "https://%0$0")
 +
  }
 +
}
 +
</nowiki>}}
  
 
To redirect all hosts for part of the site (e.g. secure or phpmyadmin):
 
To redirect all hosts for part of the site (e.g. secure or phpmyadmin):
$SERVER["socket"] == ":80" {
 
  $HTTP["url"] =~ "^/secure" {
 
    url.redirect = ( "^/(.*)" => "https://example.com/$1" )
 
  }
 
}
 
  
=== Output Compression ===
+
{{bc|<nowiki>
 +
$SERVER["socket"] == ":80" {
 +
  $HTTP["url"] =~ "^/secure" {
 +
    url.redirect = ( "^/(.*)" => "https://example.com/$1" )
 +
  }
 +
}
 +
</nowiki>}}
 +
 
 +
=== Output compression ===
  
 
In {{ic|/etc/lighttpd/lighttpd.conf}} add
 
In {{ic|/etc/lighttpd/lighttpd.conf}} add
Line 289: Line 361:
 
Add following in {{ic|/etc/lighttpd/lighttpd.conf}}:
 
Add following in {{ic|/etc/lighttpd/lighttpd.conf}}:
 
  include "conf.d/compress.conf"
 
  include "conf.d/compress.conf"
{{Box Note | You can not do this (copy compress.conf) and add a needed content in {{ic|/etc/lighttpd/lighttpd.conf}} instead.}}
+
{{Note| You can not do this (copy compress.conf) and add a needed content in {{ic|/etc/lighttpd/lighttpd.conf}} instead.}}
 
+
==Troubleshooting==
+
=== Lighttpd downloads .php files ===
+
If lighttpd downloads {{ic|.php}} files instead of "initializing" them you probably missed to add these lines to your {{ic|/etc/lighttpd/lighttpd.conf}}.
+
 
+
{{bc|1=
+
server.modules = (
+
                  "mod_fastcgi",
+
                )
+
 
+
fastcgi.server = ( ".php" => ((
+
                    "bin-path" => "/usr/bin/php-cgi", #depends where your php-cgi has been installed. Default here.
+
                    "socket" => "/tmp/php.socket",
+
                    "max-procs" => 2,
+
                    "bin-environment" => (
+
                      "PHP_FCGI_CHILDREN" => "16",
+
                      "PHP_FCGI_MAX_REQUESTS" => "10000"
+
                    ),
+
                    "bin-copy-environment" => (
+
                      "PATH", "SHELL", "USER"
+
                    ),
+
                    "broken-scriptfilename" => "enable"
+
                )))
+
 
+
}}
+
 
+
=== Styles (CSS) not working properly ===
+
The default lighttpd config does not include a mimetype definition for CSS so when standards compliant browsers get text/html instead of text/css they get confused and nothing displays properly. To fix this add an entry for CSS.
+
 
+
{{bc|1=
+
mimetype.assign = (
+
  ".html" => "text/html",
+
  ".txt" => "text/plain",
+
  ".jpg" => "image/jpeg",
+
  ".png" => "image/png",
+
  ".css" => "text/css",
+
  "" => "application/octet-stream"
+
)
+
}}
+
New lines are not needed and are only used here for readability.
+
 
+
Note: The "application/octet-stream" declaration must be at the end. It is a catch-all, and any declarations after it will be ignored.
+
  
 
== See also ==
 
== See also ==
 
* [http://redmine.lighttpd.net/projects/lighttpd/wiki Lighttpd wiki]
 
* [http://redmine.lighttpd.net/projects/lighttpd/wiki Lighttpd wiki]

Latest revision as of 14:40, 26 June 2016

Lighttpd is "a secure, fast, compliant, and very flexible web-server that has been optimized for high-performance environments. It has a very low memory footprint compared to other webservers and takes care of cpu-load. Its advanced feature-set (FastCGI, CGI, Auth, Output-Compression, URL-Rewriting and many more) make lighttpd the perfect webserver-software for every server that suffers load problems."

Installation

Install the lighttpd package.

Configuration

Basic setup

The lighttpd configuration file is: /etc/lighttpd/lighttpd.conf. By default it should produce a working test page.

To check your lighttpd.conf for bugs you can use this command - helps finding misconfigurations very fast:

$ lighttpd -t -f /etc/lighttpd/lighttpd.conf

The default configuration file specifies /srv/http/ as the document directory served. To test the installation, create a dummy file:

/srv/http/index.html
Hello world!

Then start/enable the lighttpd.service and point your browser to localhost, where you should see the test page.

Example configuration files are available in /usr/share/doc/lighttpd/.

Basic logging

Lighttpd can write out both errors and access to log files. To enabled both or of the logging options, simply edit /etc/lighttpd/lighttpd.conf as follows:

server.modules = (
   "mod_access",
   "mod_accesslog",
)

server.errorlog   = "/var/log/lighttpd/error.log"
accesslog.filename = "/var/log/lighttpd/access.log"

Enabling https via SSL

Warning: Users planning to implementing SSL/TLS, should know that some variations and implementations are still vulnerable to attack. For details on these current vulnerabilities within SSL/TLS and how they apply to Lighttpd and other services (such as email) visit http://disablessl3.com/ and https://weakdh.org/sysadmin.html

Self-signed SSL Certificates can be generated assuming openssl is installed on the system as follows:

# mkdir /etc/lighttpd/certs
# openssl req -x509 -nodes -days 7300 -newkey rsa:2048 -sha256 -keyout /etc/lighttpd/certs/server.pem -out /etc/lighttpd/certs/server.pem
# chmod 600 /etc/lighttpd/certs/server.pem

Modify /etc/lighttpd/lighttpd.conf adding the following lines to enable https:

$SERVER["socket"] == ":443" {
    ssl.engine                  = "enable" 
    ssl.pemfile                 = "/etc/lighttpd/certs/server.pem" 
 }

Password protecting a directory

A passwd file which is lighttpd's equivalent to the system's /etc/passwd is needed for user authentication. The setup requires a specific format and md5sum hashed password but users can quickly and easily create an entry using the following as an example:

$ user=foo
$ password=b@R102
$ realm='Password Required'
$ hash=`echo -n "$user:$realm:$pass" | md5sum | cut -b -32`

# echo "$user:$realm:$hash" >> /etc/lighttpd/lighttpd.user

Modify /etc/lighttpd/lighttpd.conf adding the following lines to enable the directory protection:

server.modules = (
   "mod_auth",
 )

auth.debug = 2
auth.backend                = "htdigest"
auth.backend.htdigest.userfile = "/etc/lighttpd/lighttpd.user"

# note this entry is relative to the server.document-root
auth.require = ( "/secret" =>
   (
    "method" => "basic",
    "realm" => "Password Required",
    "require" => "user=foo"
   )
)
Note: The realm and user entered into /etc/lighttpd/lighttpd.conf must match the values chosen in /etc/lighttpd/lighttpd.user for authentication to work.

CGI

Common Gateway Interface (CGI) scripts work with Lighttpd out of box, you just need to enable the CGI module, include the configuration file and make sure your chosen programming language interpreter is installed. (i.e. for python you would install python)

Create the file /etc/lighttpd/conf.d/cgi.conf Add the following to it:

server.modules += ( "mod_cgi" )

cgi.assign                 = ( ".pl"  => "/usr/bin/perl",
                               ".cgi" => "/usr/bin/perl",
                               ".rb"  => "/usr/bin/ruby",
                               ".erb" => "/usr/bin/eruby",
                               ".py"  => "/usr/bin/python",
                               ".php" => "/usr/bin/php-cgi" )

index-file.names           += ( "index.pl",   "default.pl",
                               "index.rb",   "default.rb",
                               "index.erb",  "default.erb",
                               "index.py",   "default.py",
                               "index.php",  "default.php" )

For PHP scripts you will need to make sure the following is set in /etc/php/php.ini

cgi.fix_pathinfo = 1

In your Lighttpd configuration file, /etc/lighttpd/lighttpd.conf add:

include "conf.d/cgi.conf"

FastCGI

Install fcgi. Now you have lighttpd with fcgi support. If it was that what you wanted you are all set. People that want Ruby on Rails, PHP or Python should continue.

Note: New default user and group: Instead of group nobody lighttpd now runs as user/group http by default.

First copy the example config file form /usr/share/doc/lighttpd/config/conf.d/fastcgi.conf to /etc/lighttpd/conf.d

The following needs adding to the config file, /etc/lighttpd/conf.d/fastcgi.conf

server.modules += ( "mod_fastcgi" )

#server.indexfiles += ( "dispatch.fcgi" ) #this is deprecated
index-file.names += ( "dispatch.fcgi" ) #dispatch.fcgi if rails specified

server.error-handler-404   = "/dispatch.fcgi" #too
fastcgi.server = (
    ".fcgi" => (
      "localhost" => ( 
        "socket" => "/run/lighttpd/rails-fastcgi.sock",
        "bin-path" => "/path/to/rails/application/public/dispatch.fcgi"
      )
    )
)

Then in /etc/lighttpd/lighttpd.conf:

include "conf.d/fastcgi.conf"

For PHP or Ruby on Rails see the next sections.

PHP

Install php and php-cgi (see also PHP and LAMP).

Check that php-cgi is working php-cgi --version

PHP 5.4.3 (cgi-fcgi) (built: May  8 2012 17:10:17)
Copyright (c) 1997-2012 The PHP Group
Zend Engine v2.4.0, Copyright (c) 1998-2012 Zend Technologies

If you get a similar output then php is installed correctly.

Create a new configuration file:

/etc/lighttpd/conf.d/fastcgi.conf
# Make sure to install php and php-cgi. See:                                                             
# https://wiki.archlinux.org/index.php/Fastcgi_and_lighttpd#PHP

server.modules += ("mod_fastcgi")

# FCGI server
# ===========
#
# Configure a FastCGI server which handles PHP requests.
#
index-file.names += ("index.php")
fastcgi.server = ( 
    # Load-balance requests for this path...
    ".php" => (
        # ... among the following FastCGI servers. The string naming each
        # server is just a label used in the logs to identify the server.
        "localhost" => ( 
            "bin-path" => "/usr/bin/php-cgi",
            "socket" => "/tmp/php-fastcgi.sock",
            # breaks SCRIPT_FILENAME in a way that PHP can extract PATH_INFO
            # from it 
            "broken-scriptfilename" => "enable",
            # Launch (max-procs + (max-procs * PHP_FCGI_CHILDREN)) procs, where
            # max-procs are "watchers" and the rest are "workers". See:
            # https://redmine.lighttpd.net/projects/1/wiki/frequentlyaskedquestions#How-many-php-CGI-processes-will-lighttpd-spawn 
            "max-procs" => 4, # default value
            "bin-environment" => (
                "PHP_FCGI_CHILDREN" => "1" # default value
            )
        )
    )   
)

Make lighttpd use the new configuration file:

/etc/lighttpd/lighttpd.conf
include "conf.d/fastcgi.conf"
Note: Remember that the order in which the modules are loaded is important, the correct order is listed in /usr/share/doc/lighttpd/config/modules.conf. Any misconfiguration may cause lighttpd to crash.

Reload lighttpd.

Note:
  • If you receive errors like No input file found when attempting to access php files, there are several possible explanations. See this FAQ for more information.
  • Make sure that no other module (e.g. mod_cgi) will try to handle the .php extension.
Using php-fpm

There is no adaptive spawning anymore in recent lighttpd releases. For dynamic management of PHP processes, you can install php-fpm and then start and enable php-fpm.service.

Note: You can configure the number of servers in the pool and tweak other configuration options by editing the file /etc/php/php-fpm.conf. More details on php-fpm can be found on the php-fpm website. Remember that when you make changes to /etc/php/php.ini you will need to restart php-fpm.service.

In /etc/lighttpd/conf.d/fastcgi.conf add:

server.modules += ( "mod_fastcgi" )

index-file.names += ( "index.php" ) 

fastcgi.server = (
    ".php" => (
      "localhost" => ( 
        "socket" => "/run/php-fpm/php-fpm.sock",
        "broken-scriptfilename" => "enable"
      ))
)
eAccelerator
Note: As of November 2014, eacceleratorAUR[broken link: archived in aur-mirror] cannot be compiled.

Install eacceleratorAUR[broken link: archived in aur-mirror].

Add own config file for eaccelerator:

/etc/php/conf.d/eaccelerator-own.ini
zlib.output_compression = On
cgi.fix_pathinfo=1
eaccelerator.cache_dir="/home/phpuser/eaccelerator/cache"
Tip: I additionally set safe_mod to On in my setup, but this is not required.
Try a php page

Create the following php page, name it index.php, and place a copy in both /srv/http/ and /srv/http-ssl/html/

<?php
phpinfo();
?>

Try navigating with a web browser to both the http and https address of your server. You should see the phpinfo page.

Check eaccelerator caching:

# ls -l /home/phpuser/eaccelerator/cache

If the above command outputs the following:

-rw-------  1 phpuser phpuser 456 2005-05-05 14:53 eaccelerator-277.58081
-rw-------  1 phpuser phpuser 452 2005-05-05 14:53 eaccelerator-277.88081

Then eaccelerator is happily caching your php scripts to help speed things up.

Ruby on Rails

Install and configure FastCGI (see #FastCGI above).

Install ruby from official repositories and ruby-fcgiAUR[broken link: archived in aur-mirror] from AUR.

Follow instructions on RubyOnRails.

Python FastCGI

Note: This method will not work with Python 3 because Flup library is only available for Python 2. If you want to use Python 3, you should refer to #CGI section.

Install and configure FastCGI (see #FastCGI above).

Install python2-flup.

Configure:

fastcgi.server = (
    ".py" =>
    (
        "python-fcgi" =>
        (
        "socket" => "/run/lighttpd/fastcgi.python.socket",
         "bin-path" => "test.py",
         "check-local" => "disable",
         "max-procs" => 1,
        )
    )
)

Put the test.py in the root of your server (do not forget to chmod +x it)

#!/usr/bin/env python2

def myapp(environ, start_response):
    print 'got request: %s' % environ
    start_response('200 OK', [('Content-Type', 'text/plain')])
    return ['Hello World!']

if __name__ == '__main__':
    from flup.server.fcgi import WSGIServer
    WSGIServer(myapp).run()

Thanks to firecat53 for his explanation

Server name indication

To use SNI with lighttpd, simply put additional ssl.pemfile configuration directives inside host conditionals. A default ssl.pemfile is still required.

$HTTP["host"] == "www.example.org" {
    ssl.pemfile = "/etc/lighttpd/certs/www.example.org.pem" 
}

$HTTP["host"] == "mail.example.org" {
    ssl.pemfile = "/etc/lighttpd/certs/mail.example.org.pem" 
}

Redirect http requests to https

You should add "mod_redirect" in server.modules array in /etc/lighttpd/lighttpd.conf:

server.modules += ( "mod_redirect" )

$SERVER["socket"] == ":80" {
  $HTTP["host"] =~ "example.org" {
    url.redirect = ( "^/(.*)" => "https://example.org/$1" )
    server.name                 = "example.org" 
  }
}

$SERVER["socket"] == ":443" {
  ssl.engine = "enable" 
  ssl.pemfile = "/etc/lighttpd/ssl/server.pem" 
  server.document-root = "..." 
}

To redirect all hosts to their secure equivalents use the following in place of the socket 80 configuration above:

$SERVER["socket"] == ":80" {
  $HTTP["host"] =~ ".*" {
    url.redirect = (".*" => "https://%0$0")
  }
}

To redirect all hosts for part of the site (e.g. secure or phpmyadmin):

$SERVER["socket"] == ":80" {
  $HTTP["url"] =~ "^/secure" {
    url.redirect = ( "^/(.*)" => "https://example.com/$1" )
  }
}

Output compression

In /etc/lighttpd/lighttpd.conf add

var.cache_dir           = "/var/cache/lighttpd"

Then create directory for a compressed files:

# mkdir /var/cache/lighttpd/compress
# chown http:http /var/cache/lighttpd/compress

Copy example configuration file:

# mkdir /etc/lighttpd/conf.d
# cp /usr/share/doc/lighttpd/config/conf.d/compress.conf /etc/lighttpd/conf.d/

Add following in /etc/lighttpd/lighttpd.conf:

include "conf.d/compress.conf"
Note: You can not do this (copy compress.conf) and add a needed content in /etc/lighttpd/lighttpd.conf instead.

See also