···11+# Superplan AT Proto Project
22+33+Historical-language systems lab for a terminal Bluesky / AT Protocol client.
44+55+## Stack
66+77+- Superplan-26: main visible language
88+- Lisp: parser, interpreter, meta-tooling
99+- ALGOL influence: syntax and block structure
1010+- Plankalkül influence: typed data model ideas
1111+- Rust bridge: protocol edge only
1212+1313+## Current state
1414+1515+This repo currently includes:
1616+1717+- vision and language docs
1818+- Superplan example program
1919+- Common Lisp lexer, parser, AST, pretty printer, interpreter
2020+- fake Lisp bridge process over stdin/stdout
2121+- fake Rust bridge preserving the same ABI
2222+2323+## Quick start
2424+2525+### 1. Install prerequisites
2626+2727+- SBCL
2828+- Rust / Cargo
2929+3030+### 2. Run the Rust fake bridge directly
3131+3232+```bash
3333+cd bridge
3434+cargo run
3535+```
3636+3737+### 3. Run the Lisp parser + interpreter
3838+3939+From repo root:
4040+4141+```bash
4242+sbcl --script lisp-tools/parser/run.lisp
4343+```
4444+4545+By default, the interpreter tries to launch the Rust bridge first and falls back to the Lisp bridge if Rust is unavailable.
4646+4747+## Repo layout
4848+4949+- `docs/` — vision, language spec, grammar, ABI
5050+- `superplan/examples/` — `.sp` examples
5151+- `lisp-tools/parser/` — lexer, parser, AST, pretty printer, runner
5252+- `lisp-tools/interpreter/` — environment, bridge client, interpreter
5353+- `lisp-tools/bridge/` — fake Lisp bridge
5454+- `bridge/` — fake Rust bridge
+10
bridge/Cargo.toml
···11+[package]
22+name = "superplan-atproto-bridge"
33+version = "0.1.0"
44+edition = "2021"
55+66+[dependencies]
77+chrono = { version = "0.4", features = ["clock"] }
88+reqwest = { version = "0.12", features = ["blocking", "json", "rustls-tls"] }
99+serde = { version = "1", features = ["derive"] }
1010+serde_json = "1"
···11+# Superplan-26 Specification (v0)
22+33+## Overview
44+55+Superplan-26 is a modern reconstruction inspired by early high-level languages such as Superplan and ALGOL.
66+77+It is:
88+- procedural
99+- statically typed
1010+- deterministic
1111+- designed for terminal applications and system control
1212+1313+## Program Structure
1414+1515+```text
1616+PROGRAM NAME
1717+1818+<declarations>
1919+2020+BEGIN
2121+ <statements>
2222+END
2323+```
2424+2525+## Types
2626+2727+### Primitive
2828+- INTEGER
2929+- BOOLEAN
3030+- STRING
3131+- JSON
3232+3333+### Composite
3434+```text
3535+ARRAY <TYPE> NAME[N]
3636+```
3737+3838+Example:
3939+```text
4040+INTEGER I
4141+STRING CMD
4242+JSON TL
4343+ARRAY STRING LINES[10]
4444+```
4545+4646+## Statements
4747+4848+### Assignment
4949+```text
5050+X = 10
5151+NAME = "hello"
5252+```
5353+5454+### Output
5555+```text
5656+WRITE("TEXT")
5757+WRITE(NAME)
5858+```
5959+6060+### Input
6161+```text
6262+NAME = READLINE()
6363+```
6464+6565+### Conditional
6666+```text
6767+IF X = 1 THEN
6868+ WRITE("ONE")
6969+END
7070+```
7171+7272+### Loop (WHILE)
7373+```text
7474+WHILE TRUE DO
7575+ CMD = READLINE()
7676+END
7777+```
7878+7979+### Loop (FOR)
8080+```text
8181+FOR I = 0 TO 10 STEP 1 DO
8282+ WRITE("ROW")
8383+END
8484+```
8585+8686+### Procedure
8787+```text
8888+PROCEDURE SHOW(JSON TL)
8989+BEGIN
9090+ WRITE("DATA")
9191+END
9292+```
9393+9494+### Call
9595+```text
9696+CALL SHOW(TL)
9797+```
9898+9999+### Stop
100100+```text
101101+STOP
102102+```
103103+104104+## Expressions
105105+106106+### Arithmetic
107107+- `+ - * /`
108108+109109+### Comparison
110110+- `= <> < <= > >=`
111111+112112+### Boolean
113113+- `AND OR NOT`
114114+115115+## Built-in Functions
116116+117117+### IO
118118+- `WRITE(STRING)`
119119+- `READLINE() -> STRING`
120120+121121+### JSON
122122+- `JSON_PARSE(STRING) -> JSON`
123123+- `JSON_STRINGIFY(JSON) -> STRING`
124124+- `JSON_GET(JSON, STRING) -> JSON`
125125+- `JSON_INDEX(JSON, INTEGER) -> JSON`
126126+- `JSON_LEN(JSON) -> INTEGER`
127127+- `JSON_TYPE(JSON) -> STRING`
128128+- `JSON_STRING(JSON) -> STRING`
129129+- `JSON_NUMBER(JSON) -> INTEGER`
130130+- `JSON_BOOL(JSON) -> BOOLEAN`
131131+- `JSON_IS_NULL(JSON) -> BOOLEAN`
132132+133133+### AT Proto Bridge
134134+- `ATP_LOGIN(STRING, STRING) -> BOOLEAN`
135135+- `ATP_TIMELINE(STRING) -> JSON`
136136+- `ATP_PROFILE(STRING) -> JSON`
137137+- `ATP_THREAD(STRING) -> JSON`
138138+- `ATP_POST(STRING) -> BOOLEAN`
139139+- `ATP_NOTIFICATIONS() -> JSON`
140140+141141+## Example
142142+143143+```text
144144+PROGRAM DEMO
145145+146146+JSON TL
147147+JSON FEED
148148+JSON ITEM
149149+STRING TEXT
150150+151151+BEGIN
152152+ TL = ATP_TIMELINE("")
153153+ FEED = JSON_GET(TL, "feed")
154154+ ITEM = JSON_INDEX(FEED, 0)
155155+ TEXT = JSON_STRING(JSON_GET(ITEM, "text"))
156156+ WRITE(TEXT)
157157+END
158158+```
159159+160160+## Notes
161161+162162+- No floating point in v0
163163+- No recursion in v0
164164+- JSON is opaque runtime value
165165+- All networking is delegated to bridge
+67
docs/vision.md
···11+# Superplan AT Proto Project
22+33+## Vision
44+55+Build a working Bluesky / AT Protocol terminal client using a stack centered on **historical programming languages**, not modern frameworks.
66+77+This is not nostalgia. This is a systems experiment:
88+99+- What happens when early-language design meets modern decentralized protocols?
1010+- How far can we push pre-modern language models into real networked software?
1111+1212+## Core Stack
1313+1414+- **Superplan-26** → primary user-facing language
1515+- **Lisp** → compiler tooling, AST transforms, meta-layer
1616+- **ALGOL influence** → structure, readability, block discipline
1717+- **Plankalkül influence** → typed data and structured values
1818+- **Rust/C bridge** → minimal AT Proto edge (HTTP, JSON, auth)
1919+2020+## Design Principles
2121+2222+### 1. Old languages first
2323+Push as much logic as possible into:
2424+- Superplan
2525+- Lisp
2626+2727+### 2. Modern code only at the edge
2828+Rust/C is allowed only for:
2929+- HTTPS / XRPC
3030+- JSON parsing/serialization
3131+- secure token handling
3232+- IPC
3333+3434+### 3. Deterministic and simple
3535+- no hidden magic
3636+- no runtime surprises
3737+- explicit flow
3838+3939+### 4. Historical but usable
4040+This is not a museum recreation.
4141+4242+Superplan-26 is:
4343+- inspired by history
4444+- shaped for real execution
4545+4646+## Target
4747+4848+A working terminal client that can:
4949+- login
5050+- read timeline
5151+- view profiles
5252+- view threads
5353+- post messages
5454+5555+All driven from Superplan programs.
5656+5757+## Philosophy
5858+5959+> The device speaks better than 100 slides.
6060+6161+This repo should demonstrate:
6262+- a language
6363+- a compiler
6464+- a runtime
6565+- a real protocol integration
6666+6767+All grounded in early computing ideas.
+90
lisp-tools/bridge/fake-bridge.lisp
···11+(defpackage :superplan.fake-bridge
22+ (:use :cl)
33+ (:export :main))
44+(in-package :superplan.fake-bridge)
55+66+(defun trim-whitespace (s)
77+ (string-trim '(#\Space #\Tab #\Newline #\Return) s))
88+99+(defun json-escape (s)
1010+ (with-output-to-string (out)
1111+ (loop for ch across s do
1212+ (case ch
1313+ (#\" (write-string "\\\"" out))
1414+ (#\\ (write-string "\\\\" out))
1515+ (#\Newline (write-string "\\n" out))
1616+ (#\Tab (write-string "\\t" out))
1717+ (#\Return (write-string "\\r" out))
1818+ (t (write-char ch out))))))
1919+2020+(defun extract-json-string-field (line key)
2121+ (let* ((needle (format nil "\"~A\":\"" key))
2222+ (pos (search needle line :test #'char=)))
2323+ (when pos
2424+ (let* ((start (+ pos (length needle)))
2525+ (end (position #\" line :start start)))
2626+ (when end (subseq line start end))))))
2727+2828+(defun extract-json-number-field (line key)
2929+ (let* ((needle (format nil "\"~A\":" key))
3030+ (pos (search needle line :test #'char=)))
3131+ (when pos
3232+ (let* ((start (+ pos (length needle)))
3333+ (end (or (position-if-not #'digit-char-p line :start start) (length line)))
3434+ (frag (subseq line start end)))
3535+ (when (> (length frag) 0)
3636+ (parse-integer frag :junk-allowed t))))))
3737+3838+(defun send-ok (id value-json)
3939+ (format t "{\"id\":~A,\"ok\":true,\"value\":~A}~%" id value-json)
4040+ (finish-output))
4141+4242+(defun send-error (id msg)
4343+ (format t "{\"id\":~A,\"ok\":false,\"error\":\"~A\"}~%" id (json-escape msg))
4444+ (finish-output))
4545+4646+(defun handle-login (id line)
4747+ (declare (ignore line))
4848+ (send-ok id "{\"success\":true,\"handle\":\"demo.example\"}"))
4949+5050+(defun handle-timeline (id line)
5151+ (declare (ignore line))
5252+ (send-ok id "{\"feed\":[{\"text\":\"Hello from bridge timeline item 1\"},{\"text\":\"Hello from bridge timeline item 2\"}]}") )
5353+5454+(defun handle-profile (id line)
5555+ (let ((actor (or (extract-json-string-field line "actor") "demo.example")))
5656+ (send-ok id (format nil "{\"handle\":\"~A\",\"displayName\":\"Demo User\"}" (json-escape actor)))))
5757+5858+(defun handle-thread (id line)
5959+ (declare (ignore line))
6060+ (send-ok id "{\"thread\":{\"post\":{\"text\":\"Fake thread root from bridge\"}}}"))
6161+6262+(defun handle-post (id line)
6363+ (let ((text (or (extract-json-string-field line "text") "")))
6464+ (send-ok id (format nil "{\"success\":true,\"echo\":\"~A\"}" (json-escape text)))))
6565+6666+(defun handle-notifications (id line)
6767+ (declare (ignore line))
6868+ (send-ok id "{\"notifications\":[]}"))
6969+7070+(defun dispatch-line (line)
7171+ (let ((id (or (extract-json-number-field line "id") 0))
7272+ (op (extract-json-string-field line "op")))
7373+ (cond
7474+ ((null op) (send-error id "missing op"))
7575+ ((string= op "login") (handle-login id line))
7676+ ((string= op "timeline") (handle-timeline id line))
7777+ ((string= op "profile") (handle-profile id line))
7878+ ((string= op "thread") (handle-thread id line))
7979+ ((string= op "post") (handle-post id line))
8080+ ((string= op "notifications") (handle-notifications id line))
8181+ (t (send-error id (format nil "unknown op: ~A" op))))))
8282+8383+(defun main ()
8484+ (loop for line = (read-line *standard-input* nil nil)
8585+ while line do
8686+ (let ((clean (trim-whitespace line)))
8787+ (unless (zerop (length clean))
8888+ (dispatch-line clean)))))
8989+9090+(main)