Documentation
¶
Overview ¶
Package trellis is a state machine engine designed for building text-based adventure games, interactive stories, and complex conversational flows.
It provides a flexible runtime that separates the narrative graph definition from the execution state, enabling rich, logic-driven navigation.
Key Features ¶
- Graph-based State Machine: Define complex flows with nodes and transitions.
- Pluggable Loaders: Load graphs from the filesystem (Markdown/Frontmatter) or in-memory structures.
- Conditional Logic: Dynamic transitions based on custom evaluators.
- State Management: Serializable state for long-running sessions.
Basic Usage ¶
Initialize the engine seamlessly using the filesystem loader (powered by Loam):
eng, err := trellis.New("./story-data")
if err != nil {
log.Fatal(err)
}
state := eng.Start()
// Render the initial view
actions, _, err := eng.Render(context.Background(), state)
// Navigate based on input
nextState, err := eng.Navigate(context.Background(), state, "open door")
For advanced usage, including custom loaders or conditional logic, refer to the examples and sub-packages.
Index ¶
- Variables
- type Engine
- func (e *Engine) Inspect() ([]domain.Node, error)
- func (e *Engine) Loader() ports.GraphLoader
- func (e *Engine) Navigate(ctx context.Context, state *domain.State, input any) (*domain.State, error)
- func (e *Engine) Render(ctx context.Context, state *domain.State) ([]domain.ActionRequest, bool, error)
- func (e *Engine) Start() *domain.State
- func (e *Engine) Watch(ctx context.Context) (<-chan string, error)
- type Option
Examples ¶
Constants ¶
This section is empty.
Variables ¶
var Version string
Functions ¶
This section is empty.
Types ¶
type Engine ¶
type Engine struct {
// contains filtered or unexported fields
}
Engine is the high-level entry point for the Trellis library. It wraps the internal runtime and provides a simplified API for consumers.
func New ¶
New initializes a new Trellis Engine. By default, it uses a Loam repository at the given path. If WithLoader option is provided, repoPath can be empty and Loam is skipped.
Example (Memory) ¶
ExampleNew_memory demonstrates how to use the Engine with an in-memory graph definition. This is useful for testing, embedded scenarios, or when you don't want to rely on the file system.
package main
import (
"context"
"fmt"
"log"
"github.com/aretw0/trellis"
"github.com/aretw0/trellis/pkg/adapters/memory"
"github.com/aretw0/trellis/pkg/domain"
)
func main() {
// 1. Define your graph using helper NewFromNodes for clean, type-safe construction.
loader, err := memory.NewFromNodes(
domain.Node{
ID: "start",
Type: "question",
Content: []byte("Hello! Do you want to proceed? [yes] [no]"),
Transitions: []domain.Transition{
{ToNodeID: "yes", Condition: "input == 'yes'"},
{ToNodeID: "no"},
},
},
domain.Node{
ID: "yes",
Type: "text",
Content: []byte("Great! You moved forward."),
},
domain.Node{
ID: "no",
Type: "text",
Content: []byte("Okay, bye."),
},
)
if err != nil {
log.Fatal(err)
}
// 2. Initialize Trellis with the custom loader
// Note: We leave path empty ("") because we are providing a loader.
engine, err := trellis.New("", trellis.WithLoader(loader))
if err != nil {
log.Fatal(err)
}
// 4. Start the flow
state := engine.Start()
ctx := context.Background()
// 5. Navigate (Input: "yes")
// "start" -> (input: yes) -> "yes"
// Note: Example previously captured actions from Step.
// Render to show we can get actions, then Navigate.
actions, _, err := engine.Render(ctx, state)
if err != nil {
log.Fatal(err)
}
// Verify actions from start node (optional in example, but good for completeness)
nextState, err := engine.Navigate(ctx, state, "yes")
if err != nil {
log.Fatal(err)
}
fmt.Printf("Current Node: %s\n", nextState.CurrentNodeID)
for _, action := range actions {
fmt.Printf("Action: %s\n", action.Type)
}
}
Output: Current Node: yes Action: RENDER_CONTENT
func (*Engine) Inspect ¶
Inspect returns the full graph definition for visualization or introspection tools.
func (*Engine) Loader ¶ added in v0.3.3
func (e *Engine) Loader() ports.GraphLoader
Loader returns the underlying GraphLoader used by the engine.
func (*Engine) Navigate ¶ added in v0.3.2
func (e *Engine) Navigate(ctx context.Context, state *domain.State, input any) (*domain.State, error)
Navigate determines the next state based on input.
func (*Engine) Render ¶ added in v0.3.2
func (e *Engine) Render(ctx context.Context, state *domain.State) ([]domain.ActionRequest, bool, error)
Render generates the actions (view) for the current state without transitioning. Returns actions, isTerminal (true if no transitions), and error.
type Option ¶
type Option func(*Engine)
Option defines a functional option for configuring the Engine.
func WithConditionEvaluator ¶
func WithConditionEvaluator(eval runtime.ConditionEvaluator) Option
WithConditionEvaluator sets a custom logic evaluator for the engine.
func WithLoader ¶ added in v0.3.1
func WithLoader(l ports.GraphLoader) Option
WithLoader injects a custom GraphLoader, bypassing the default Loam initialization.
Directories
¶
| Path | Synopsis |
|---|---|
|
cmd
|
|
|
trellis
command
|
|
|
examples
|
|
|
hello-world
command
|
|
|
low-level-api
command
|
|
|
internal
|
|
|
adapters/http
Package http provides primitives to interact with the openapi HTTP API.
|
Package http provides primitives to interact with the openapi HTTP API. |
|
pkg
|
|