Sula: 一个用 Scryer Prolog 编写的 Gemini 协议服务器
/'su.la/ 来源于西班牙语的胶囊后缀,Cápsula。Git 一个用 Scryer Prolog 编写的 Gemini 协议服务器。要求sula依赖于一个修补过的 Scryer Prolog,可以在这里找到 (branch js/fixes)。所需的补丁包括:一个原生的 '$copy_stream'/2 内置函数,用于将二进制文件主体流式传输到 TLS 客户端,而不在 Prolog 堆上实例化内容。对 library(pio) 的 buffer_prepare_for_n/5 的修复,以便从进程管道(以及其他 at_end_of_stream/1 从不报告 true 的流)的延迟读取在 EOF 上终止,而不是持续循环。socket_server_accept/4 中的非阻塞轮询循环,检查 Scryer 的 INTERRUPT 标志,因此 SIGINT 可以变成可捕获的 '$interrupt_thrown' 异常,而不是被阻塞的系统调用阻塞。移植到 rustls。修改 tls_server_negotiate 以包括可选的客户端证书。构建并安装修补过的 Scryer:git clone https://git.sagredo.dev/scryer-prolog -b js/fixes cd scryer-prolog cargo install --path . openssl(1) 必须也在 PATH 中 - 它在启动时调用以读取 CN 来自配置的身份证书并验证其是否与配置的主机名匹配。运行 ./sula.pl --addr HOST:PORT --hostname NAME --content DIR --certs DIR sula.pl 是一个多语言脚本:bash 检测到 scryer-prolog 在 PATH 中,并用 sula:run, halt 作为入口目标执行它。示例: ./sula.pl \ --addr 127.0.0.1:1965 \ --hostname gmi.example.dev \ --content ./site \ --certs . CLI 选项 所有选项接受任意顺序。任何不被识别的选项都将安静地被丢弃。 选项 含义 默认 --addr HOST:PORT 监听套接字的绑定地址和端口 127.0.0.1:1965 --hostname NAME 证书的预期 CN。启动时在不匹配时中止 localhost --content DIR 提供文件的根目录 ./site --certs DIR 包含 cert.pem 和 key.pem 的目录。 停止服务器 Ctrl+C 会触发干净的关闭:监听套接字被关闭,顶级捕获记录关闭,进程以 0 退出。 特性 通过 rustls 的 TLS,PKCS#12 身份文件。主机名验证:在启动时,cert_is_for_hostname/2 调用 openssl x509 并确认证书的 CN 与 --hostname 匹配。通过扩展进行内容协商,通过 mime/2 实现,启动时从 /etc/mime.types 中填充(由 mime.pl 中的 DCG 解析)。为 .gmi 添加 text/gemini。文本响应通过 format/3 发送;通过 copy_stream/2 在本机代码中流式传输的二进制响应(文件 → TLS 套接字,没有 Prolog 堆流量)。每个连接的错误处理:TLS 握手失败和流中的客户端断开连接被记录,循环继续。其他错误重新抛出并在顶层显示。通过修补过的 Scryer socket_server_accept/4 在 SIGINT 时优雅关闭。 阶段 sula.pl 多语言启动器 + 主 sula 模块 (run/0,请求循环)。 config.pl CLI 解析 (DCG) 和配置访问器 (cert/1, addr/1, ...)。 cert.pl 证书加载 + 主机名与 CN 检查。 mime.pl /etc/mime.types 解析器 (DCG) 和 mime/2 事实。 request.pl 请求行读取器。 gemini_uri.pl Gemini URI DCG (gemini://host[:port]/path[?query])。 ip.pl IP 地址识别(被拒绝为 Gemini 主机)。 response.pl 响应状态代码 DCG。 log.pl 带标签的 log_msg/3。 banner.pl 读取 banner.txt 并逐行通过 display_banner/1 发出。 计划功能 使用密钥和证书代替 identity.p12 客户端证书 从配置文件加载配置 保存和加载用户 运行 CGI 脚本 所有状态代码 限流 虚拟主机 文件日志 多线程或某种形式的? 热重载?
本站免费、广告极少。如果觉得有帮助,可以请我们喝杯咖啡 —— 任何金额都对持续运营有实际帮助。
☕请我喝杯咖啡