Skip to main content

Self-hosted guidance distribution for coding agents

Project description

Agent Guidance Hub (AGH)

Self-hosted guidance distribution for coding agents.

PyPI GHCR CI Release

install · quick start · how it works · server ops · development · español

Español


AGH workspace pull demo

AGH gives teams one place to publish, version, assign, and pull reusable agent instructions and skills into their repos.

Use it when agent guidance needs the same discipline as infrastructure: reproducible changes, clear ownership, and self-hosted runtime. AGH is early, Docker-first, and published as a PyPI package, Homebrew formula, and GHCR server image.

  • Centralize guidance: publish shared AGENTS.md, CLAUDE.md, and skill files once.
  • Version every change: packages are immutable SemVer releases assigned to projects.
  • Keep repos deterministic: each workspace records .agh/lock.toml and applies only the selected agent target.
  • Run it yourself: host the server with Docker, SQLite, and persistent /data storage.

Install

Linux / macOS:

brew install giulianotesta7/tap/agh

Windows (Scoop):

scoop bucket add agh https://github.com/giulianotesta7/scoop-agh
scoop install agh

or install with script:

curl -fsSL https://raw.githubusercontent.com/giulianotesta7/AgentGuidanceHub/main/scripts/install.sh | sh

or install with uv:

uv tool install --force agh

from a checkout:

git clone https://github.com/giulianotesta7/AgentGuidanceHub.git
cd AgentGuidanceHub
uv tool install --force .

check the CLI:

agh --help

Run the server with the published Docker image:

docker compose up -d
curl http://127.0.0.1:8912/api/v1/health

The default Compose image is:

ghcr.io/giulianotesta7/agent-guidance-hub:${AGH_IMAGE_TAG:-latest}

Pin production deployments with a release tag:

AGH_IMAGE_TAG=0.2.0 docker compose up -d

Quick start

Read the first owner token on the host running AGH:

docker run --rm -v agh-data:/data busybox \
  cat /data/secrets/initial_owner_token

Then log in from your machine:

agh login \
  --url <instance-url> \
  --email owner@example.com \
  --token "<initial-owner-token>"

Check the saved config. AGH masks the token:

agh config show

Create a project with the repo URL developers use in git remotes:

agh project create "Agent Guidance Hub" \
  --repo-url https://github.com/giulianotesta7/AgentGuidanceHub.git

Work from a linked repo:

agh sync
agh agent select opencode # or: agh agent select claude
agh pull --dry-run
agh pull
agh agent
agh agent show

How AGH works

Package author ── publish ──▶ AGH server ── assign ──▶ Project
                              │                         │
                              │                         ▼
                         SQLite + /data          Repo workspace
                                                       │
                                                       ├─ AGENTS.md + .opencode/skills/
                                                       └─ CLAUDE.md + .claude/skills/
Piece What it does
Packages Shared instructions, skills, or both. Published versions are immutable.
Projects One git repository plus the package versions it should use.
Workspaces A local repo linked with agh sync, one selected agent, and a committed lockfile.
Package authoring

A package starts with this shape:

my-package/
├── agh.package.toml
├── instructions/
│   ├── AGENTS.md
│   └── CLAUDE.md
└── skills/
    └── reviewer/
        └── SKILL.md

Create a template:

agh package init ./my-package --domain acme --name onboarding --version 1.0.0

The manifest starts as:

domain = "acme"
name = "onboarding"
version = "1.0.0"
description = "TODO"

Useful starter flags:

  • --with-agents creates instructions/AGENTS.md.
  • --with-claude creates instructions/CLAUDE.md.
  • --with-skill NAME creates skills/NAME/SKILL.md.

Allowed files:

  • agh.package.toml
  • instructions/AGENTS.md
  • instructions/CLAUDE.md
  • skills/<name>/SKILL.md

