npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

opencode-sm

v0.3.8

Published

OpenCode Settings Manager — sync your OpenCode configs, agents, skills, sessions and more across machines via GitHub

Downloads

492

Readme

opencode-sm — OpenCode Settings Manager

opencode-sm is an OpenCode plugin that synchronizes your OpenCode configuration — configs, agents, skills, commands, tools, themes, plugins, and more — across multiple machines via a private GitHub repository.

npm license


Features

  • Full configuration syncopencode.json, tui.json, AGENTS.md, agents, skills, commands, tools, themes, and plugins
  • Automatic secret sanitization — API keys, tokens, passwords, and private keys are redacted before upload (unless explicitly opted in)
  • AES-256-GCM encryption — sensitive config values can be encrypted end-to-end with a local key; never stored in plaintext in the repo
  • Extra config paths — sync custom files and directories beyond the OpenCode defaults via extraConfigPaths
  • .syncignore support — skip specific files or glob patterns via a .syncignore file or excludePaths config
  • Machine isolation — each machine syncs to its own machines/<name>/ subfolder, preventing cross-machine file pollution
  • Machine identification — every git commit includes the machine name
  • Per-machine overridesopencode-sm.overrides.jsonc is never synced; settings here apply only to the local machine
  • Bidirectional sync — push local changes up, pull remote changes down, with conflict detection
  • Mirror sync/sync-up is an exact mirror of local state, including deletions
  • Automatic backups — local state is backed up before any destructive operation; up to 10 write manifests are retained
  • Atomic file writes — files are written via tmp+rename, eliminating partial-write corruption
  • Safe mode by default — startup is non-destructive; logs divergence, never modifies files without an explicit command
  • Preflight health checks — verifies gh CLI, git, GitHub authentication, and git identity before any operation
  • Conflict detection — files modified both locally and remotely are skipped and logged; no silent overwrites
  • Event-driven startup sync — sync triggers on server.connected, guaranteeing the TUI is ready before notifications appear
  • Toast notifications — every command completion surfaces a descriptive popup in the TUI
  • History and recovery/sync-log shows commit history; /sync-restore restores from a local backup

Prerequisites

  • Node.js 18 or later

  • OpenCode installed and configured

  • Git installed and available on PATH

  • GitHub CLI (gh) installed and authenticated

    gh auth login
  • Git identity configured:

    git config --global user.name "Your Name"
    git config --global user.email "[email protected]"

Installation

opencode plugin add opencode-sm

Or add to your opencode.json:

{
  "plugin": ["opencode-sm"]
}

Quick Start

First machine — create a sync repository

/sync-new my-config

This will:

  1. Create a private GitHub repository named my-config
  2. Clone it locally to ~/.local/share/opencode/opencode-sm/repo
  3. Collect your current OpenCode configuration files
  4. Sanitize secrets (API keys, tokens, etc.)
  5. Push everything with a commit like [my-laptop] Initial sync from opencode-sm

Second machine — connect to the existing repo

/sync-connect my-config
# or with explicit owner:
/sync-connect your-user/my-config

Regular workflow

# After making changes on machine A:
/sync-up

# On machine B to receive those changes:
/sync-down

Commands

| Command | Description | Use case | |---------|-------------|----------| | /sync-new [repo] | Create a new private GitHub repo and push current configs | First machine setup | | /sync-connect [repo] | Connect this machine to an existing sync repo | Subsequent machines | | /sync-up | Upload local config changes to GitHub | After modifying configs locally | | /sync-down | Download remote config changes from GitHub | After configs changed elsewhere | | /sync-check | Show diff between local configs and the remote repo | Preview before up/down | | /sync-repo | Display current sync repo configuration | Diagnostics | | /sync-fix | Propagate pending local deletions to the remote repo | After deleting files locally | | /sync-log | Show recent commit history from the sync repo | Audit trail | | /sync-restore [backup] | Restore local files from a previous backup | Recovery |

/sync-log

Displays the recent commit history from the GitHub sync repository — commit hashes, authors, dates, and messages. Use this to audit what was synced and when, or to identify a point before running /sync-restore.

/sync-restore [backup-name]

Restores local OpenCode configuration files from a backup created during a previous sync. Backups are created automatically by /sync-down and /sync-up before overwriting files. If no backup name is provided, the most recent backup is used. Does not modify the remote repository.


Configuration

Main config: ~/.config/opencode/opencode-sm.jsonc

Created automatically by /sync-new or /sync-connect.

