Every Toolforge tool can run a dedicated website under "https://toolname
.toolforge.org". Toolforge provides the webservice
command which is used to start and stop the web server for each tool. Toolforge supports websites written in several programming languages including PHP, Python, Node.js, Java, Ruby and others. Toolforge also provides some support services which can help you make your website’s visitors safe from tracking by third party services.
The webservice
command uses convention over configuration for some aspects of how the website is deployed. You’ll find details for different programming languages below.
You can use the toolforge webservice
command to start
, stop
, restart
, and check the status
of a webserver.
$ ssh login.toolforge.org $ become my-cool-tool $ toolforge webservice start
Use toolforge webservice --help
to get a full list of arguments.
Without any additional arguments or configuration files, toolforge webservice start
will currently start a PHP 7.4 Kubernetes container serving content from your tool's $HOME/public_html directory using lighttpd as the web server software.
The webservice
subcommand has the concept of a "template" file which can be used to store arguments (and eventually other structured content) for starting a webservice. The code will look for a --template=...
command line argument and fallback to looking for a $HOME/service.template file. The $HOME/service.template file is what most tools will be expected to use, but we may find interesting uses for multiple templates in a single tool as well.
A webservice template file is a YAML document. It can contain these settings:
TYPE
)--cpu=...
)--mem=...
)--replicas=...
)/healthz
; equivalent to --health-check-path=...
)--mount=...
)--buildservice-image=...
)--backend=...
); since 2024, kubernetes
is the only supported valueBy saving desired startup state in a file, the user can use simple webservice stop; webservice start
commands again!
# Toolforge webservice template # Provide default arguments for `webservice start` commands for this tool. # # Uncomment lines below and adjust as needed # Set Kubernetes cpu limit (--cpu=...) #cpu: 500m # Set Kubernetes memory limit (--mem=...) #mem: 512Mi # Set ReplicaSet size for a Kubernetes deployment (--replicas=...) #replicas: 2 # Runtime type # See "Supported webservice types" in `webservice --help` output for valid values. #type: {{toolforge latest image|python3}} # Extra arguments to be parsed by the chosen TYPE #extra_args: # - arg0 # - arg1 # - arg2Features
Toolforge has an Nginx server configured as a proxy server which handles all inbound requests to your tool's web server. This proxy server takes care of providing TLS termination and then reverse proxies the inbound request to your tool's web service. Web servers running on Kubernetes have a second Nginx proxy server running as the "Ingress" component inside the Kubernetes cluster. See Portal:Toolforge/Admin/Kubernetes/Networking and ingress for detailed information about the network and web request routing used by the Toolforge Kubernetes cluster.
The proxy attempts to protect tools from denial of service by rate-limiting clients. Each source IP is limited to 100 requests per minute across all of toolforge.
Toolforge also includes a 404 handler service which will respond to HTTP requests for tools which do not exist and tools which are not currently running a web service. This service is implemented as the fourohfour tool which runs on the Kubernetes backend.
Supported images and languagesWe recommend building your own using the build service, that will give you more control over the setup of the service, allow you to use more languages and language-specific build tools, and it's simpler for us to maintain.
For any use-case that does not fit in the build service, we provide some pre-built images with a more limited set of languages:
Default web server (lighttpd + PHP)See: Help:Toolforge/Web/Lighttpd
PHP PythonSee: Help:Toolforge/Web/Python
Node.js web servicesSee: Help:Toolforge/Web/Node.js
Java Other / generic web serversYou can run other web servers that are not directly supported. This can be accomplished using a runtime specific type.
toolforge webservice jdk17 start|stop|restart|shell SCRIPT
Your script will be passed an HTTP port to bind to in an environment variable named PORT. This is the port that the Nginx proxy will forward requests for https://YOUR_TOOL.toolforge.org/ to. PORT currently is 8000.
Latest supported pre-built imagesTo check all the supported images toolforge webservice --help
will have the latest, but here's a somewhat updated list of supported images for each language (new languages have to be manually added):
Toolforge storage uses NFS which has limited storage and network bandwidth. If your tool requires a static file larger than 1GB (for example serving up a container image or tarball), please store that file in the 'Download' project rather than storing it in your tools home directory.
The Download project hosts https://download.wmcloud.org, a public read-only web server for large file storage. If you would like a file added, create a Phabricator ticket or contact WMCS staff directly to have the file added.
Serving static filesFiles placed in a tool's $HOME/www/static
directory are available directly from the URL tools-static.wmflabs.org/toolname
. This does not require any action on the tool's part — putting the files in the appropriate folder (and making the directory readable) should 'just work'.
You can use this to serve static assets (CSS, HTML, JS, etc) or to host simple websites that don't require a server-side component.
Load external assets using our CDN servicesTo preserve the privacy of our users, avoid embedding assets (images, CSS, JavaScript) from servers outside of Wikimedia Foundation control.
All containers run with CPU and RAM limits set. Defaults are set at 0.5 CPU and 512Mi of memory per container. Users can adjust these up to the highest level allowed without any help from an administrator (the top limit is set at 3 CPU and 6Gi of memory per pod) with command line arguments to the toolforge webservice
command (--cpu
and --mem
).
By default, the entire tool is limited to 8 CPU and 8Gi of memory total. Both the per-webservice and total limits can be increased upon request (see below), however, larger per-webservice limits will almost certainly result in delays when starting it since they take up a large chunk of an individual worker.
The Toolforge admin team encourages you to try running your webservice with the defaults before deciding that you need more resources. We believe that most PHP and Python3 webservices will work as expected with the lower values. Java webservices will almost certainly need higher limits due to the nature of running a JVM.
Assigning a custom domainAt the moment all Toolforge websites must be available under the domain toolforge.org. So, it's not possible to assign a custom domain, pointing DNS records to Toolforge servers, etc.
This also allows the origin of the tools to be very clear.
Quota increasesIt is possible to request a quota increase if you can demonstrate your tool's need for more resources than the default namespace quota allows. Instructions and a template link for creating a quota request can be found at Toolforge (Quota requests) in Phabricator.
Please read all the instructions there before submitting your request.
Note for Toolforge admins: there are docs on how to do quota upgrades.
Response bufferingAn Nginx proxy sits between your webservice and the user. By default this proxy buffers the response sent from your server. For some use cases, including streaming large quantities of data to the browser, this can be undesirable. Buffering can be disabled on a per-request basis by sending an X-Accel-Buffering: no
header in your response.[1]
A default image will be served by the shared proxy layer if your webservice returns a 404 Not Found response when asked for /favicon.ico. This default icon is the same as the one found at https://tools-static.wmflabs.org/toolforge/favicons/favicon.ico.
/robots.txtA default response will be served by the shared proxy layer if your webservice returns a 404 Not Found response when asked for /robots.txt. The default robots.txt response denies access to all compliant web crawlers. We decided that this "fail closed" approach would be safer than a "fail open" telling all crawlers to crawl all tools.
Any tool that does wish to be indexed by search engines and other crawlers can serve their own /robots.txt content. Please see https://www.robotstxt.org/ for more information on /robots.txt in general.
Health checksBy default all web pods have a TCP health check attached that will restart the web service if it stops responding. To configure an application-layer check, use the --health-check-path PATH
flag or add health-check-path: PATH
to service.template
. It is recommended to use a dedicated endpoint (such as /healthz) for the health check probe. A HTTP health check is considered successful if the status code is at least 200 but below 400.
Some of the language specific web service types will log errors and other information to a file in the tool home directory.
In addition, the output from the webservice command is stored by the Toolforge Kubernetes infrastructure as long as the web service is running. To view these logs, use:
$ toolforge webservice logs
This command also takes some flags:
-f
to follow logs in real-time-l [number]
to only see a specific number of newest log linesIt is intended that these logs will eventually be stored in a more persistent storage system.
Running the webservice locallyYou may run the container on your local computer (not on Toolforge servers) by executing a command like this:
$ docker run \ --name toolforge \ -p 8888:80 \ -v "${PWD}:/var/www/html:cached" \ -d \ docker-registry.tools.wmflabs.org/toolforge-php73-sssd-web \ sh -c "lighty-enable-mod fastcgi-php && lighttpd -D -f /etc/lighttpd/lighttpd.conf"
Then the tool will be available at http://localhost:8888
Communication and supportSupport and administration of the WMCS resources is provided by the Wikimedia Foundation Cloud Services team and Wikimedia movement volunteers. Please reach out with questions and join the conversation:
Use a subproject of the #Cloud-Services Phabricator project to track confirmed bug reports and feature requests about the Cloud Services infrastructure itself
References See alsoRetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4