commit 0c2e8788cd86c23df960644b67e0543fc9519cf0
parent 157c16d32a7a8b1b0c4158a1c7b4dc383b711233
Author: Erik Loualiche <[email protected]>
Date: Fri, 6 Feb 2026 11:03:51 -0600
Document all supported FFI types with examples
- Primitive types: Int64, Float64, Bool, String, Nothing
- Compound types: Vector{Any}, Dict{String, Any}
- Enums: simple and with arguments
- Nested structures: arbitrary depth
- Computed values: expressions, functions, merges
Co-Authored-By: Claude Opus 4.5 <[email protected]>
Diffstat:
| M | docs/src/man/ffi.md | | | 87 | ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------------- |
1 file changed, 73 insertions(+), 14 deletions(-)
diff --git a/docs/src/man/ffi.md b/docs/src/man/ffi.md
@@ -30,6 +30,79 @@ nickel_eval_ffi("{ a = 1, b = 2 }") # JSON.Object with dot-access
nickel_eval_ffi("{ a = 1 }", Dict{String, Int}) # Typed Dict
```
+## Supported Types
+
+### Primitive Types
+
+| Nickel | Julia | Example |
+|--------|-------|---------|
+| Integer numbers | `Int64` | `42` → `42::Int64` |
+| Decimal numbers | `Float64` | `3.14` → `3.14::Float64` |
+| Booleans | `Bool` | `true` → `true::Bool` |
+| Strings | `String` | `"hello"` → `"hello"::String` |
+| Null | `Nothing` | `null` → `nothing` |
+
+**Note:** Nickel has a single `Number` type. Whole numbers (like `42` or `42.0`) become `Int64`. Only true decimals (like `3.14`) become `Float64`.
+
+### Compound Types
+
+| Nickel | Julia | Example |
+|--------|-------|---------|
+| Arrays | `Vector{Any}` | `[1, 2, 3]` → `Any[1, 2, 3]` |
+| Records | `Dict{String, Any}` | `{ x = 1 }` → `Dict("x" => 1)` |
+
+### Enums
+
+Nickel enums are converted to `Dict{String, Any}` with special fields:
+
+**Simple enum** (no argument):
+```julia
+nickel_eval_native("let x = 'Foo in x")
+# => Dict("_tag" => "Foo")
+```
+
+**Enum with argument**:
+```julia
+nickel_eval_native("let x = 'Some 42 in x")
+# => Dict("_tag" => "Some", "_value" => 42)
+
+nickel_eval_native("let x = 'Ok { value = 123 } in x")
+# => Dict("_tag" => "Ok", "_value" => Dict("value" => 123))
+```
+
+### Nested Structures
+
+Arbitrary nesting is fully supported:
+
+```julia
+# Deeply nested records
+result = nickel_eval_native("{ a = { b = { c = 42 } } }")
+result["a"]["b"]["c"] # => 42
+
+# Arrays of records
+result = nickel_eval_native("[{ id = 1 }, { id = 2 }]")
+result[1]["id"] # => 1
+
+# Records with arrays
+result = nickel_eval_native("{ items = [1, 2, 3], name = \"test\" }")
+result["items"] # => Any[1, 2, 3]
+
+# Mixed nesting
+result = nickel_eval_native("{ data = [{ a = 1 }, { b = [true, false] }] }")
+result["data"][2]["b"] # => Any[true, false]
+```
+
+### Computed Values
+
+Functions and expressions are evaluated before conversion:
+
+```julia
+nickel_eval_native("1 + 2") # => 3
+nickel_eval_native("let x = 10 in x * 2") # => 20
+nickel_eval_native("[1, 2, 3] |> std.array.map (fun x => x * 2)") # => Any[2, 4, 6]
+nickel_eval_native("{ a = 1 } & { b = 2 }") # => Dict("a" => 1, "b" => 2)
+```
+
## Checking FFI Availability
```julia
@@ -67,20 +140,6 @@ cp target/release/libnickel_jl.so ../../deps/
cp target/release/nickel_jl.dll ../../deps/
```
-## Type Mapping
-
-| Nickel | Julia (native) |
-|--------|----------------|
-| Integer numbers | `Int64` |
-| Decimal numbers | `Float64` |
-| Bool | `Bool` |
-| String | `String` |
-| null | `nothing` |
-| Array | `Vector{Any}` |
-| Record | `Dict{String, Any}` |
-
-Note: Nickel has a single `Number` type. Whole numbers (like `42` or `42.0`) become `Int64`. Only true decimals (like `3.14`) become `Float64`.
-
## Performance Comparison
FFI mode is faster for repeated evaluations because it: