2026-07-07 16:48:09 +02:00
2026-06-15 23:59:34 +02:00
2025-03-04 23:15:55 +01:00
2026-06-15 23:59:34 +02:00
2026-06-15 23:59:34 +02:00
2025-05-03 23:47:30 +02:00
2025-03-04 23:15:55 +01:00
2026-07-07 16:48:09 +02:00

Amethyst Web Server

A word of warning!

Currently Amethyst is in very early alpha stage, a lot of things will be broken, names won't be correct, promised features missing, but I'm very much working on it live!
Every save I do increments the build number by 1, I won't publish all of them, but some of them will be published.
Once a milestone is hit (e.g. a new feature fully implemented), I'll publish a release!

Currently working features:

  • New configuration is ~95% done, most features work.
  • Fixed A LOT of unreported bugs from the old code.
  • More resilliency against errors.
  • Improved security.
  • Proxy almost working!

Project status:

Amethyst will stay in beta for a while, I want all features to work, but I will make pre-release versions that are mostly stable.
They can be found as the amethyst-prerel-0.a.b releases. I won't guarantee 100% stability, but waay more than just some random build.

Install instructions:

Install Python, execute amethyst.py and change the provided config.

Minimum requirements:

Python 3.10+
And whatever PC that happens to run that.
I recommend Python 3.12 or above though, with a PC running:

  • Windows 8.1+
  • macOS 10.15+
  • Linux 4.19+
  • FreeBSD 13.2R+
  • Some other somewhat recent OS.

The webserver itself:

The Amethyst webserver is meant to be easy to use and configure. Its configuration takes inspiration from nginx and Caddyfile.
The language the configuration is made in is AmethystConf. The default config is as follows:

host * {
    directory:./html
    pesmode:0
    block-ua:match("Discordbot")
    index:index.html
}

globals {
    http:1
    https:1
    port:8080
    https-port:8443
    key:./key.pem
    cert:./cert.pem
    max-length:8192
}

It uses a key-value syntax, and uses a : as its seperator. A few key directives:
host, followed by a hostname signifies a host that will be available. Similar to nginx's server_name directive.
globals signifies all values that are of global importance, like the key and certificate file.
directory signifies the directory to look in for files on that specific host.
index, while not in the default config, signifies what path should be returned if the client only asks for / (or any subpaths without files).
pesmode signifies if the PES mode must be enabled, allowing the server to run custom Python code to manipulate the request or file further.
block-ua signifies if a specific (or loosely matched) User-Agent must be blocked from accessing the site.
proxy signifies if a the server needs to get the response from a different (remote) server but still needs to be available at this host.
max-length signifies the maximum length a request may have. AmethystConf has only 4 datatypes: String, Boolean, Function and None. A quick rundown:
String is the everything datatype. Everything is assumed to be a String unless it falls under the other categories.
Boolean is the datatype used to enable/disable features. A Boolean can have one of two possible values: 1 or 0.
Function is the datatype used in match(), it signifies that the parser has to do some work on this string before it can use it.
None is the datatype assigned to any key without a value.

PES (Python Extension Script)

The PES (Python Extension Script) is one of Amethysts main selling points. It's a new type of a dynamic page. A PES file is pretty much a Python script with some conventions. Currently it is in very alpha form. It will be heavily improved upon to make sure even people with no Python knowledge can work with it. Here's how it works:
If PES mode is enabled, the request is sent to the pes.py script, more specifically, the on_request(req) function of the PES() class.
From there, the decoded request is given to you to play with. All of Amethysts request and file processing tools are available, and soon a function will be added to hand the request back to Amethyst, if it is deemed not suitable for PES mode.
Once you're done manipulating the request, all you have to do is call return self.build_response(http_status_code, resp_body, mimetype) and Amethyst will handle the rest.
A few examples of what can be achieved with PES mode without writing any other language than Python, HTML and CSS:

  • Showing a random image from the /pics folder upon requesting /randompic from the server
  • Dynamically updating the time on a website
  • Create a complex calculator
  • Upload files to the server
  • Lock down webpages with a login prompt.
  • And much, much more.

While it might not be able to create truly dynamic pages (since PES runs server-side, not client-side), it is dynamically static, basically, it's a dynamic page until it's rendered in browser, where it's static, as PES cannot change anything there.
WARNING! PES is an advanced feature! You can absolutely compromise the security of your webserver by having a misconfigured PES file. While Amethyst still has a few protection measures built-in that activate before any request reaches the PES, but some are bypassed unless manually invoked in the PES. Because of that, here's a general user advisory:

  • Use self.fh.read_file(file_path, host=None) instead of open(file_path) because of file inclusion or directory traversal concerns.
  • Use self.fh.write_file(file_path, host=None) instead of open(file_path) because of file inclusion or directory traversal concerns.
  • NEVER allow the PES to run shell code!
  • NEVER allow the PES to run ANYTHING uploaded via the internet!
  • Try running as much of the code locally, getting data from the internet can not only take long, it can also pose a security risk.

The PES will NOT warn you if you have security issues, it's a very hands-off approach. The PES will happily run sudo rm -rf / --no-preserve-root if given the command and setup for shell execution and not tell you until everything is gone. Prevent those scenarios by limiting what PES does as much as possible!

S
Description
No description provided
Readme GPL-3.0
280 KiB
2026-03-28 23:53:07 +01:00
Languages
Python 98%
HTML 2%