Using LLMs to Create Tesseracts¶
Large Language Models (LLMs) like Claude or GPT-4 can help you create Tesseracts more quickly by generating schemas and boilerplate code. This page provides guidance on how to use LLMs effectively for Tesseract development.
Note
LLM capabilities are evolving rapidly. The prompting strategies and example outputs on this page reflect our experience as of early 2026. Newer models may require less hand-holding or produce better results with simpler prompts.
What LLMs are good at¶
LLMs excel at:
Generating Pydantic schemas from natural language descriptions or existing code
Converting existing functions into Tesseract
applyendpointsWriting boilerplate for
tesseract_api.pyfilesSuggesting field descriptions and validation rules
Explaining Tesseract concepts and debugging issues
Effective prompting strategies¶
Include conventions and an example pattern¶
LLMs produce the best results when you provide both conventions and a minimal example in the prompt. This works regardless of whether the LLM has access to the Tesseract Core codebase — by providing conventions inline, you don’t need to rely on the model knowing or being able to read Tesseract Core source code.
Tesseract conventions:
- InputSchema and OutputSchema are Pydantic BaseModel classes
- Use `from tesseract_core.runtime import Array, Float32`
- Array syntax: `Array[(None,), Float32]` for 1D dynamic arrays, `Float32` for scalars
- The `apply` function takes InputSchema and returns OutputSchema
Example pattern:
```python
from pydantic import BaseModel, Field
from tesseract_core.runtime import Array, Float32
class InputSchema(BaseModel):
x: Array[(None,), Float32] = Field(description="...")
class OutputSchema(BaseModel):
y: Float32 = Field(description="...")
def apply(inputs: InputSchema) -> OutputSchema:
...
```
Be specific about what you want¶
Describe your function clearly and explicitly ask for minimal output:
I have a function that performs CFD mesh generation:
- Input: A CAD geometry file path (string) and mesh resolution (float, 0.01 to 1.0)
- Output: Node coordinates (Nx3 float array) and element connectivity (Mx4 int array)
Generate just the InputSchema, OutputSchema, and apply function.
The phrase “generate just” helps prevent over-engineering (like adding autodiff endpoints you didn’t ask for).
Ask for incremental improvements¶
Start simple and iterate:
First, ask for basic schemas and apply function
Then, add field descriptions and validation
Finally, add autodiff endpoints if needed
Example: Generating a basic Tesseract¶
This example shows a minimal Tesseract without autodiff endpoints. The output below was generated by Claude 3.5 Haiku.
Prompt:
Create a Tesseract that wraps a function for computing the stress in a beam.
Tesseract conventions:
- InputSchema and OutputSchema are Pydantic BaseModel classes
- Use `from tesseract_core.runtime import Float64`
- `Float64` for scalar floats
- The `apply` function takes InputSchema and returns OutputSchema
Example pattern:
```python
from pydantic import BaseModel, Field
from tesseract_core.runtime import Float64
class InputSchema(BaseModel):
x: Float64 = Field(description="...")
class OutputSchema(BaseModel):
y: Float64 = Field(description="...")
def apply(inputs: InputSchema) -> OutputSchema:
...
```
Inputs:
- length: beam length in meters (positive float)
- width: beam width in meters (positive float)
- height: beam height in meters (positive float)
- force: applied force in Newtons (can be negative)
- material_E: Young's modulus in Pascals (positive float)
Output:
- max_stress: maximum stress in Pascals (float)
- deflection: maximum deflection in meters (float)
Generate just the InputSchema, OutputSchema, and apply function.
Use Pydantic Field() with descriptions.
Actual code the LLM produced (Claude 3.5 Haiku):
from pydantic import BaseModel, Field
from tesseract_core.runtime import Float64
class InputSchema(BaseModel):
length: Float64 = Field(description="Beam length in meters (positive float)")
width: Float64 = Field(description="Beam width in meters (positive float)")
height: Float64 = Field(description="Beam height in meters (positive float)")
force: Float64 = Field(description="Applied force in Newtons (can be negative)")
material_E: Float64 = Field(description="Young's modulus in Pascals (positive float)")
class OutputSchema(BaseModel):
max_stress: Float64 = Field(description="Maximum stress in Pascals (float)")
deflection: Float64 = Field(description="Maximum deflection in meters (float)")
def apply(inputs: InputSchema) -> OutputSchema:
"""Compute the maximum stress and deflection in a beam under load."""
# Second moment of inertia for rectangular cross-section: I = (width * height^3) / 12
I = (inputs.width * (inputs.height ** 3)) / 12.0
# Distance from neutral axis to outer fiber
c = inputs.height / 2.0
# Maximum bending moment for simply supported beam with center load
max_moment = (inputs.force * inputs.length) / 4.0
max_stress = (max_moment * c) / I
# Maximum deflection: delta = (F * L^3) / (48 * E * I)
max_deflection = (inputs.force * (inputs.length ** 3)) / (48.0 * inputs.material_E * I)
return OutputSchema(
max_stress=abs(max_stress),
deflection=abs(max_deflection)
)
Note
This basic example does not implement autodiff endpoints. To make a Tesseract fully differentiable, you need to:
Wrap types with
Differentiable[...]Implement
jacobian,jacobian_vector_product, and/orvector_jacobian_productfunctions
See the differentiable programming guide and Tesseract-JAX for how to add autodiff support.
Example: Converting existing code¶
When converting existing code, be explicit about array shapes and which parameters should be differentiable.
Prompt:
Convert this existing Python function into a Tesseract:
def simulate_heat_transfer(T_initial, T_boundary, diffusivity, dx, dt, n_steps):
"""
1D heat equation solver using finite differences.
Args:
T_initial: Initial temperature distribution (1D array)
T_boundary: Boundary temperature (scalar)
diffusivity: Thermal diffusivity (scalar)
dx: Grid spacing (scalar)
dt: Time step (scalar)
n_steps: Number of time steps (integer)
Returns:
Final temperature distribution (1D array, same shape as T_initial)
"""
T = T_initial.copy()
r = diffusivity * dt / dx**2
for _ in range(n_steps):
T_new = T.copy()
T_new[1:-1] = T[1:-1] + r * (T[2:] - 2*T[1:-1] + T[:-2])
T_new[0] = T_boundary
T_new[-1] = T_boundary
T = T_new
return T
Generate just the InputSchema, OutputSchema, and apply function.
n_steps is an integer (not differentiable). Use Array[(None,), Float32] for variable-length arrays.
Expected LLM output:
from pydantic import BaseModel, Field
from tesseract_core.runtime import Array, Float32
class InputSchema(BaseModel):
T_initial: Array[(None,), Float32] = Field(
description="Initial temperature distribution (1D array)"
)
T_boundary: Float32 = Field(description="Boundary temperature (scalar)")
diffusivity: Float32 = Field(description="Thermal diffusivity (scalar)")
dx: Float32 = Field(description="Grid spacing (scalar)")
dt: Float32 = Field(description="Time step (scalar)")
n_steps: int = Field(description="Number of time steps (integer)")
class OutputSchema(BaseModel):
T_final: Array[(None,), Float32] = Field(
description="Final temperature distribution (1D array)"
)
def apply(inputs: InputSchema) -> OutputSchema:
"""1D heat equation solver using finite differences."""
import numpy as np
T = np.array(inputs.T_initial, dtype=np.float32)
r = inputs.diffusivity * inputs.dt / inputs.dx**2
for _ in range(inputs.n_steps):
T_new = T.copy()
T_new[1:-1] = T[1:-1] + r * (T[2:] - 2 * T[1:-1] + T[:-2])
T_new[0] = inputs.T_boundary
T_new[-1] = inputs.T_boundary
T = T_new
return OutputSchema(T_final=T)
Tips for better results¶
Validate the output¶
Always review and test LLM-generated code:
Check that schemas match your actual data types
Verify that array shapes are correct (use
Nonefor dynamic dimensions)Test with real inputs before building the Tesseract
Run
tesseract buildto catch any issues early
Iterate on the design¶
Use the LLM as a pair programming partner:
The schema you generated works, but I'd like to:
1. Add validation that dx and dt satisfy the CFL condition
2. Make the boundary conditions more flexible (fixed, periodic, or insulating)
3. Add an optional output for the full time history, not just final state
Update the Tesseract accordingly.
Using LLMs with autodiff frameworks¶
If you’re using JAX and want automatic differentiation, mention this explicitly:
I'm using JAX for automatic differentiation. Generate a Tesseract that:
1. Uses Tesseract-JAX utilities if applicable
2. Implements jacobian using jax.jacobian
3. Implements jvp using jax.jvp
4. Implements vjp using jax.vjp
Here's my JAX function: ...
See also
Tesseract-JAX allows you to embed Tesseracts as JAX primitives into end-to-end differentiable programs, and provides helpers for automatically generating autodiff endpoints from JAX functions.