harness

package
v1.5.0 Latest Latest
Warning

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

Go to latest
Published: Sep 16, 2026 License: MIT Imports: 9 Imported by: 0

Documentation

Overview

Package harness detects and checks AI coding agent integration health.

Index

Constants

View Source
const (
	// ClaudeMarketplaceSource is the marketplace repository carrying the hey plugin.
	ClaudeMarketplaceSource = "basecamp/claude-plugins"
	// ClaudeMarketplaceName is the marketplace name as it appears in plugin keys.
	ClaudeMarketplaceName = "37signals"
	// ClaudePluginName is the plugin identifier to install.
	ClaudePluginName = "hey"
	// ClaudeExpectedPluginKey is the fully-qualified key for a correctly installed plugin.
	ClaudeExpectedPluginKey = ClaudePluginName + "@" + ClaudeMarketplaceName
)
View Source
const AutoUpdateHint = "In Claude Code: /plugins → Marketplaces → 37signals → Enable auto-update"

AutoUpdateHint is the user-facing instruction for enabling plugin auto-update.

View Source
const SkillOwnershipMarker = ".managed-by-hey-cli"

SkillOwnershipMarker marks a skill directory as written by hey-cli. A skill file at a canonical path without it is somebody's hand-authored skill: present, but not a working hey integration.

Variables

This section is empty.

Functions

func AgentSkillPath added in v1.5.0

func AgentSkillPath() string

AgentSkillPath returns the shared location used by agents that implement the Agent Skills convention.

func CodexHome

func CodexHome() string

CodexHome returns Codex's home directory: $CODEX_HOME or ~/.codex.

func DetectClaude

func DetectClaude() bool

DetectClaude returns true if Claude Code is installed. Checks ~/.claude/ directory first, then falls back to binary on PATH.

func DetectCodex

func DetectCodex() bool

DetectCodex returns true when Codex has a home directory or executable.

func FindClaudeBinary

func FindClaudeBinary() string

FindClaudeBinary returns the path to the claude binary, or "" if not found.

func FindCodexBinary

func FindCodexBinary() string

FindCodexBinary returns the Codex executable path, or an empty string.

func InstalledPluginVersion

func InstalledPluginVersion() string

InstalledPluginVersion reads the installed plugin version from ~/.claude/plugins/installed_plugins.json. Returns "" if unreadable.

func LegacyCodexSkillPath added in v1.5.0

func LegacyCodexSkillPath() string

LegacyCodexSkillPath returns the old Codex-specific skill path. Current Codex discovers AgentSkillPath directly; this remains only so hey-cli can safely migrate and remove copies written by older releases.

func RegisterAgent

func RegisterAgent(info AgentInfo)

RegisterAgent adds an agent to the global registry. Called from init() in agent-specific files. Panics on empty or duplicate IDs to keep registry state well-defined.

func RegularSkillFile

func RegularSkillFile(path string) bool

RegularSkillFile reports whether path's final component is a regular file (Lstat, so a symlinked SKILL.md does not count — its target was never inspected). Intermediate directories may still be symlinks: hey-cli's own canonical Claude link is a directory link whose SKILL.md is the baseline's regular file. That deliberate resolution bounds what this proves: a user-symlinked skill *directory* can pass reads that the write paths refuse — a non-destructive asymmetry, since every write, removal and refresh still declines to touch it.

func SameFile added in v1.5.0

func SameFile(a, b string) bool

SameFile reports whether two paths resolve to the same existing file. The clean-path fallback also handles the useful missing-file case without following or inventing any filesystem state.

func SkillDirOwned

func SkillDirOwned(dir string) bool

SkillDirOwned reports whether hey-cli wrote the skill directory at dir. The marker itself must be a regular file — the same shape rule as every other skill file, so a planted symlink or directory in the marker's name cannot confer ownership. Intermediate directory links still resolve, so ownership stays visible through hey-cli's own canonical Claude symlink.

Types

type AgentInfo

type AgentInfo struct {
	Name   string                // "Claude Code"
	ID     string                // "claude"
	Detect func() bool           // reports whether the agent is installed
	Checks func() []*StatusCheck // cheap health checks gating setup wizard behavior

	// Diagnostics returns the full doctor check suite, including checks that
	// are too slow or noisy for the wizard (e.g. version comparisons).
	// When nil, doctor falls back to Checks.
	Diagnostics func(ctx context.Context) []*StatusCheck
}

AgentInfo describes a coding agent integration.

func AllAgents

func AllAgents() []AgentInfo

AllAgents returns every registered agent.

func DetectedAgents

func DetectedAgents() []AgentInfo

DetectedAgents returns all agents whose Detect function returns true. Copies the registry under the lock before calling Detect callbacks to avoid holding the lock during potentially slow I/O.

func FindAgent

func FindAgent(id string) *AgentInfo

FindAgent returns the agent with the given ID, or nil.

type StatusCheck

type StatusCheck struct {
	Name    string `json:"name"`
	Status  string `json:"status"` // "pass", "warn", "fail"
	Message string `json:"message"`
	Hint    string `json:"hint,omitempty"`
}

StatusCheck represents a single agent integration health check result.

func CheckClaudePlugin

func CheckClaudePlugin() *StatusCheck

CheckClaudePlugin checks whether the hey plugin is installed in Claude Code.

func CheckClaudePluginVersion

func CheckClaudePluginVersion() *StatusCheck

CheckClaudePluginVersion compares the installed plugin version against the running CLI version. Returns a warn check when they differ.

func CheckClaudeSkillLink() *StatusCheck

CheckClaudeSkillLink checks whether ~/.claude/skills/hey contains a valid SKILL.md.

func CheckCodexSkill

func CheckCodexSkill() *StatusCheck

CheckCodexSkill checks whether the shared hey skill is installed for Codex.

Jump to

Keyboard shortcuts

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