Rules:

  • A package can contain instructions, skills, or both.
  • It must include at least one instruction file or skill.
  • version must be exact SemVer, such as 1.0.0.
  • Published versions are immutable. Publish 1.0.1 for changes.
  • Do not publish latest. Use latest only when assigning packages to projects.
  • Use UTF-8 text files. Do not include symlinks.

Publish and list packages:

agh package publish ./my-package
agh package list

Example publish output:

Published acme/onboarding@1.0.0.
Package ID: pkg_...
Checksum: sha256:...
Project assignment

A project is an AGH record linked to one git repository.

agh project create "Agent Guidance Hub" \
  --repo-url https://github.com/giulianotesta7/AgentGuidanceHub.git
agh project list
agh project get prj_...
agh project update prj_... --name "App API"
agh project delete prj_...

Project commands that take a project reference accept prj_... ids or exact project names. All-digit values are treated as ids, and project names cannot contain only digits.

Assign packages interactively or directly:

agh project package add
agh project package add prj_...
agh project package add prj_... acme/onboarding@latest
agh project package add prj_... onboarding@1.0.0
agh project package list prj_...
agh project package update prj_... asn_... --package-ref acme/onboarding@1.0.0
agh project package remove prj_... asn_...
  • agh project package add guides you through project selection, unassigned package selection, and confirmation.
  • agh project package add <project> skips project selection, shows unassigned packages for that project, and asks for confirmation.
  • agh project package add <project> <package-ref> assigns directly without prompts, which fits scripts and CI.

asn_... identifies the project-to-package assignment. Package inputs accept pkgv_..., domain/name@version, and exact name@version refs. No-domain refs must match a single package domain, otherwise AGH reports a conflict. Use an exact version to pin the project. Use latest with domain-qualified refs when the project should resolve to the newest published version during pull.

During workspace pull, AGH writes the resolved concrete version and checksum to .agh/lock.toml.

Collection administration

Collections group skill-only packages that members install through agh skill .... Owners and admins manage collections with the agh collection commands. These admin commands are separate from the consumer agh skill ... flow.

agh collection create "Team Skills" --description "Shared review skills"
agh collection list
agh collection get "Team Skills"
agh collection update "Team Skills" --name "Review Skills"
agh collection delete "Review Skills"

Collection commands that take a collection reference accept col_... ids or exact active collection names. Canonical ids skip name resolution; exact names resolve through the active-collection by-name endpoint.

Assign skill-only packages to a collection:

agh collection package list "Team Skills"
agh collection package add "Team Skills" acme/reviewer@latest
agh collection package add "Team Skills" acme/reviewer@latest --position 2
agh collection package update "Team Skills" casn_... --package-ref acme/reviewer@1.0.0 --inactive
agh collection package remove "Team Skills" casn_...

casn_... identifies the collection-to-package assignment. Collection packages must be skill-only: AGH rejects packages that contain instructions/AGENTS.md, instructions/CLAUDE.md, or no skills, and the CLI surfaces that server validation. Package inputs accept pkgv_..., domain/name@version, and exact name@version refs. Unlike agh project package add, agh collection package add requires both the collection and the package reference — there is no interactive picker, since only the server can validate skill-only packages.

Global skills

Global skills are collection-backed tools installed into the selected agent's native user-level skill directory. A collection is an AGH-managed group of skill-only packages made available by the server; global skills are separate from workspace package assignments.

Command What it does
agh skill list Lists skills available from active collections.
agh skill install acme/commenting@latest reviewer Resolves, downloads, and installs reviewer globally for the selected agent.
agh skill remove reviewer Removes the global install for the selected or default agent.
agh skill installed Lists locally installed global skills from the global-skill lock for the selected or default agent.
agh skill agent show Shows the saved default agent for global skill commands.
agh skill agent select opencode Saves OpenCode as the default for global skill commands.
agh skill agent clear Clears the global skill default agent.

If no default is saved and --agent is omitted, AGH prompts with:

Select the agent for global skills:

Install paths:

  • OpenCode global skills: ~/.config/opencode/skills
  • Claude global skills: ~/.claude/skills

