Skip to content

Commit 089157e

Browse files
authored
Merge pull request #43 from sigilante/claude/goth-language-overview-fOWhO
Add Nockchain gRPC contact example.
2 parents f75444d + 9a6b912 commit 089157e

19 files changed

Lines changed: 2861 additions & 3 deletions

File tree

crates/goth-eval/src/eval.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -647,6 +647,7 @@ fn prim_arity(prim: PrimFn) -> usize {
647647
PrimFn::Neg | PrimFn::Abs | PrimFn::Not | PrimFn::Exp | PrimFn::Ln | PrimFn::Sqrt | PrimFn::Sin | PrimFn::Cos | PrimFn::Tan | PrimFn::Floor | PrimFn::Ceil | PrimFn::Round | PrimFn::Sum | PrimFn::Prod | PrimFn::Len | PrimFn::Shape | PrimFn::Reverse | PrimFn::Transpose | PrimFn::Norm | PrimFn::ToInt | PrimFn::ToFloat | PrimFn::ToBool | PrimFn::ToChar | PrimFn::ParseInt | PrimFn::ParseFloat | PrimFn::Iota | PrimFn::ToString | PrimFn::Chars => 1,
648648
PrimFn::Print | PrimFn::Write | PrimFn::ReadLine | PrimFn::ReadKey | PrimFn::ReadFile | PrimFn::Sleep => 1,
649649
PrimFn::Flush | PrimFn::RawModeEnter | PrimFn::RawModeExit => 1, // Terminal control (take unit)
650+
PrimFn::FromChars => 1, // [n]Char → String
650651
PrimFn::Lines | PrimFn::Words | PrimFn::Bytes => 1, // String splitting (unary)
651652
PrimFn::Re | PrimFn::Im | PrimFn::Conj | PrimFn::Arg => 1, // Complex decomposition
652653
PrimFn::Trace | PrimFn::Det | PrimFn::Inv | PrimFn::Diag | PrimFn::Eye | PrimFn::Eig | PrimFn::EigVecs => 1, // Matrix utilities

examples/README.md

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -277,6 +277,32 @@ cargo run --quiet --package goth-cli -- ../examples/crypto/hashfile.goth /tmp/te
277277

278278
---
279279

280+
## json/
281+
282+
JSON parsing and serialization — pure Goth implementation using recursive descent parsing and fold-based serialization. All functions are implemented entirely in Goth via the `json.goth` standard library.
283+
284+
| File | Description | Example |
285+
|------|-------------|---------|
286+
| `parse_simple.goth` | Parse JSON, extract fields, serialize | `parseJson "{\"name\":\"Goth\"}" → ⟨⊤, ..., ""⟩` |
287+
| `roundtrip.goth` | Parse → serialize → re-parse roundtrip test | `toJson (parseJson input).1` |
288+
289+
```sh
290+
# Parse and extract fields from JSON
291+
cargo run --quiet --package goth-cli -- ../examples/json/parse_simple.goth
292+
# Name: Goth
293+
# Version: 1
294+
# Features: 3
295+
# ...
296+
297+
# Roundtrip: parse → serialize → parse → serialize
298+
cargo run --quiet --package goth-cli -- ../examples/json/roundtrip.goth
299+
# Roundtrip: PASS
300+
```
301+
302+
**Demonstrates:** Recursive descent parsing, `chars`, `fromChars`, `parseFloat`, fold-based string building, tagged tuples as sum types, `strEq`, `use` imports.
303+
304+
---
305+
280306
## Language Features Covered
281307

282308
| Feature | Examples |
@@ -291,13 +317,13 @@ cargo run --quiet --package goth-cli -- ../examples/crypto/hashfile.goth /tmp/te
291317
| Sum/Product (`Σ`/`Π`) | numeric, higher-order, simulation |
292318
| Iota (`ι`) | numeric, simulation |
293319
| Array concat (``) | higher-order |
294-
| String concat (``) | simulation, crypto |
320+
| String concat (``) | simulation, crypto, json |
295321
| Conditionals (`if/then/else`) | basic, recursion, algorithms |
296322
| Contracts (``/``) | contracts, random |
297323
| Uncertainty (`±`) | uncertainty |
298324
| File I/O (``, `writeFile`, `readFile`) | io, simulation, crypto |
299-
| Module imports (`use`) | simulation, random, crypto |
325+
| Module imports (`use`) | simulation, random, crypto, json |
300326
| Tail-call optimization | tco |
301327
| Bitwise ops (`bitand`, `bitor`, `bitxor`, `shl`, `shr`) | crypto |
302-
| Tuple destructuring (`⟨a, b⟩`) | random |
328+
| Tuple destructuring (`⟨a, b⟩`) | random, json |
303329
| PRNG / entropy | random |

examples/json/parse_simple.goth

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
# JSON Parsing Example
2+
# Parse a JSON string and extract fields
3+
use "../../stdlib/json.goth"
4+
5+
╭─ main : () → String
6+
╰─ let input = "{\"name\":\"Goth\",\"version\":1.0,\"features\":[\"arrays\",\"tuples\",\"unicode\"],\"stable\":true}"
7+
in let result = parseJson input
8+
in if ¬(result.0) then "Parse error: " ⧺ result.2
9+
else let json = result.1
10+
in let nameOpt = jsonGet "name" json
11+
in let nameLine = if nameOpt.0 then "Name: " ⧺ asStr nameOpt.1 else "No name"
12+
in let verOpt = jsonGet "version" json
13+
in let verLine = if verOpt.0 then "Version: " ⧺ toString (asNum verOpt.1) else "No version"
14+
in let featOpt = jsonGet "features" json
15+
in let featLine = if featOpt.0 then "Features: " ⧺ toString (jsonLen featOpt.1) else "No features"
16+
in let stableOpt = jsonGet "stable" json
17+
in let stableLine = if stableOpt.0 then "Stable: " ⧺ toString (asBool stableOpt.1) else "No stable"
18+
in let serialized = toJson json
19+
in nameLine ⧺ "\n" ⧺ verLine ⧺ "\n" ⧺ featLine ⧺ "\n" ⧺ stableLine ⧺ "\n" ⧺ "Serialized: " ⧺ serialized

examples/json/roundtrip.goth

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# JSON Roundtrip Example
2+
# Parse JSON, serialize back, and compare
3+
use "../../stdlib/json.goth"
4+
5+
╭─ main : () → String
6+
╰─ let input = "{\"a\":1,\"b\":[2,3],\"c\":{\"d\":true},\"e\":null,\"f\":\"hello\\nworld\"}"
7+
in let r1 = parseJson input
8+
in if ¬(r1.0) then "Parse error: " ⧺ r1.2
9+
else let serialized = toJson r1.1
10+
in let r2 = parseJson serialized
11+
in if ¬(r2.0) then "Re-parse error: " ⧺ r2.2
12+
else let serialized2 = toJson r2.1
13+
in "Input: " ⧺ input ⧺ "\n"
14+
⧺ "Serialized: " ⧺ serialized ⧺ "\n"
15+
⧺ "Re-serial: " ⧺ serialized2 ⧺ "\n"
16+
⧺ if strEq serialized serialized2
17+
then "Roundtrip: PASS"
18+
else "Roundtrip: FAIL"

examples/nockchain/balance.goth

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
# Query wallet balance via nockchain-bridge
2+
# Usage: nockchain-bridge examples/nockchain/balance.goth <address>
3+
#
4+
# The bridge spawns this program, pipes its stdout as commands,
5+
# and feeds gRPC responses back via stdin.
6+
#
7+
# Protocol: print "BALANCE <addr>", readLine → "OK <nicks>" or "ERROR <msg>"
8+
9+
╭─ main : String → ()
10+
╰─ let _ = print ("BALANCE " ⧺ ₀) in
11+
let resp = readLine ⟨⟩ in
12+
print (words resp)

examples/nockchain/blocks.goth

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
# List recent blocks from Nockchain
2+
# Usage: nockchain-bridge examples/nockchain/blocks.goth
3+
#
4+
# Sends GET_BLOCKS, reads multi-line response (each line: OK <height> <id> <ts>),
5+
# terminated by a blank line.
6+
7+
╭─ main : I64 → ()
8+
╰─ let _ = print "GET_BLOCKS" in
9+
let resp = readLine ⟨⟩ in
10+
print resp

examples/nockchain/tx_status.goth

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
# Check if a transaction has been accepted
2+
# Usage: nockchain-bridge examples/nockchain/tx_status.goth <tx_id>
3+
#
4+
# Protocol: print "TX_ACCEPTED <txid>", readLine → "OK true|false" or "ERROR <msg>"
5+
6+
╭─ main : String → ()
7+
╰─ let _ = print ("TX_ACCEPTED " ⧺ ₀) in
8+
let resp = readLine ⟨⟩ in
9+
print resp

0 commit comments

Comments
 (0)