{
  // GitHub repository configuration
  "repo": {
    // "owner": "your-github-username",
    // "name": "opencode-config",
    // "branch": "main"
  },

  // Sync secrets (API keys, tokens, auth data).
  // WARNING: Only enable if your sync repo is PRIVATE.
  "includeSecrets": false,

  // Extra paths to sync (files or directories).
  "extraConfigPaths": [],

  // Glob patterns to exclude from sync entirely.
  // You can also use a .syncignore file in your config directory.
  "excludePaths": [],

  // Machine name used in git commits and machine isolation folder.
  // Falls back to OS hostname if empty.
  "machineName": "",

  // AES-256-GCM encryption key for sensitive config values.
  // Generate with: node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"
  // Use the same key on all machines. Never commit this value.
  // "encryptionKey": "your-64-hex-character-key-here"
}

| Field | Type | Default | Description | |-------|------|---------|-------------| | repo.owner | string | gh api user | GitHub owner for the sync repo | | repo.name | string | opencode-config | Name of the sync repo | | repo.branch | string | Auto-detected | Git branch | | includeSecrets | boolean | false | Sync blocked/secret files (requires private repo) | | extraConfigPaths | string[] | [] | Extra file/directory paths to include | | excludePaths | string[] | [] | Glob patterns to exclude from sync | | machineName | string | OS hostname | Name used in commits and machine isolation | | encryptionKey | string | — | AES-256-GCM key (hex, 32 bytes). Never synced. | | safe | boolean | true | Safe mode — startup only logs divergence, never modifies |

Per-machine overrides: ~/.config/opencode/opencode-sm.overrides.jsonc

Never synchronized. Deep-merged into runtime config after every /sync-down.

{
  // "model": "anthropic/claude-sonnet-4-5",
  // "agent": { "build": { "permission": { "bash": "ask" } } }
}

.syncignore

Create ~/.config/opencode/.syncignore with gitignore-style patterns to exclude files from sync. Merged with excludePaths from config.

# Example .syncignore
*.log
sensitive-local-only.json
agents/private-*.md

Encryption

When encryptionKey is configured, individual sensitive field values are encrypted with AES-256-GCM before being pushed to the remote repo, and decrypted transparently on pull.

  • Each encrypted value is self-contained (stores IV + auth tag + ciphertext inline)
  • Pass-through transparent — machines without a key read values as-is
  • The key itself is in SENSITIVE_KEYS and is never synced

Generate a key:

node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"

Set the same key in opencode-sm.jsonc on every machine that shares the repo.


Machine Isolation

When machineName is configured, each machine syncs to its own subfolder:

opencode-config/
  machines/
    work-pc/
      agents/zeus.md
      opencode.json
    home-pc/
      agents/ra.md
      tui.json
  • /sync-up writes only to machines/<machineName>/
  • /sync-down reads only from machines/<machineName>/
  • Other machines' files are never touched

Without machineName, files go to the repo root (backward compatible).


Security

Secret sanitization

All files pass through a sanitizer before upload:

JSON files — deep key-based redaction of: apiKey, api_key, apikey, token, password, secret, credential, authorization, privateKey, private_key, accessToken, access_token, refreshToken, refresh_token, clientSecret, client_secret

Non-JSON files — regex-based redaction of:

  • OpenAI/Anthropic API keys (sk-...)
  • GitHub tokens (ghp_, gho_, ghu_, ghs_, ghr_ prefixes)
  • Bearer and Authorization header values
  • RSA / EC / OpenSSH private key blocks

Denylist (blocked by default)

| Pattern | Type | |---------|------| | auth.json | Credential store | | mcp-auth.json | MCP credential store | | opencode.db | Session database | | .netrc | Login credentials | | .git-credentials | Git credentials | | .env | Environment variables | | *.pem, *.key | Private key files | | storage/session, storage/message, storage/part | Session data |

Only synced when includeSecrets: true is explicitly set.

Backups

Before any destructive write, a timestamped backup is created:

~/.local/share/opencode/opencode-sm/backups/backup-<timestamp>/

Up to 10 write manifests are retained; older ones are rotated automatically. Use /sync-restore to recover.


Environment Variables

| Variable | Description | |----------|-------------| | OPENCODE_CONFIG_DIR | Override the OpenCode config directory | | OPENCODE_CONFIG | Override the path to the main config file | | GITHUB_TOKEN / GH_TOKEN | GitHub token (fallback: gh auth token) |


Directory Structure