Global skill state is local user state under XDG_STATE_HOME/agh or ~/.local/state/agh; it does not change workspace pull behavior or .agh/lock.toml. If a remove operation reports a filesystem recovery error, follow the command output: the lock and native skill file may need manual cleanup before retrying.

Workspace pull and Git state
Command What it does
agh sync Matches the git remote to an AGH project and writes .agh/project.toml.
agh agent / agh agent show Shows Claude Code/OpenCode availability and the current local selection.
agh agent select claude Selects Claude Code for this workspace.
agh agent select opencode Selects OpenCode for this workspace.
agh agent clear Removes the local workspace agent selection.
agh pull --dry-run Fetches the server plan without writing repo files.
agh pull Applies instructions and skills for the selected agent and writes .agh/lock.toml.
agh pull --force Replaces conflicted AGH blocks or skill targets.

There is no both option. If no agent is selected, interactive agh pull asks which agent to use. Skip exits with code 2 and writes nothing.

Instruction files use managed blocks:

<!-- AGH-BEGIN package="<package-ref>" artifact="instructions/AGENTS.md" checksum="sha256:..." -->
Project instructions from AGH live here.
<!-- AGH-END package="<package-ref>" -->

If you edit inside the block, the next agh pull exits with conflict code 3. Use agh pull --force when AGH should replace it.

Skills go where agents already look:

.claude/skills/<skill>/SKILL.md
.opencode/skills/<skill>/SKILL.md

AGH tries a relative symlink to .agh-cache/packages/.... If the OS rejects symlinks, AGH copies the file. The lockfile records the mode:

[[packages]]
package_ref = "acme/onboarding@1.0.0"

[[artifacts]]
package_ref = "acme/onboarding@1.0.0"
path = "skills/reviewer/SKILL.md"
target_path = ".opencode/skills/reviewer/SKILL.md"
mode = "symlink" # or mode = "copy"
source = ".agh-cache/packages/acme/onboarding/1.0.0/skills/reviewer/SKILL.md"

Commit shared workspace state:

  • .agh/project.toml
  • .agh/lock.toml
  • generated AGENTS.md / CLAUDE.md when your team wants those reviewed
  • generated .claude/skills/ or .opencode/skills/ when your team wants skills reviewed

Do not commit local cache state:

.agh-cache/

AGH downloads packages to .agh-cache/packages/ and stores each developer's agent choice in .agh-cache/preferences.toml. If skill targets are symlinks, a fresh clone needs agh pull to rebuild the cache before those links resolve.

Exit codes:

Code Meaning
0 Success or no changes.
1 Runtime/API/download failure.
2 Local validation, malformed manifest, or missing/skipped agent selection.
3 Conflict.
4 Authentication/authorization failure.
5 Workspace is not linked; run agh sync.

Server operations

The first owner token is written once:

/data/secrets/initial_owner_token

Store it. AGH will not show it again. The server stores token hashes, not plaintext tokens.

Role Use
owner Full admin access, including bootstrap ownership.
admin Manage users, projects, packages, and assignments.
member Day-to-day workspace access.

Admin commands:

agh user list
agh user create user@example.com --role admin
agh user show user@example.com
agh user update usr_... --role member
agh user delete usr_...
agh token rotate
agh token reset usr_...
agh config show

User commands that take a user reference accept usr_... ids or exact emails.

agh config show masks the saved token as token = ****.

Runtime state lives under /data:

Path Purpose
/data/agh.sqlite3 SQLite database.
/data/packages/ Published package payloads.
/data/logs/agh.log Server log.
/data/secrets/initial_owner_token First owner token, created once.

The image owns /data as agh:agh (10001:10001) at build time. Named Docker volumes are initialized from that image-owned /data tree. Bind mounts must already be writable by UID/GID 10001:10001; the container does not repair host ownership.

Direct Docker run:

docker run --rm -p 8912:8912 -v agh-data:/data \
  -e AGH_BOOTSTRAP_OWNER_EMAIL=owner@example.com \
  ghcr.io/giulianotesta7/agent-guidance-hub:0.2.0

