# lighttpd configuration for cgit. # # This is a complete lighttpd.conf rather than a snippet for conf-enabled, so # nothing here is included from elsewhere and no distro base config is # assumed. Check it and run it with # lighttpd -tt -f /path/to/lighttpd.conf # check the syntax and modules # lighttpd -D -f /path/to/lighttpd.conf # run it in the foreground # # lighttpd runs the cgit.cgi binary directly through mod_cgi, so no FastCGI # bridge is needed. This is cgit's classic reference deployment, mod_cgi with # mod_alias and mod_setenv. # # Paths assumed below, edit them to match your install. # cgit CGI binary /usr/lib/cgit/cgit.cgi # static assets /usr/share/cgit (cgit.css cgit.js cgit.png favicon.ico robots.txt) # cgit config /etc/cgitrc # public URL https://git.example.org/ (cgit at the domain root) # # cgit is one CGI executable. It learns the repository and the page from # PATH_INFO and reads page options such as h= and id= from QUERY_STRING. cgit # builds its own link base from SCRIPT_NAME. The five static assets are served # straight off disk and must never be routed through cgit. # A plain assignment rather than "+=", since this config stands on its own # and there is no distro base list to append to. Adding mod_accesslog here # is what the access log below needs. server.modules = ( "mod_alias", "mod_setenv", "mod_cgi", "mod_accesslog", ) server.port = 80 server.username = "http" # Debian and Ubuntu use www-data server.groupname = "http" server.document-root = "/usr/share/cgit" # a valid docroot must exist. The # alias rules below do the routing. server.pid-file = "/run/lighttpd.pid" server.errorlog = "/var/log/lighttpd/error.log" accesslog.filename = "/var/log/lighttpd/access.log" # Drop the version number from the Server header and from error pages. server.tag = "lighttpd" # The only request body cgit ever reads is the auth-filter login form, and it # stops after 4096 bytes. Nothing else here accepts an upload. The value is in # kilobytes and the default of 0 means unlimited. server.max-request-size = 64 # mod_alias serves the assets off disk, so lighttpd must know their content # types. Without this the stylesheet is sent as application/octet-stream and # the browser ignores it. Only these five files are served off disk, so this # short table is the whole of it and no external mime file is needed. mimetype.assign = ( ".css" => "text/css", ".js" => "text/javascript", ".png" => "image/png", ".ico" => "image/vnd.microsoft.icon", ".txt" => "text/plain", ) # The vhost, as a top-level conditional so it matches on both the port 80 # socket and the optional TLS socket at the end of this file. $HTTP["host"] == "git.example.org" { # Which config cgit reads. It falls back to the compiled-in /etc/cgitrc, # the same path used here, but setting it makes the location explicit. setenv.add-environment = ( "CGIT_CONFIG" => "/etc/cgitrc" ) # Site-wide security headers are set here so they also cover the static # assets lighttpd serves. cgit itself sends only the headers the server # cannot supply. Those are Status, Content-Type, Content-Length and # Content-Disposition on downloads, Location on redirects, a Cache-Control # marking the login page no-store and a page behind an auth filter private, # the auth filter's Set-Cookie, and on raw repository bytes a nosniff of # its own next to the stricter policy "default-src 'none'". Everything # else, this policy included, is the server's job. # # The add in add-response-header is load bearing. It appends a second # copy next to what cgit emitted, so a raw page carries both policies and # the browser enforces the stricter one, while the doubled nosniff line # is harmless. The set-response-header directive would instead replace # what cgit sent, swapping the strict policy on raw repository content # for this looser site one. Never switch add to set. # # form-action self covers the login form, the only form cgit renders. If # you enable the gravatar or libravatar avatar filter, add its host to # img-src. A head-include or repo.head-content that injects a