Documentation
¶
Index ¶
- Constants
- Variables
- func BuildOrderingKey(schema, table string, keyValues []string) string
- func LookupCacheKeyPrefix(sourceID string) string
- func MetadataValue(msg Message, key string) (string, bool)
- func OrderingKey(msg Message) string
- func SourceAllowsDirectQueries(sourceType string, config map[string]string) bool
- func SourceUsesCDC(config map[string]string) bool
- type BatchSink
- type Browser
- type ColumnDiscoverer
- type ColumnInfo
- type Consumer
- type Discoverer
- type Formatter
- type Handler
- type IdempotencyReporter
- type LagReporter
- type Loggable
- type Logger
- type Message
- type NamedBegin
- type Operation
- type OutboxItem
- type OutboxStorage
- type PendingWorkReporter
- type Producer
- type PublicationInfo
- type ReadyChecker
- type ReplicationDiscoverer
- type ReplicationSlotInfo
- type SQLExecutor
- type Sampler
- type Sink
- type SinkOperationMode
- type Snapshottable
- type Source
- type StateStore
- type Stateful
- type StreamLivenessReporter
- type StringMap
- type TraceRecorder
- type TraceStep
- type Transactional
- type TwoPhaseCommit
- type TwoPhaseCommitPreflight
- type VHostScoped
- type ValidatingSink
Constants ¶
const ( StateStoreKey contextKey = "stateStore" RegistryKey contextKey = "registry" WorkflowIDKey contextKey = "workflow_id" NodeIDKey contextKey = "node_id" LastTraceSnapshotKey contextKey = "lastTraceSnapshot" )
const MetaOrderingKey = "_hermod_order_key"
MetaOrderingKey names the row a message changes.
It is the unit of ordering: two messages carrying the same key are delivered in the order the source produced them, and messages carrying different keys are free to run in parallel. The engine pins a key to one worker and one sink shard, so the guarantee holds end to end rather than only inside the writer.
It must identify a *row*, not a change. A CDC message's ID is its LSN, which is unique per change — hashing on that scatters every change to one row across every worker, which is the opposite of what is wanted. Sources that know their row identity set this to schema.table plus the primary-key values; the format is opaque, only equality matters.
Empty means "no order to keep" — a queue message, a cron tick, a batch row — and those are spread across workers exactly as before.
Variables ¶
var ( ErrNotSupported = errors.New("not supported") // ErrPermanent marks a sink failure another attempt cannot fix: the // destination refused this message for what it is — too large, addressed // to a device that no longer exists — not because it could not be reached. // // The retry layers stop on it, so the message goes to the dead-letter sink // on the first refusal instead of after the whole retry budget, and the // circuit breaker does not count it: a refusal about one message says // nothing about the sink's health. A sink reports it by wrapping it with // %w, or with an error type whose Is method matches it. ErrPermanent = errors.New("permanent failure") )
Functions ¶
func BuildOrderingKey ¶ added in v1.8.1
BuildOrderingKey composes an ordering key from a table and its key values. It returns "" when there are no key values, because a row that cannot be identified cannot be ordered against itself.
func LookupCacheKeyPrefix ¶ added in v1.8.1
LookupCacheKeyPrefix is the prefix a db_lookup's cache entry carries for the source it queried. The key continues past it with the table, columns, key value and mode, so the trailing separator is load-bearing: without it, invalidating source "cust" would also drop everything cached from "customers".
It lives here because two packages need to agree on it and neither imports the other -- pkg/comm/transformer/lookup builds the key, and internal/engine/registry drops entries by it when the source is edited.
func MetadataValue ¶ added in v1.8.1
MetadataValue reads one metadata entry, without copying the map when the message supports it.
Metadata() has to clone — handing out the live map would race with a concurrent SetMetadata — so reading a single key through it copies every other entry only to discard them. Almost every caller wants one key: `_outbox_id`, `_source_node_id`, `traceparent`, the delivery markers. On a real workflow at 32 columns those reads were 11% of everything the pipeline allocated.
A message that cannot do the single-key read still works, at the old cost. This lives here, beside the interface, because three packages had each grown a private copy of it and a fourth was about to.
func OrderingKey ¶ added in v1.8.1
OrderingKey returns the message's ordering key, or "" when it has none.
It must not clone the metadata map to read one entry. This runs once per message on the dispatch path, and cloning there cost about a third of the engine's throughput (165k -> 108k msgs/s measured) for a single map lookup.
It used to avoid the clone by indexing MetadataRef's live map with no lock held, on the ground that the caller owns the message — taken off the buffer, not yet handed to a worker. That held for the dispatch path it was written for and not for the caller it later acquired: sinkWriter.pickShard calls this from the per-sink enqueue goroutines runner.go fans out with swg.Go, one per target and all holding the same message, while the sinks' workers write delivery markers and trace lineage back onto it through the locked SetMetadata. An unlocked read against a locked write is a race, and the runtime makes a racing map read fatal.
MetadataValue takes the read lock and still does not clone, so there is no longer a cost to trade against correctness here.
func SourceAllowsDirectQueries ¶ added in v1.8.1
SourceAllowsDirectQueries reports whether a source may be the target of SQL that is not its change stream: a db_lookup's per-message query, a batch_sql's scheduled one. A database already serving logical replication should not also serve those, and where the source is a source node in a workflow as well, batching the same table delivers every row twice.
SQL Server is the documented exception -- its CDC is read back through ordinary queries against change tables, so it carries none of that cost.
func SourceUsesCDC ¶ added in v1.8.1
SourceUsesCDC reports whether a source's configuration asks for change data capture.
The flag is opt-out: a configuration with no use_cdc key at all is a CDC source, which is how internal/factory builds one. Reading it any other way -- testing for the key's presence, say -- disagrees with what the engine actually runs, and lets CDC sources through checks written to exclude them.
Types ¶
type ColumnDiscoverer ¶
type ColumnDiscoverer interface {
DiscoverColumns(ctx context.Context, table string) ([]ColumnInfo, error)
}
ColumnDiscoverer defines an optional interface for discovering columns of a table.
type ColumnInfo ¶
type Discoverer ¶
type Discoverer interface {
DiscoverDatabases(ctx context.Context) ([]string, error)
DiscoverTables(ctx context.Context) ([]string, error)
}
Discoverer defines an optional interface for discovering databases and tables.
type Formatter ¶
Formatter defines the interface for formatting messages before they are written to a sink.
type IdempotencyReporter ¶
type IdempotencyReporter interface {
// LastWriteIdempotent returns true when the latest write was treated as a
// duplicate (no-op), and true for conflict when a key collision with a
// differing payload was detected (when supported by the sink).
LastWriteIdempotent() (dedup bool, conflict bool)
}
IdempotencyReporter is an optional interface for sinks to report whether the last successful Write/WriteBatch resulted in a deduplicated (skipped) write and/or a payload conflict. Engines can use this to emit standardized metrics.
type LagReporter ¶
LagReporter defines an optional interface for reporting source lag.
type Loggable ¶
type Loggable interface {
SetLogger(Logger)
}
Loggable defines an optional interface for things that support structured logging.
type Logger ¶
type Logger interface {
Debug(msg string, keysAndValues ...any)
Info(msg string, keysAndValues ...any)
Warn(msg string, keysAndValues ...any)
Error(msg string, keysAndValues ...any)
}
Logger defines the interface for logging in Hermod.
type Message ¶
type Message interface {
ID() string
Operation() Operation
Table() string
Schema() string
Before() []byte
After() []byte
Payload() []byte // Primary data payload
Metadata() map[string]string
Data() map[string]any
MetadataRef() map[string]string
DataRef() map[string]any
SetMetadata(key, value string)
SetData(key string, value any)
Clone() Message
ToMap() map[string]any
ClearPayloads()
Retain()
Release()
}
Message represents a generic message structure. Using interface to allow different message implementations.
type NamedBegin ¶ added in v1.18.0
NamedBegin is an optional interface for a TwoPhaseCommit participant that has to name its transaction when it opens it rather than when it prepares it.
MySQL XA is the case: XA START takes the identifier, and an XA transaction cannot be renamed afterwards. Without this the participant would have to invent a name at Begin and report it back from Prepare, and a crash between that Prepare returning and the coordinator recording the substitute would leave a prepared transaction nothing can name — the window the coordinator-supplied ID in Prepare exists to close.
The coordinator calls BeginNamed instead of Begin when a participant has it, and later calls Prepare with the same txID. An open transaction that has not been prepared is not in doubt — a crash rolls it back — so the name does not need to be durable yet; it is recorded before Prepare, as for every participant.
type OutboxItem ¶
type OutboxItem struct {
ID string `json:"id"`
WorkflowID string `json:"workflow_id"`
SinkID string `json:"sink_id"`
Payload []byte `json:"payload" omitzero:"true"`
Metadata map[string]string `json:"metadata" omitzero:"true"`
CreatedAt time.Time `json:"created_at" omitzero:"true"`
Attempts int `json:"attempts"`
LastError string `json:"last_error,omitempty"`
Status string `json:"status"` // pending, processing, failed
}
OutboxItem represents a message persisted for reliable delivery.
type OutboxStorage ¶
type OutboxStorage interface {
CreateOutboxItem(ctx context.Context, item OutboxItem) error
ListOutboxItems(ctx context.Context, status string, limit int) ([]OutboxItem, error)
DeleteOutboxItem(ctx context.Context, id string) error
UpdateOutboxItem(ctx context.Context, item OutboxItem) error
}
OutboxStorage defines the interface for persisting and retrieving outbox items.
type PendingWorkReporter ¶
type PendingWorkReporter interface {
// PendingWork reports whether the source has delivered messages that have
// not been acknowledged yet. known is false when the source cannot tell,
// so callers fall back to their own signals rather than concluding that
// nothing is outstanding — a distinction wrappers need, since a decorator
// implements this interface on behalf of sources that may not.
PendingWork() (pending bool, known bool)
}
PendingWorkReporter is an optional interface for sources that can say precisely whether they are still owed acknowledgements.
It exists because replication lag does not answer that question. Lag measures the distance between the server's current WAL position and the position this pipeline has confirmed, and the server's position advances on every write anywhere on that instance — including databases and tables this workflow does not follow. An idle workflow attached to a busy server therefore reports lag that grows without limit and never returns to zero, which is indistinguishable from a wedge if lag is all you look at. What distinguishes them is whether the source actually handed over messages that were never acknowledged.
type PublicationInfo ¶
type PublicationInfo struct {
Name string `json:"name"`
AllTables bool `json:"all_tables"`
Tables []string `json:"tables"`
}
PublicationInfo describes an existing publication and the tables it covers.
type ReadyChecker ¶
ReadyChecker is an optional interface for sources that support deep readiness checks.
type ReplicationDiscoverer ¶
type ReplicationDiscoverer interface {
DiscoverReplicationSlots(ctx context.Context) ([]ReplicationSlotInfo, error)
DiscoverPublications(ctx context.Context) ([]PublicationInfo, error)
}
ReplicationDiscoverer is an optional interface for CDC sources (e.g. PostgreSQL) that can enumerate existing logical replication slots and publications so the user can choose an existing one or decide to create a new one.
type ReplicationSlotInfo ¶
type ReplicationSlotInfo struct {
Name string `json:"name"`
Plugin string `json:"plugin"`
SlotType string `json:"slot_type"`
Database string `json:"database"`
Active bool `json:"active"`
}
ReplicationSlotInfo describes an existing logical replication slot.
type SQLExecutor ¶
type SQLExecutor interface {
ExecuteSQL(ctx context.Context, query string) ([]map[string]any, error)
}
SQLExecutor is an interface for sources and sinks that can execute arbitrary SQL queries.
type SinkOperationMode ¶
type SinkOperationMode string
SinkOperationMode defines how a sink should treat incoming messages.
const ( SinkOpModeAuto SinkOperationMode = "auto" // Follow message operation SinkOpModeInsert SinkOperationMode = "insert" // Always insert SinkOpModeUpsert SinkOperationMode = "upsert" // Always upsert/merge SinkOpModeUpdate SinkOperationMode = "update" // Always update SinkOpModeDelete SinkOperationMode = "delete" // Always delete )
type Snapshottable ¶
Snapshottable defines an optional interface for sources that support manual snapshots.
type Source ¶
type Source interface {
Read(ctx context.Context) (Message, error)
Ack(ctx context.Context, msg Message) error
Ping(ctx context.Context) error
Close() error
}
Source defines the interface for reading data from a CDC source.
type StateStore ¶
type StateStore interface {
Get(ctx context.Context, key string) ([]byte, error)
Set(ctx context.Context, key string, value []byte) error
Delete(ctx context.Context, key string) error
}
StateStore defines an interface for persistent key-value storage used by transformers.
type Stateful ¶
Stateful defines an optional interface for sources and sinks that have persistent state.
type StreamLivenessReporter ¶
type StreamLivenessReporter interface {
// LastStreamActivity reports when anything was last received on the
// stream, keepalives included. A zero time means the stream has not
// started, which is not a fault.
LastStreamActivity() time.Time
// StreamSilenceThreshold is how long silence must last before it is a
// fault. Zero disables the check — appropriate when the server is
// configured not to send keepalives at all (wal_sender_timeout = 0).
StreamSilenceThreshold() time.Duration
}
StreamLivenessReporter is an optional interface for sources that hold a long-lived, server-pushed stream open — a logical replication connection above all.
Such a stream is expected to deliver something at a known cadence even when there are no changes to send: PostgreSQL emits a keepalive on an idle replication connection every wal_sender_timeout/2. That makes silence measurable evidence rather than an absence of evidence, and it is the only signal that distinguishes a source which has stopped delivering from one which simply has nothing to deliver. Every other indicator the engine has — buffer depth, sink queues, processed counts — sees only work the source has already handed over, so a stream wedged upstream of them is invisible.
type StringMap ¶
StringMap is a map[string]string that tolerates JSON values of other scalar types when unmarshalling. UI clients sometimes send configuration values as booleans or numbers (e.g. {"use_cdc": true, "batch_size": 100}) rather than strings. Decoding such payloads directly into map[string]string fails with errors like "json: cannot unmarshal bool into Go struct field ... of type string". StringMap coerces those scalar values to their string form so the API stays robust regardless of how the client encodes them.
func (*StringMap) UnmarshalJSON ¶
UnmarshalJSON decodes a JSON object into a StringMap, coercing scalar values (string, bool, number) to strings. Null becomes an absent/empty map and null values become empty strings. Objects and arrays are preserved as their JSON encoding.
type TraceRecorder ¶
type TraceRecorder interface {
RecordStep(ctx context.Context, workflowID, messageID string, step TraceStep)
}
TraceRecorder defines the interface for recording message traces.
type TraceStep ¶
type TraceStep struct {
NodeID string `json:"node_id"`
Timestamp time.Time `json:"timestamp" omitzero:"true"`
Duration time.Duration `json:"duration" omitzero:"true"`
Before map[string]any `json:"before,omitempty" omitzero:"true"`
After map[string]any `json:"after,omitempty" omitzero:"true"`
Error string `json:"error,omitempty"`
Lineage string `json:"lineage,omitempty"`
}
TraceStep represents a single step in a message's journey.
type Transactional ¶
type Transactional interface {
Begin(ctx context.Context) error
Commit(ctx context.Context) error
Rollback(ctx context.Context) error
}
Transactional is an optional interface for sources and sinks that support atomic transactions.
type TwoPhaseCommit ¶
type TwoPhaseCommit interface {
Transactional
// Prepare votes to commit, under a transaction ID the coordinator supplies.
//
// The ID is an argument rather than a return value because of what happens
// when the process dies mid-flight. A participant that named its own
// transaction left a window between Prepare returning and the coordinator
// writing that name down: a crash there leaves a prepared transaction
// nothing can name, and on PostgreSQL a prepared transaction holds its
// locks cluster-wide until somebody finds it by hand in
// pg_prepared_xacts. Supplying the ID lets the coordinator record it
// *before* the transaction exists, so recovery can always name what it
// might have created.
//
// The returned string is the ID actually in force. It is normally the one
// passed in; a participant that cannot honour 2PC in its current
// configuration may return its own sentinel instead — the PostgreSQL sink
// does this behind a transaction pooler, where PREPARE TRANSACTION is
// unavailable and it degrades to a local commit.
Prepare(ctx context.Context, txID string) (string, error)
CommitPrepared(ctx context.Context, txID string) error
RollbackPrepared(ctx context.Context, txID string) error
}
TwoPhaseCommit is an optional interface for sinks that support 2PC.
It is driven by pkg/engine/twopc.Coordinator, which a transactional sink group (pkg/comm/sink/txgroup) uses to commit several sinks atomically. The coordinator makes its decision durable before telling any participant, so a crash mid-round is resolved on the next start rather than left in doubt.
Implement this only with genuine prepared-transaction semantics. A no-op implementation is actively harmful: the contract reports failure through the error return, so a Rollback that returns nil without rolling anything back tells a future coordinator the abort succeeded while the writes stand.
type TwoPhaseCommitPreflight ¶
type TwoPhaseCommitPreflight interface {
// PreflightTwoPhaseCommit returns nil only if a later Prepare would give a
// genuinely in-doubt, resolvable transaction.
PreflightTwoPhaseCommit(ctx context.Context) error
}
TwoPhaseCommitPreflight is an optional interface for participants that can check, before any data moves, whether real two-phase commit is actually available to them.
It exists because "implements TwoPhaseCommit" is not the same as "can honour it right now". A PostgreSQL sink behind a transaction pooler cannot use PREPARE TRANSACTION at all — the in-doubt transaction has to be resolved on the backend that created it, which a pooler cannot guarantee — and PostgreSQL ships with max_prepared_transactions = 0, which makes PREPARE fail outright.
Without this check those cases surface as a mid-batch failure at best, and at worst as a participant that quietly commits when asked to prepare: the coordinator then believes it can still roll back, and the transaction silently diverges. A participant that cannot guarantee the contract should say so here and be refused at start-up.
type VHostScoped ¶ added in v1.17.0
VHostScoped is implemented by a message that knows which vhost's workflow it is running in. The engine sets it when the message is read; it is not part of the message's data or metadata, so a payload cannot set it. secret() uses it to answer from that vhost's own secrets.
Directories
¶
| Path | Synopsis |
|---|---|
|
cmd
|
|
|
hermod
command
|
|
|
hermod-edge
command
|
|
|
hermodctl
command
|
|
|
examples
|
|
|
eventstore
command
|
|
|
internal
|
|
|
aibudget
Package aibudget enforces a vhost's AI spending policy: the kill switch, the monthly token and cost budget of the vhost, and the monthly caps of single workflows.
|
Package aibudget enforces a vhost's AI spending policy: the kill switch, the monthly token and cost budget of the vhost, and the monthly caps of single workflows. |
|
aibudget/transport/http
Package http is the REST surface of the vhost AI budgets: reading a vhost's budget and this month's usage, setting the budget and the per-workflow caps, the kill switch, and the two routes a worker uses to have its model calls checked and counted by the control plane.
|
Package http is the REST surface of the vhost AI budgets: reading a vhost's budget and this month's usage, setting the budget and the per-workflow caps, the kill switch, and the two routes a worker uses to have its model calls checked and counted by the control plane. |
|
chat/transport/http
Package http is the chat trigger's transport: the endpoint a chat source receives messages on, from a web page, Slack or Telegram, and answers with the workflow's reply.
|
Package http is the chat trigger's transport: the endpoint a chat source receives messages on, from a web page, Slack or Telegram, and answers with the workflow's reply. |
|
deadletter/transport/http
Package http is the REST surface of the dead letter page: listing the messages workflows could not deliver, reading one, replaying it (as it was, or edited, from the node that failed it or from the start), discarding it and exporting a selection.
|
Package http is the REST surface of the dead letter page: listing the messages workflows could not deliver, reading one, replaying it (as it was, or edited, from the node that failed it or from the start), discarding it and exporting a selection. |
|
engine/registry/noderetry
Package noderetry is the per-step retry policy any workflow node can carry.
|
Package noderetry is the per-step retry policy any workflow node can carry. |
|
engine/registry/nodes
Package nodes is the one import that makes every workflow node type available.
|
Package nodes is the one import that makes every workflow node type available. |
|
engine/registry/nodes/ai
Package ai holds the workflow node executors that call a language model and route on its answer.
|
Package ai holds the workflow node executors that call a language model and route on its answer. |
|
engine/registry/nodes/ai/agent
Package agent is the ai_agent node: a bounded tool-use loop in which a language model works towards a goal by calling the tools the node allows.
|
Package agent is the ai_agent node: a bounded tool-use loop in which a language model works towards a goal by calling the tools the node allows. |
|
engine/registry/nodes/ai/agent/mcptool
Package mcptool lets the ai_agent node use one tool of a remote MCP server over the Streamable HTTP transport.
|
Package mcptool lets the ai_agent node use one tool of a remote MCP server over the Streamable HTTP transport. |
|
executions
Package executions reads a workflow's run history out of its message traces.
|
Package executions reads a workflow's run history out of its message traces. |
|
executions/transport/http
Package http serves a workflow's runs: running it once with a payload the user supplies, and (see executions.go) its run history.
|
Package http serves a workflow's runs: running it once with a payload the user supplies, and (see executions.go) its run history. |
|
lineage
Package lineage derives a data-lineage graph from what is stored: the workflows of a vhost, the sources and sinks their nodes name, and the ML models the vhost registers.
|
Package lineage derives a data-lineage graph from what is stored: the workflows of a vhost, the sources and sinks their nodes name, and the ML models the vhost registers. |
|
lineage/endpoint
Package endpoint is the lineage API's endpoints: the request and response of each route, validated, and bound to the service.
|
Package endpoint is the lineage API's endpoints: the request and response of each route, validated, and bound to the service. |
|
lineage/repository
Package repository loads the stored records a lineage graph is derived from: a vhost's workflows, sources and sinks, page by page, and its ML models where the backend keeps them.
|
Package repository loads the stored records a lineage graph is derived from: a vhost's workflows, sources and sinks, page by page, and its ML models where the backend keeps them. |
|
lineage/service
Package service is the lineage service: it loads one scope's stored records through a Loader, keeps only what the caller may see, and runs the lineage use cases on them.
|
Package service is the lineage service: it loads one scope's stored records through a Loader, keeps only what the caller may see, and runs the lineage use cases on them. |
|
lineage/transport/http
Package http is the REST surface of data lineage: a vhost's lineage graph, and everything downstream of one of its assets or workflows.
|
Package http is the REST surface of data lineage: a vhost's lineage graph, and everything downstream of one of its assets or workflows. |
|
mcpserver
Package mcpserver exposes Hermod workflows to Model Context Protocol clients: an MCP client (Claude, ChatGPT, an IDE agent) can list the workflows a user may see, read their status, and run the ones their owner has opted in.
|
Package mcpserver exposes Hermod workflows to Model Context Protocol clients: an MCP client (Claude, ChatGPT, an IDE agent) can list the workflows a user may see, read their status, and run the ones their owner has opted in. |
|
mcpserver/transport/http
Package http mounts the MCP server on Hermod's HTTP API.
|
Package http mounts the MCP server on Hermod's HTTP API. |
|
ml
Package ml is Hermod's model registry and inference path: the models a vhost can call, and the one Predict every caller uses — the Predict node, the REST endpoints and the gRPC InferenceService.
|
Package ml is Hermod's model registry and inference path: the models a vhost can call, and the one Predict every caller uses — the Predict node, the REST endpoints and the gRPC InferenceService. |
|
ml/monitor
Package monitor watches what a vhost's models are asked and answer.
|
Package monitor watches what a vhost's models are asked and answer. |
|
ml/transport/grpc
Package grpc serves hermod.ml.v1 InferenceService: the gRPC twin of POST /api/ml/serve/{vhost}/{name}.
|
Package grpc serves hermod.ml.v1 InferenceService: the gRPC twin of POST /api/ml/serve/{vhost}/{name}. |
|
ml/transport/http
Package http is the REST surface of the model registry: managing a vhost's models, calling one from the UI, and the serving endpoint applications call with a model's serving key.
|
Package http is the REST surface of the model registry: managing a vhost's models, calling one from the UI, and the serving endpoint applications call with a model's serving key. |
|
runtimetune
Package runtimetune applies process-wide runtime tuning (soft memory limit and GC behaviour) so Hermod stays within its lightweight, low-memory target and returns unused memory to the operating system promptly.
|
Package runtimetune applies process-wide runtime tuning (soft memory limit and GC behaviour) so Hermod stays within its lightweight, low-memory target and returns unused memory to the operating system promptly. |
|
selfheal
Package selfheal keeps the self-correction gate's fixes as proposals that change a workflow only when a person approves them.
|
Package selfheal keeps the self-correction gate's fixes as proposals that change a workflow only when a person approves them. |
|
selfheal/transport/http
Package http serves the self-healing proposals of a workflow.
|
Package http serves the self-healing proposals of a workflow. |
|
storage/configsecrets
Package configsecrets decides which connector configuration values are credentials, and encrypts them at rest.
|
Package configsecrets decides which connector configuration values are credentials, and encrypts them at rest. |
|
storage/mlblobtest
Package mlblobtest is the contract every storage.MLBlobStore keeps, run against each backend by its own tests.
|
Package mlblobtest is the contract every storage.MLBlobStore keeps, run against each backend by its own tests. |
|
workflow/builder
Package builder drafts a workflow from a plain-language description with a language model.
|
Package builder drafts a workflow from a plain-language description with a language model. |
|
workflow/builder/transport/http
Package http serves the natural-language workflow builder.
|
Package http serves the natural-language workflow builder. |
|
workflow/redact
Package redact removes credentials from a workflow before it leaves the instance it runs on.
|
Package redact removes credentials from a workflow before it leaves the instance it runs on. |
|
ml
|
|
|
bench/gomlp
command
Command gomlp measures the built-in engine's neural network (learn's mlp) on a generated tabular dataset: peak memory while it trains, CPU time, wall time, the saved model's size, scoring latency and throughput, and its quality against always answering the most common class.
|
Command gomlp measures the built-in engine's neural network (learn's mlp) on a generated tabular dataset: peak memory while it trains, CPU time, wall time, the saved model's size, scoring latency and throughput, and its quality against always answering the most common class. |
|
pkg
|
|
|
comm/conformance
Package conformance provides a shared contract suite that every Hermod source and sink must satisfy.
|
Package conformance provides a shared contract suite that every Hermod source and sink must satisfy. |
|
comm/formatter/schemaregistry
Package schemaregistry formats a Hermod message as a Confluent-framed record, so that a topic Hermod writes can be read by the consumers an existing Kafka estate already runs.
|
Package schemaregistry formats a Hermod message as a Confluent-framed record, so that a topic Hermod writes can be read by the consumers an existing Kafka estate already runs. |
|
comm/reply
Package reply carries what a workflow did with a message back to a caller that is waiting for it.
|
Package reply carries what a workflow did with a message back to a caller that is waiting for it. |
|
comm/sink/fcm
Package fcm sends messages to devices, topics and conditions through Firebase Cloud Messaging.
|
Package fcm sends messages to devices, topics and conditions through Firebase Cloud Messaging. |
|
comm/sink/metis
Package metis drives a BPMN 2.0 workflow engine from a Hermod pipeline.
|
Package metis drives a BPMN 2.0 workflow engine from a Hermod pipeline. |
|
comm/sink/mldataset
Package mldataset is the Collect Dataset sink: each message a workflow sends it becomes a row of a dataset on Hermod's hermod-ml worker, so the next training of a model on that dataset learns from it.
|
Package mldataset is the Collect Dataset sink: each message a workflow sends it becomes a row of a dataset on Hermod's hermod-ml worker, so the next training of a model on that dataset learns from it. |
|
comm/sink/panmail
Package panmail sends each message as an email through a panmail gateway.
|
Package panmail sends each message as an email through a panmail gateway. |
|
comm/sink/txgroup
Package txgroup writes to several sinks inside one distributed transaction.
|
Package txgroup writes to several sinks inside one distributed transaction. |
|
comm/source/metis
Package metis reads a BPMN 2.0 workflow engine into a Hermod pipeline.
|
Package metis reads a BPMN 2.0 workflow engine into a Hermod pipeline. |
|
comm/transformer/features
Package features holds the feature-engineering transformers: the steps that turn a record into the numbers a model takes, the same way at training and at inference.
|
Package features holds the feature-engineering transformers: the steps that turn a record into the numbers a model takes, the same way at training and at inference. |
|
comm/transformer/genai
Package genai holds the workflow nodes that call a large language model: ai_prompt, ai_extract and ai_embed.
|
Package genai holds the workflow nodes that call a large language model: ai_prompt, ai_extract and ai_embed. |
|
comm/transformer/genai/memory
Package memory gives an AI node a memory of the conversation a message belongs to: the earlier exchanges of the same chat, loaded before the model is called and extended after it answers.
|
Package memory gives an AI node a memory of the conversation a message belongs to: the earlier exchanges of the same chat, loaded before the model is called and extended after it answers. |
|
comm/transformer/genai/retrieve
Package retrieve is the ai_retrieve (RAG) transformer: it embeds a query with the node's AI connection, asks a vector store for the nearest documents, and writes them with their scores into the message, ready for a following ai_prompt node (or an ai_agent tool).
|
Package retrieve is the ai_retrieve (RAG) transformer: it embeds a query with the node's AI connection, asks a vector store for the nearest documents, and writes them with their scores into the message, ready for a following ai_prompt node (or an ai_agent tool). |
|
comm/transformer/geo
Package geo holds the geometry transformer: the distance between two points on a record, and whether a point lies in a polygon.
|
Package geo holds the geometry transformer: the distance between two points on a record, and whether a point lies in a polygon. |
|
comm/transformer/ml
Package ml holds the machine-learning transformers.
|
Package ml holds the machine-learning transformers. |
|
comm/transformer/structure
Package structure holds the transformers that change the shape of a record rather than its values: flatten and unflatten, parse_field, template_render and field_diff.
|
Package structure holds the transformers that change the shape of a record rather than its values: flatten and unflatten, parse_field, template_render and field_diff. |
|
engine/telemetry/aimetrics
Package aimetrics turns the record of every language model call an AI node makes into the Prometheus metrics in pkg/engine/telemetry.
|
Package aimetrics turns the record of every language model call an AI node makes into the Prometheus metrics in pkg/engine/telemetry. |
|
engine/twopc
Package twopc coordinates two-phase commit across sinks.
|
Package twopc coordinates two-phase commit across sinks. |
|
infra/ackwatermark
Package ackwatermark turns out-of-order acknowledgements into a cursor that is safe to persist.
|
Package ackwatermark turns out-of-order acknowledgements into a cursor that is safe to persist. |
|
infra/avrodecode
Package avrodecode decodes Avro binary records into map[string]any.
|
Package avrodecode decodes Avro binary records into map[string]any. |
|
infra/pgxutil
Package pgxutil centralizes pgx connection configuration so that every Postgres connection (source metadata, sink pool, pgvector pool, state store) is built consistently and is safe to use behind a transaction/statement pooling proxy such as PgBouncer.
|
Package pgxutil centralizes pgx connection configuration so that every Postgres connection (source metadata, sink pool, pgvector pool, state store) is built consistently and is safe to use behind a transaction/statement pooling proxy such as PgBouncer. |
|
infra/schemaregistry
Package schemaregistry speaks the Confluent Schema Registry wire format and REST API.
|
Package schemaregistry speaks the Confluent Schema Registry wire format and REST API. |
|
infra/sqlident
Package sqlident validates and quotes SQL identifiers.
|
Package sqlident validates and quotes SQL identifiers. |
|
infra/tracing
Package tracing carries trace context on a message rather than in a Go context.
|
Package tracing carries trace context on a message rather than in a Go context. |
|
llm
Package llm is Hermod's one interface to large language model providers.
|
Package llm is Hermod's one interface to large language model providers. |
|
llm/anthropic
Package anthropic is the llm adapter for Claude, through the official Anthropic Go SDK.
|
Package anthropic is the llm adapter for Claude, through the official Anthropic Go SDK. |
|
llm/connect
Package connect builds a ready-to-use llm.Provider from a connection description: the adapter for its kind, plus retries, a concurrency limit and an optional fallback chain.
|
Package connect builds a ready-to-use llm.Provider from a connection description: the adapter for its kind, plus retries, a concurrency limit and an optional fallback chain. |
|
llm/gemini
Package gemini is the llm adapter for Google's Gemini API (generativelanguage.googleapis.com, v1beta generateContent).
|
Package gemini is the llm adapter for Google's Gemini API (generativelanguage.googleapis.com, v1beta generateContent). |
|
llm/openai
Package openai is the llm adapter for the OpenAI Chat Completions wire format.
|
Package openai is the llm adapter for the OpenAI Chat Completions wire format. |
|
ml/builtin
Package builtin is Hermod's built-in ML engine: datasets, training, versions and predictions in Hermod's own process, in pure Go, with no hermod-ml worker to run.
|
Package builtin is Hermod's built-in ML engine: datasets, training, versions and predictions in Hermod's own process, in pure Go, with no hermod-ml worker to run. |
|
ml/builtin/learn
Package learn holds the built-in ML engine's algorithms, in pure Go: ridge and logistic regression, a random forest, gradient-boosted trees and a small multilayer perceptron, over the same preprocessing the hermod-ml worker applies (ml/worker/hermod_ml/training.py build_pipeline): a missing number gets the training median, numbers are standardised for the linear model and the network, and text is one-hot encoded.
|
Package learn holds the built-in ML engine's algorithms, in pure Go: ridge and logistic regression, a random forest, gradient-boosted trees and a small multilayer perceptron, over the same preprocessing the hermod-ml worker applies (ml/worker/hermod_ml/training.py build_pipeline): a missing number gets the training median, numbers are standardised for the linear model and the network, and text is one-hot encoded. |
|
ml/builtin/table
Package table is the built-in ML engine's dataset in memory: typed columns, read from JSON rows, CSV or Excel, with the hermod-ml worker's typing rules (ml/worker/hermod_ml/datasets.py), so the same file gives the same columns on either engine.
|
Package table is the built-in ML engine's dataset in memory: typed columns, read from JSON rows, CSV or Excel, with the hermod-ml worker's typing rules (ml/worker/hermod_ml/datasets.py), so the same file gives the same columns on either engine. |
|
ml/inference
Package inference calls a model server and turns its answer back into rows.
|
Package inference calls a model server and turns its answer back into rows. |
|
ml/onnxscore
Package onnxscore evaluates small tabular ONNX models in pure Go: the linear models and tree ensembles scikit-learn and XGBoost export through skl2onnx and onnxmltools, with the preprocessing glue those exports carry.
|
Package onnxscore evaluates small tabular ONNX models in pure Go: the linear models and tree ensembles scikit-learn and XGBoost export through skl2onnx and onnxmltools, with the preprocessing glue those exports carry. |
|
ml/profile
Package profile describes a dataset for someone deciding what to do with it: per column its kind, how much is missing, how many different values it has, and its numbers, top values or dates with a small chart; the data's problems in plain words, each with how to fix it; and the numeric columns that move together.
|
Package profile describes a dataset for someone deciding what to do with it: per column its kind, how much is missing, how many different values it has, and its numbers, top values or dates with a small chart; the data's problems in plain words, each with how to fix it; and the numeric columns that move together. |
|
ml/recommend
Package recommend serves the recommendation models the hermod-ml worker trains (ml/worker/hermod_ml/recommend.py) in-process: it parses a version's artifact once and answers "which items next for this person" and "which items are like this one" from it, without a call to the worker.
|
Package recommend serves the recommendation models the hermod-ml worker trains (ml/worker/hermod_ml/recommend.py) in-process: it parses a version's artifact once and answers "which items next for this person" and "which items are like this one" from it, without a call to the worker. |
|
ml/worker
Package worker is Hermod's client for its hermod-ml worker: the Python process that holds datasets, trains models on them, exports each one to ONNX and serves it over the Open Inference Protocol.
|
Package worker is Hermod's client for its hermod-ml worker: the Python process that holds datasets, trains models on them, exports each one to ONNX and serves it over the Open Inference Protocol. |
|
scripts
|
|
|
atomic_wipe
command
|
|
|
audit_conversion
command
Command audit_conversion reports the data_conversion nodes whose behaviour changed when an unresolvable field stopped being a silent no-op.
|
Command audit_conversion reports the data_conversion nodes whose behaviour changed when an unresolvable field stopped being a silent no-op. |
|
drop_all_slots
command
|
|
|
drop_slot
command
|
|
|
flow
command
|
|
|
insert
command
|
|
|
lsn
command
|
|
|
pub
command
|
|
|
replica
command
|
|
|
seed
command
|
|
|
setup_test_db
command
|
|
|
slots
command
|