langreg

package
v0.14.3 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 2, 2026 License: Apache-2.0 Imports: 5 Imported by: 0

README

langreg — Language Registry for the AILANG Eval Harness

langreg is the single registration point for languages supported by ailang eval-suite. Each language registers itself via init(), so adding a new language requires one new file and zero edits to existing switch statements.

Adding a new language in 5 steps

1. Create <language>.go in this package
package langreg

import (
    "context"
    "fmt"
)

var _ Language = (*jsLang)(nil)

func init() { Register(&jsLang{}) }

type jsLang struct{}

func (j *jsLang) Name() string        { return "javascript" }
func (j *jsLang) DisplayName() string { return "JavaScript" }
func (j *jsLang) FileExt() string     { return ".js" }

func (j *jsLang) SolutionFilename() string  { return "solution.js" }
func (j *jsLang) PromptTemplatePath() string { return "internal/eval_harness/templates/agent_prompt_js.txt" }
func (j *jsLang) TaskTemplatePath() string   { return "internal/eval_harness/templates/agent_task_js.txt" }

func (j *jsLang) LoadSyntaxRef(_ string) (string, string, error) {
    return j.DefaultPrompt(), "default", nil
}

func (j *jsLang) DefaultPrompt() string {
    return "You are an expert JavaScript programmer. Write clean, modern ES2023+ code."
}

func (j *jsLang) NewRunner(_ context.Context, spec interface{}, _ string) (interface{}, error) {
    if newJSRunner == nil {
        return nil, fmt.Errorf("langreg: javascript runner factory not registered")
    }
    return newJSRunner(spec), nil
}

var newJSRunner func(spec interface{}) interface{}

func SetJSRunnerFactory(f func(spec interface{}) interface{}) { newJSRunner = f }
2. Add template files

Create internal/eval_harness/templates/agent_prompt_js.txt and agent_task_js.txt following the existing Python/AILANG templates.

3. Implement a runner

Create internal/eval_harness/js_runner.go (or similar) implementing LanguageRunner. It must satisfy:

  • Run(ctx, taskDir, solutionPath string) RunResult
  • Language() string returning "javascript"
4. Wire the factory

In internal/eval_harness/langreg_wire.go, add inside init():

langreg.SetJSRunnerFactory(func(spec interface{}) interface{} {
    if bs, ok := spec.(*BenchmarkSpec); ok {
        return NewJSRunnerWithSpec(bs)
    }
    return NewJSRunner()
})
5. Add the blank import

In internal/eval_harness/provider_executor.go (or wherever language registrations are gathered), add:

_ "github.com/sunholo-data/ailang/internal/eval_harness/langreg"

(Only needed if the package isn't already transitively imported.)


Architecture notes

  • Circular import avoided: langreg lives inside eval_harness/langreg/ but cannot import eval_harness. Runner factories are injected via Set*RunnerFactory functions, which langreg_wire.go calls from its init().
  • NewRunner returns interface{}: callers in eval_harness type-assert to LanguageRunner. This keeps langreg free of eval_harness types.
  • LoadSyntaxRef returns the resolved version ID: use promptpkg.LoadPromptWithVersion (not LoadPrompt) so the actual active version key is returned, not the string "active".

Documentation

Overview

Package langreg is the language registry for the AILANG eval harness. Each supported language (python, ailang, javascript, go, ...) registers itself via init() → Register(). Callers use Get(name) instead of switch statements, so adding a new language is one file + one init() call.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Names

func Names() []string

Names returns all registered language names, sorted alphabetically.

func Register

func Register(lang Language)

Register adds a Language implementation to the registry. Calling Register with the same name twice is a no-op (idempotent). Panics if lang is nil.

func SetAILANGRunnerFactory

func SetAILANGRunnerFactory(f func(ctx context.Context, spec interface{}, taskID string) interface{})

SetAILANGRunnerFactory registers the factory used by NewRunner. Must be called before any NewRunner call — eval_harness does this in its init.

func SetGoRunnerFactory

func SetGoRunnerFactory(f func(spec interface{}) interface{})

SetGoRunnerFactory registers the factory used by NewRunner. Must be called before any NewRunner call — eval_harness does this in its init.

func SetJSRunnerFactory

func SetJSRunnerFactory(f func(spec interface{}) interface{})

SetJSRunnerFactory registers the factory used by NewRunner. Must be called before any NewRunner call — eval_harness does this in its init.

func SetPythonRunnerFactory

func SetPythonRunnerFactory(f func(spec interface{}) interface{})

SetPythonRunnerFactory registers the factory used by NewRunner. Must be called before any NewRunner call — eval_harness does this in its init.

Types

type Language

type Language interface {
	// Name returns the canonical registry key ("python", "ailang", "javascript", "go").
	Name() string
	// DisplayName returns the human-readable name for prompt placeholders ("Python 3", "AILANG").
	DisplayName() string
	// FileExt returns the solution file extension (".py", ".ail", ".js", ".go").
	FileExt() string
	// SolutionFilename returns the expected output filename ("solution.py", "solution.ail").
	SolutionFilename() string
	// PromptTemplatePath returns the agent_prompt template file path.
	// Empty string means use the AILANG fallback template.
	PromptTemplatePath() string
	// TaskTemplatePath returns the agent_task template file path.
	TaskTemplatePath() string
	// LoadSyntaxRef loads the teaching / syntax reference prompt.
	// version is the requested prompt version ("" = active/default).
	// Returns (content, versionUsed, error).
	LoadSyntaxRef(version string) (string, string, error)
	// DefaultPrompt returns a minimal fallback prompt when LoadSyntaxRef fails.
	DefaultPrompt() string
	// NewRunner constructs a language-specific runner.
	// Returns a value satisfying eval_harness.LanguageRunner; callers type-assert.
	// spec is *eval_harness.BenchmarkSpec (passed as interface{} to avoid circular import).
	// Returns (runner interface{}, error).
	NewRunner(ctx context.Context, spec interface{}, taskID string) (interface{}, error)
}

Language is the per-language descriptor used by the eval harness. Implement this interface and call Register() from init() to add a new language.

func Get

func Get(name string) (Language, error)

Get returns the Language for the given name, or an error if not registered.

func MustGet

func MustGet(name string) Language

MustGet returns the Language for the given name, panicking if not registered. Use only in test helpers or init paths where the language is guaranteed registered.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL