SlopScore
00 crowd

gitsyncer

Tool to sync git repos across Codeberg, Github and SSH git server.
Open repo on GitHubgithub.com/snonux/gitsyncer
Go · ★ 2 · 0 forks · BSD-2-Clause · paperwork by the Cap'mmostly ai (inferred)light human (inferred)works-on-my-machine (inferred)other
listed 2 hours ago by snonux · last checked 2 hours ago
The owner didn't write this. This repo never submitted itself. The Cap'm found it on a truffle trawl and wrote its paperwork from what GitHub already shows. Picked by hand by the Cap'm on 2026-10-12: Tool to sync git repos across Codeberg, Github and SSH git server.; its own README says "It has been vibe coded mainly using AI tools (Claude Code CLI and amp)". 2 stars; BSD-2-Clause license. The owner did not submit this. Votes count; awards don't until the owner claims it.

I'm not calling your project slop! Geeze, it's a joke... Do you own this repo?

Log in with GitHub as snonux. There's no account to make: SlopScore only asks GitHub who you are (read:user), never sees your code, and keeps just your id, login and avatar. Then you can:

  • Keep it, on your terms. Commit your own slopscore.md (spec) and press Refresh. Your paperwork replaces the Cap'm's, and you can submit it for Slop of the Day.
  • Take it down. One click on Remove. It stays gone; the trawl never brings it back.

Log in with GitHub

Can't log in as the owner? Request a takedown. No login needed, and a trawled listing comes down right away.

GitHub says
Tool to sync git repos across Codeberg, Github and SSH git server.
created
2025-06-23 · pushed 2 hours ago · 279 commits · 1 contributor
release
v0.19.3 · 2026-08-21
languages
Go 97%Shell 3%Go Template 1%
paperwork
licensereadme 42% health
dependencies
no dependency graph (no manifest, or disabled) · OSV.dev, checked 2 hours ago

Disclosures, inferred by the Cap'm

slopbucket
vibe-coded
category
other
ai_generated
mostly
human_touch
light
status
works-on-my-machine
language (detected)
gogo-templateshell
license (detected)
bsd-2-clause

The Cap'm's log

The Cap'm wrote this paperwork, not the owner. This repo never submitted itself to SlopScore. The Cap'm picked it by hand: Tool to sync git repos across Codeberg, Github and SSH git server.; its own README says "It has been vibe coded mainly using AI tools (Claude Code CLI and amp)". It carries the BSD-2-Clause license. The disclosures above are his best guess from what GitHub shows.

Is this yours? Commit a real slopscore.md and press Refresh to replace this, or remove the listing in one click. There's no account to make: you log in with GitHub.

README — the repo's own words, folded up so the grading fits on one screen

GitSyncer

GitSyncer is a tool for synchronizing git repositories between multiple organizations (e.g., GitHub and Forgejo). It automatically keeps all branches in sync across different git hosting platforms.

It has been vibe coded mainly using AI tools (Claude Code CLI and amp).

Documentation

📚 Full documentation is available in the doc/ directory

Features

  • Sync repositories between multiple git organizations
  • Automatic branch creation on remotes that don't have them
  • Batch sync multiple repositories with a single command
  • Discover and sync public GitHub repositories to configured destinations
  • Automatic repository creation on GitHub and Forgejo
  • SSH backup locations with automatic bare repository creation
  • One-way backup to private SSH servers (e.g., home NAS)
  • Merge conflict detection with clear error messages
  • Never deletes branches (only adds/updates)
  • GitHub token validation tool
  • Backup sync for full-sync modes, with --backup available for single-repo and sync all runs
  • Per-destination backup fail-fast for a run: after a backup fails, later repos skip only that destination
  • Default once-daily sync limit with --force override
  • Opt-in sync throttling with --throttle based on local activity
  • AI-powered project showcase generation for documentation
  • Weekly batch run mode with manage batch-run for automated synchronization

Installation

go build -o gitsyncer ./cmd/gitsyncer

Configuration

Create a configuration file at ~/.config/gitsyncer/config.json (or specify a custom path with -c):

{
  "organizations": [
    {
      "host": "ssh://git@forgejo.example",
      "name": "yourusername",
      "forgejo_api_base": "https://forgejo.example/api/v1",
      "forgejo_owner": "yourusername"
    },
    {
      "host": "git@github.com",
      "name": "yourusername"
    },
    {
      "host": "user@nas.local:git",
      "backupLocation": true,
      "forcePush": true,
      "descriptionSyncHost": "root@nas.local",
      "descriptionSyncRoot": "/srv/git/repos"
    }
  ],
  "repositories": [
    "repo1",
    "repo2"
  ],
  "showcase_output_dir": "~/git/foo.zone-content/gemtext/about",
  "showcase_stats_branches": {
    "foo.zone": "content-gemtext"
  },
}

Usage

Command Structure

GitSyncer uses a modern command-based structure that provides:

  • Clear organization of related functionality
  • Built-in help for every command and subcommand
  • Consistent flag naming and behavior
  • Better discoverability of features

Quick Start

Explore available commands and get help:

# Show available commands
gitsyncer --help

# Show help for a specific command
gitsyncer sync --help

Synchronization Commands

gitsyncer sync repo myproject

# Include backup locations for a single repository run
gitsyncer sync repo myproject --backup

# Preview what would be synced
gitsyncer sync repo myproject --dry-run

# Override sync interval checks
gitsyncer sync repo myproject --force

# Sync without AI-generated release notes
gitsyncer sync repo myproject --no-ai-release-notes

# Auto-create releases without prompts (AI notes enabled by default)
gitsyncer sync repo myproject --auto-create-releases

Each repository is synced at most once every 24 hours by default. Successful sync times are stored in .gitsyncer-state.json inside the work directory. Use --force to bypass sync interval checks.

Throttled sync

# Throttle syncing based on local activity in ~/git/<repo>
gitsyncer sync repo myproject --throttle

# Throttle all public repo sync modes
gitsyncer sync bidirectional --throttle
gitsyncer sync github-to-forgejo --throttle

When --throttle is enabled, GitSyncer still applies the default once-daily limit first, then checks ~/git/<repo> for commits in the last 7 days. If no recent commits are found (or the repo is missing locally), the repo sync is allowed only once per random interval between 60 and 120 days and the next allowed date is stored. Sync state is stored in .gitsyncer-state.json in the work directory. Use --force to bypass both interval checks.

Sync all configured repositories

gitsyncer sync all

# Include backup locations when running sync all
gitsyncer sync all --backup

Full bidirectional sync

# Complete bidirectional sync of all public repos
gitsyncer sync bidirectional

# Preview what would be synced
gitsyncer sync bidirectional --dry-run

sync bidirectional, sync github-to-forgejo, and manage batch-run now always try configured backup locations when backupLocation: true is present in the config. If a backup push fails because that host is offline or unavailable, GitSyncer records that failure in memory and skips that destination for the rest of the process while continuing the primary sync targets and other backups.

Forgejo can be used as a one-way public backup, as a one-way mirror that is pushed on every run, or as an optional bidirectional sync peer. Repository creation and descriptions use its Gitea-compatible API, while Git data is transferred over SSH. To make it a peer that is fetched, merged, and pushed whenever available, set optional: true instead of backupLocation:

{
  "organizations": [{
    "host": "ssh://git@code.f3s.buetow.org:2022",
    "forgejo_api_base": "https://code.f3s.buetow.org/api/v1",
    "forgejo_owner": "snonux",
    "forgejo_owner_type": "organization",
    "optional": true
  }]
}

To mirror GitHub to Forgejo one way, set pushOnly: true (it may be combined with optional: true so an unreachable Forgejo is skipped instead of failing the run):

{
  "organizations": [{
    "host": "ssh://git@code.f3s.buetow.org:2022",
    "forgejo_api_base": "https://code.f3s.buetow.org/api/v1",
    "forgejo_owner": "snonux",
    "forgejo_owner_type": "organization",
    "optional": true,
    "pushOnly": true
  }]
}

A pushOnly organization is pushed on every sync (no --backup needed) but is never fetched, merged, or cloned from, so commits, branches, and tags that exist only there never reach GitHub. While a pushOnly organization is configured, the GitHub discovery commands (sync github-to-forgejo, sync bidirectional, manage batch-run) sync every public, non-fork, non-archived GitHub repository instead of only those in repositories; that list then only decides which repositories also go to Forgejo. Pushes are not forced unless forcePush: true is set, so a branch or tag that diverged on the mirror makes its push fail rather than being overwritten. GitSyncer never deletes branches or tags on the mirror.

Set an API token with the minimal scopes for the configured owner type: write:repository plus write:organization for an organization, or write:repository plus write:user for a user. The owner type may be user (the default for backward compatibility) or organization. For an organization owner, use a token from an interactive user that is authorized to create repositories in that organization; an organization pseudo-user cannot issue a usable token. Store the token in protected process environment as FORGEJO_TOKEN, or store it in ~/.gitsyncer_forgejo_token with mode 0600. The environment takes precedence; surrounding whitespace is removed from either source. Never put a Forgejo token in the JSON configuration. A repository named demo uses ssh://git@code.f3s.buetow.org:2022/snonux/demo.git. Forgejo targets with backupLocation: true or pushOnly: true are never fetched. Targets with only optional: true participate fully in branch discovery, fetch, merge, and push. Metadata API failures are reported but do not prevent Git-over-SSH synchronization; a fetch or push failure skips that Forgejo peer for the remainder of the run without interrupting synchronization between the other hosts. GitSyncer never runs remote shell repository-creation or description-file commands for Forgejo. When a Forgejo organization is configured and FORGEJO_TOKEN (or ~/.gitsyncer_forgejo_token) is available, release checking also creates and updates releases on Forgejo using the same Gitea-compatible API.

Release Management

Check for missing releases

# Check all repositories
gitsyncer release check

# Check specific repository
gitsyncer release check myproject

Create releases

# Create releases with confirmation prompts (AI notes enabled by default)
gitsyncer release create

# Auto-create without prompts
gitsyncer release create --auto

# Create without AI-generated notes
gitsyncer release create --no-ai-notes

# Update existing releases with AI notes
gitsyncer release create --update-existing

# Create for specific repository without AI
gitsyncer release create myproject --no-ai-notes

# Use amp for AI release notes
gitsyncer release create --ai-tool amp

AI Release Notes Engines

  • Default flow: tries ollama run glm-5.3-flash:cloud first with the commit/diff payload and instruction prompt combined into a single argument (--hidethinking so chain-of-thought is not captured).
  • Fallback: if ollama is not available or fails, falls back to hexai, then claude --model sonnet, then amp.
  • Explicit tool: --ai-tool hexai, --ai-tool claude, --ai-tool amp, etc. adjust the fallback chain order. OpenRouter/pi is no longer used.
  • Requirements: ensure ollama, hexai, claude, or amp are installed and available in PATH.

Project Showcase

# Generate showcase with cached summaries
gitsyncer showcase

# Force regeneration of all summaries
gitsyncer showcase --force

# Generate showcase for one repository
gitsyncer showcase --repo gitsyncer

# Use a specific AI tool
gitsyncer showcase --ai-tool opencode

Repository Management

Delete repository

# Delete repository from all organizations (with confirmation)
gitsyncer manage delete-repo old-project

Clean workspace

# Clean work directory (with confirmation)
gitsyncer manage clean

# Force clean without confirmation
gitsyncer manage clean --force

Automated weekly sync

# Run weekly batch sync (full sync + showcase)
gitsyncer manage batch-run

# Force run even if already run this week
gitsyncer manage batch-run --force

Testing and Information

Test authentication

# Test GitHub token
gitsyncer test github-token

# # Validate configuration
gitsyncer test config

List configured items

# List organizations
gitsyncer list orgs

# List repositories
gitsyncer list repos

Show version

gitsyncer version

Global Options

These options are available for all commands:

  • -c, --config - Path to configuration file (default: ~/.config/gitsyncer/config.json)
  • -w, --work-dir - Working directory (default: ~/git/gitsyncer-workdir)
  • -h, --help - Show help for any command

The --backup Flag

The --backup flag enables syncing to backup locations configured in your config file. This is particularly useful when:

  • Your backup server might be offline (e.g., home NAS)
  • You want to control when backups happen
  • You need to separate regular syncing from backup operations

Without --backup: GitSyncer only syncs between primary git hosts (GitHub, Forgejo, etc.) With --backup: GitSyncer also pushes to backup locations marked with "backupLocation": true

# Regular sync (backup locations ignored)
gitsyncer sync repo myrepo

# Sync with backup enabled
gitsyncer sync repo myrepo --backup

How It Works

  1. GitSyncer clones the repository from the first configured organization
  2. Adds all other organizations as git remotes
  3. For each branch:
    • Fetches from all remotes
    • Merges changes from remotes that have the branch
    • Pushes to all remotes (creating branches if needed)

Branch Selection and Exclusion

By default, GitSyncer synchronizes only main, master, and develop. Set a global list with branches, then override it for individual repositories with repository_branches:

{
  "branches": ["main", "stable"],
  "repository_branches": {
    "legacy-app": ["master", "release"]
  }
}

Branches outside the selected list are not synchronized. You can also exclude branches from that list using regex patterns in exclude_branches:

{
  "organizations": [...],
  "repositories": [...],
  "branches": ["main", "master", "develop"],
  "exclud

Read the rest on GitHub

Scan report · 2026-10-12
  • ✓ Prohibited terms or links
  • ✓ Repository eligibility
  • ✓ slopscore.md paperwork
  • ✓ Content policy
  • ✓ Risk review

0 comments

log in to comment.

report this listing — log in to report