Healthcheck:

curl http://127.0.0.1:8912/api/v1/health

Backup at least:

/data/agh.sqlite3
/data/packages/
/data/secrets/

Upgrade by pinning the next image tag and restarting:

AGH_IMAGE_TAG=0.2.0 docker compose pull
AGH_IMAGE_TAG=0.2.0 docker compose up -d

Development

uv sync
uv run pytest
uv run uvicorn agh.server.app:app --host 0.0.0.0 --port 8912

Local data uses .agh-data/ by default.

Contributing and security:

Third-party notices

AGH includes project-specific skills adapted from third-party skill workflows.

  • skills/agh-branch-pr is adapted from skills/branch-pr/SKILL.md in Gentleman-Programming/gentle-ai, licensed under Apache-2.0, and modified for AGH's PR-first contribution policy.
  • skills/agh-issue-flow is adapted from skills/issue-creation/SKILL.md in Gentleman-Programming/gentle-ai, licensed under Apache-2.0, and modified for AGH's PR-first contribution policy and minimal issue-label workflow.
  • skills/agh-work-unit-commits is adapted from skills/work-unit-commits/SKILL.md in Gentleman-Programming/gentle-ai, licensed under Apache-2.0, and modified for AGH's Python/uv validation workflow, docs mirror policy, and PR-first contribution model.
  • skills/agh-chained-pr is adapted from skills/chained-pr/SKILL.md and skills/chained-pr/references/chaining-details.md in Gentleman-Programming/gentle-ai, licensed under Apache-2.0, and modified for AGH's PR-first contribution policy, minimal labels, Python/uv validation, and single-maintainer review flow.
  • skills/agh-docs-alignment is adapted from skills/docs-alignment/SKILL.md in Gentleman-Programming/engram, licensed under Apache-2.0, and modified for AGH's README-as-guide model, bilingual mirror policy, docs-test validation, and PR-first contribution flow.
  • skills/agh-testing-coverage is adapted from skills/testing-coverage/SKILL.md in Gentleman-Programming/engram, licensed under Apache-2.0, and modified for AGH's Python/uv, FastAPI/Typer, Docker, docs-guidance, and package-validation workflow.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

agh-0.6.0.tar.gz (399.3 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

agh-0.6.0-py3-none-any.whl (94.9 kB view details)

Uploaded Python 3

File details

Details for the file agh-0.6.0.tar.gz.

File metadata

  • Download URL: agh-0.6.0.tar.gz
  • Upload date:
  • Size: 399.3 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for agh-0.6.0.tar.gz
Algorithm Hash digest
SHA256 fa05d68870fe602b00b818aab33d802367830ff75df5f1d53ed3bc81c81ff659
MD5 3a191e964d29b77f01b888ffd4c693f9
BLAKE2b-256 5548f0a4b7b661da92ae98975e54af9e6a267d97fd431b532bb6ed604477f59b

See more details on using hashes here.

Provenance

The following attestation bundles were made for agh-0.6.0.tar.gz:

Publisher: release.yml on giulianotesta7/AgentGuidanceHub

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file agh-0.6.0-py3-none-any.whl.

File metadata

  • Download URL: agh-0.6.0-py3-none-any.whl
  • Upload date:
  • Size: 94.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.13

File hashes

Hashes for agh-0.6.0-py3-none-any.whl
Algorithm Hash digest
SHA256 bace013918569d327c9a3b1b5976389b85982caa1d4307779c2f722f35a37019
MD5 ea5be82dfb65e6224738c72228c7946c
BLAKE2b-256 435f5aab49abcca8fc41d2b78b0aa57fb10984dd0e52324ad5df22a4731a1dac

See more details on using hashes here.

Provenance

The following attestation bundles were made for agh-0.6.0-py3-none-any.whl:

Publisher: release.yml on giulianotesta7/AgentGuidanceHub

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page