| Purpose | Linux/macOS | Windows | |---------|-------------|---------| | Config | ~/.config/opencode/ | %APPDATA%\opencode\ | | Data | ~/.local/share/opencode/ | %LOCALAPPDATA%\opencode\ | | State | ~/.local/state/opencode/ | %LOCALAPPDATA%\opencode\state\ | | Sync repo | ~/.local/share/opencode/opencode-sm/repo | — | | Sync backups | ~/.local/share/opencode/opencode-sm/backups | — | | Plugin config | ~/.config/opencode/opencode-sm.jsonc | — | | Local overrides | ~/.config/opencode/opencode-sm.overrides.jsonc | — |

What gets synced

| Category | Paths | Sanitized? | |----------|-------|------------| | Main configs | opencode.json, tui.json, AGENTS.md | No | | Agents | agents/, agent/ | Yes | | Commands | commands/, command/ | Yes | | Skills | skills/, skill/ | Yes | | Tools | tools/, tool/ | Yes | | Themes | themes/, theme/ | Yes | | Plugins | plugins/, plugin/ | Yes | | Modes | modes/, mode/ | Yes | | Extra paths | extraConfigPaths | Yes | | Auth/sessions | auth.json, .env, *.pem, etc. | Only with includeSecrets: true |

What is never synced

  • opencode-sm.overrides.jsonc — per-machine overrides
  • opencode-sm.jsonc — plugin config (recreated per machine)
  • encryptionKey — encryption key (local only)
  • state.json — sync timestamps
  • model.json, prompt-stash.jsonl, prompt-history.jsonl

Changelog

v0.3.3 — 2026-05-07

Event-driven startup & toast notifications

  • Startup sync now triggers on server.connected event instead of setTimeout — the TUI is guaranteed to be ready before any notification appears
  • Guard flag prevents double-run if server.connected fires more than once
  • Every sync command (/sync-up, /sync-down, /sync-fix, /sync-connect, /sync-new, /sync-check, /sync-restore) now fires a tui.showToast popup with a descriptive summary
  • Variant (success / warning / error / info) is inferred from the result heading automatically
  • Errors also surface as error-variant toasts

v0.3.2 — 2026-05-07

Encryption, async git, conflict detection, log/restore commands

  • AES-256-GCM encryption for sensitive config values — set encryptionKey in opencode-sm.jsonc; values are encrypted before push and decrypted on pull
  • All git/gh calls converted to async (execFileAsync) with configurable timeouts — no more blocking the event loop
  • Proper JSONC parser — character-by-character parser replaces regex-based approach that was corrupting URLs inside strings
  • Conflict detection — files changed both locally and remotely are preserved locally and logged; no silent overwrites
  • New /sync-log command — shows recent commit history from the sync repo
  • New /sync-restore command — restores local config files from a backup
  • .syncignore support — create ~/.config/opencode/.syncignore for fine-grained exclusions
  • Atomic file writes — files written via tmp+rename; write manifests saved with rotation (max 10)
  • Machine name uniqueness check on /sync-connect
  • Health check on startup — verifies git, gh CLI, and git identity before syncing
  • Windows path fixdata and state directories are now distinct on Windows
  • BunShell typed correctly via PluginInput['$']

v0.3.1 — 2026-05-03

Rich UI, auto-pull on startup, toast notifications

  • Rich markdown output for all commands with badges, tables, and section headers
  • fmtStartupPull, fmtDown, fmtUp, fmtFix, fmtCheck, fmtRepo, fmtInit, fmtConnect formatters
  • Auto-pull on startup in safe mode (read remote, apply non-conflicting changes)
  • tui.showToast notifications for startup sync and command results
  • Expanded SENSITIVE_KEYS list for sanitization

v0.3.0 — 2026-05-01

Exclude paths, machine isolation, sync-fix, safer sync engine

  • excludePaths config field with glob pattern support
  • Machine isolation: machineName routes files to machines/<name>/ in the repo
  • New /sync-fix command to propagate pending local deletions
  • Safe mode (safe: true default) — startup never modifies files
  • Bidirectional conflict detection
  • Per-machine overrides (opencode-sm.overrides.jsonc)

v0.2.0

Initial public release

  • GitHub-based sync via gh CLI
  • /sync-new, /sync-connect, /sync-up, /sync-down, /sync-check, /sync-repo
  • Secret sanitization (JSON + regex)
  • Automatic local backups
  • extraConfigPaths support
  • includeSecrets opt-in for private repos

License

MIT