gex/README.md
2025-09-23 14:55:13 -07:00

135 lines
3.7 KiB
Markdown

# gex = gajumaru exchange
Currently there is only one thing, which is the Gajumaru HTTP Daemon.
## How to run `gex_httpd`
Last updated: September 23, 2025 (PRH).
1. **Install Erlang and zx/zomp**
Source: [*Building Erlang 26.2.5 on Ubuntu 24.04*](https://zxq9.com/archives/2905)
Adapt this to your Linux distribution.
a. **Install necessary build tools**
```bash
sudo apt update
sudo apt upgrade
sudo apt install \
gcc curl g++ dpkg-dev build-essential automake autoconf \
libncurses-dev libssl-dev flex xsltproc libwxgtk3.2-dev \
wget vim git
```
b. **Put [Kerl](https://github.com/kerl/kerl) somewhere
in your `$PATH`**. This is a tool to build Erlang releases.
```bash
wget -O ~/bin/kerl https://raw.githubusercontent.com/kerl/kerl/master/kerl
chmod u+x ~/bin/kerl
```
c. **Build Erlang from source using Kerl**
```bash
kerl update releases
## use the most recent one that looks stable
## you do need to type the number twice, that's not a typo
kerl build 28.1 28.1
kerl install 28.1 ~/.erts/28.1
```
d. **Put Erlang in your `$PATH`**
Update .bashrc or .zshrc or whatever with the following line:
```bash
. $HOME/.erts/28.1/activate
```
e. **Install zx**
```bash
wget -q https://zxq9.com/projects/zomp/get_zx && bash get_zx
```
f. **Test zx works**
zx installs itself to `~/bin`, so make sure that's in your
`$PATH`.
```bash
zx run erltris
```
## Notes
### Big Picture: telnet chat server -> HTTP server
- The default project (see initial commit) is a telnet echo server. It's like
the most ghetto low-budget chat server imaginable.
![screenshot of `gh_httpd` running](./etc/gh-telnet.png)
Lefty and middley can chat just like normal.
However, righty (`curl`) foolishly thinks he is talking to an HTTP server.
His request is echoed to lefty and middley.
Curl crashed because instead of a valid HTTP response back, he got something
like
```
MESSAGE from YOU: GET / HTTP/1.1
```
- We make this into an HTTP server by replacing the "echo my message to
everyone else" logic with "parse this message as an HTTP request and send
back an HTTP response" logic.
- Our "application logic" or "business logic" or whatever is contained in that
process of how the request is mapped to a response.
- It really is not more complicated than that.
### Basics of Erlang Processes
These are heuristics that are good starting points
- each module ~= 1 process
- it helps to think of erlang as an operating system, and erlang modules as
shell scripts that run in that operating system.
- some modules correspond to fungible processes, some are non-fungible
- in Observer (`observer:start()`)
- named processes are non-fungible (e.g. `gh_client_sup`)
- the name can be anything, but conventionally it's the module name
- fungible processes have numbers (PIDs) (e.g. the `gh_client` code)
- named processes also have PIDs, they just also have names
![](./etc/observer.png)
### Following the call chain of `gex_httpd:listen(8080)`
- Reference commit: `49a09d192c6f2380c5186ec7d81e98785d667214`
- By default, the telnet server doesn't occupy a port
- `gex_httpd:listen(8080)` tells it to listen on port 8080
```
%% gex_httpd.erl
-spec listen(PortNum) -> Result
when PortNum :: inet:port_num(),
Result :: ok
| {error, {listening, inet:port_num()}}.
%% @doc
%% Make the server start listening on a port.
%% Returns an {error, Reason} tuple if it is already listening.
listen(PortNum) ->
gh_client_man:listen(PortNum).
%%