mirror of
https://github.com/Andre-Bzk/github-to-gitea-mirror.git
synced 2026-11-15 15:43:12 +01:00
Compare commits
2
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c8098da66a | ||
|
|
45f414dd64 |
@@ -0,0 +1,41 @@
|
||||
name: Deploy GitHub Pages
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
paths:
|
||||
- docs/**
|
||||
- .github/workflows/pages.yml
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
pages: write
|
||||
id-token: write
|
||||
|
||||
concurrency:
|
||||
group: pages
|
||||
cancel-in-progress: false
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
environment:
|
||||
name: github-pages
|
||||
url: ${{ steps.deployment.outputs.page_url }}
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v6
|
||||
|
||||
- name: Setup Pages
|
||||
uses: actions/configure-pages@v5
|
||||
|
||||
- name: Upload artifact
|
||||
uses: actions/upload-pages-artifact@v4
|
||||
with:
|
||||
path: docs
|
||||
|
||||
- name: Deploy to GitHub Pages
|
||||
id: deployment
|
||||
uses: actions/deploy-pages@v4
|
||||
@@ -24,6 +24,11 @@ Keeping the repositories' *git content* up to date remains Gitea's job.
|
||||
| Pull new commits into **existing** mirrors | Gitea itself | `MIRROR_INTERVAL` |
|
||||
| Synchronize release metadata and uploaded assets | this script (cron) | daily |
|
||||
|
||||
### Architecture
|
||||
|
||||
- [Architecture diagram](https://andre-bzk.github.io/github-to-gitea-mirror/architecture/sync_mirrors.architecture.html)
|
||||
- [Sequence diagram](https://andre-bzk.github.io/github-to-gitea-mirror/architecture/sync_mirrors.sequence.html)
|
||||
|
||||
### Requirements
|
||||
|
||||
- Gitea 1.20+ with an API token (scopes `write:repository,read:user`)
|
||||
@@ -234,6 +239,11 @@ bleibt Giteas Aufgabe.
|
||||
| Commits in **bestehende** Mirrors holen | Gitea selbst | `MIRROR_INTERVAL` |
|
||||
| Release-Metadaten und hochgeladene Assets synchronisieren | dieses Skript (Cron) | täglich |
|
||||
|
||||
### Architektur
|
||||
|
||||
- [Architecture-Diagramm](https://andre-bzk.github.io/github-to-gitea-mirror/architecture/sync_mirrors.architecture.html)
|
||||
- [Sequence-Diagramm](https://andre-bzk.github.io/github-to-gitea-mirror/architecture/sync_mirrors.sequence.html)
|
||||
|
||||
### Voraussetzungen
|
||||
|
||||
- Gitea 1.20+ mit API-Token (Scopes `write:repository,read:user`)
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,258 @@
|
||||
{
|
||||
"schema_version": 1,
|
||||
"diagram_type": "architecture",
|
||||
"meta": {
|
||||
"title": "GitHub to Gitea Mirror Architecture",
|
||||
"subtitle": "Runtime components and trust boundaries used by sync_mirrors.py for repository mirrors, releases, and streamed release assets",
|
||||
"output": "sync_mirrors.architecture.html",
|
||||
"viewBox": [1180, 780],
|
||||
"animation": "none",
|
||||
"visual_preset": "blueprint",
|
||||
"quality_profile": "showcase",
|
||||
"repository": {
|
||||
"url": "https://github.com/Andre-Bzk/github-to-gitea-mirror.git",
|
||||
"revision": "18e926a764b6ee969ea61132bd446e22ab250a5b"
|
||||
},
|
||||
"views": [
|
||||
{
|
||||
"id": "local-runtime",
|
||||
"label": "Local runtime",
|
||||
"focus": ["runner", "config", "script", "tmp_asset"],
|
||||
"note": "The scheduled or manual run loads configuration and keeps large assets out of RAM."
|
||||
},
|
||||
{
|
||||
"id": "repository-sync",
|
||||
"label": "Repository mirror sync",
|
||||
"focus": ["script", "github_api", "github_repos", "gitea_api", "gitea_mirrors"],
|
||||
"note": "GitHub repository inventory drives Gitea mirror creation and interval alignment."
|
||||
},
|
||||
{
|
||||
"id": "release-assets",
|
||||
"label": "Release and asset sync",
|
||||
"focus": ["script", "github_releases", "tmp_asset", "gitea_releases"],
|
||||
"note": "Release metadata is reconciled and missing assets stream through a temporary file."
|
||||
}
|
||||
]
|
||||
},
|
||||
"components": [
|
||||
{
|
||||
"id": "runner",
|
||||
"type": "external",
|
||||
"label": "Runner",
|
||||
"sublabel": "cron or shell",
|
||||
"pos": [70, 355],
|
||||
"size": [126, 62]
|
||||
},
|
||||
{
|
||||
"id": "config",
|
||||
"type": "security",
|
||||
"label": "Config",
|
||||
"sublabel": "env + tokens",
|
||||
"pos": [305, 155],
|
||||
"size": [134, 64],
|
||||
"sources": [
|
||||
{
|
||||
"path": "sync_mirrors.py",
|
||||
"label": "load_config"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "script",
|
||||
"type": "backend",
|
||||
"label": "Sync Script",
|
||||
"sublabel": "coordinator",
|
||||
"pos": [300, 355],
|
||||
"size": [144, 66],
|
||||
"sources": [
|
||||
{
|
||||
"path": "sync_mirrors.py",
|
||||
"label": "main"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "tmp_asset",
|
||||
"type": "database",
|
||||
"label": "Temp Asset",
|
||||
"sublabel": "chunk buffer",
|
||||
"pos": [565, 430],
|
||||
"size": [144, 64],
|
||||
"sources": [
|
||||
{
|
||||
"path": "sync_mirrors.py",
|
||||
"label": "download asset"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "github_api",
|
||||
"type": "cloud",
|
||||
"label": "GitHub API",
|
||||
"sublabel": "REST",
|
||||
"pos": [565, 165],
|
||||
"size": [136, 64],
|
||||
"tag": "Bearer token"
|
||||
},
|
||||
{
|
||||
"id": "github_repos",
|
||||
"type": "database",
|
||||
"label": "Source Repos",
|
||||
"sublabel": "owned projects",
|
||||
"pos": [810, 95],
|
||||
"size": [142, 64]
|
||||
},
|
||||
{
|
||||
"id": "github_releases",
|
||||
"type": "database",
|
||||
"label": "GH Releases",
|
||||
"sublabel": "metadata + assets",
|
||||
"pos": [810, 255],
|
||||
"size": [148, 64]
|
||||
},
|
||||
{
|
||||
"id": "gitea_api",
|
||||
"type": "cloud",
|
||||
"label": "Gitea API",
|
||||
"sublabel": "local or LAN",
|
||||
"pos": [565, 610],
|
||||
"size": [136, 64],
|
||||
"tag": "token"
|
||||
},
|
||||
{
|
||||
"id": "gitea_mirrors",
|
||||
"type": "database",
|
||||
"label": "Pull Mirrors",
|
||||
"sublabel": "git backup",
|
||||
"pos": [810, 540],
|
||||
"size": [142, 64]
|
||||
},
|
||||
{
|
||||
"id": "gitea_releases",
|
||||
"type": "database",
|
||||
"label": "Gitea Releases",
|
||||
"sublabel": "metadata + assets",
|
||||
"pos": [810, 680],
|
||||
"size": [150, 64]
|
||||
}
|
||||
],
|
||||
"boundaries": [
|
||||
{
|
||||
"kind": "region",
|
||||
"label": "Local host running sync_mirrors.py",
|
||||
"wraps": ["runner", "config", "script", "tmp_asset"]
|
||||
},
|
||||
{
|
||||
"kind": "security-group",
|
||||
"label": "Configuration and credentials",
|
||||
"wraps": ["config"]
|
||||
},
|
||||
{
|
||||
"kind": "region",
|
||||
"label": "GitHub account",
|
||||
"wraps": ["github_api", "github_repos", "github_releases"]
|
||||
},
|
||||
{
|
||||
"kind": "region",
|
||||
"label": "Gitea instance",
|
||||
"wraps": ["gitea_api", "gitea_mirrors", "gitea_releases"]
|
||||
}
|
||||
],
|
||||
"connections": [
|
||||
{
|
||||
"id": "starts",
|
||||
"from": "runner",
|
||||
"to": "script",
|
||||
"label": "starts run",
|
||||
"variant": "emphasis",
|
||||
"labelDy": 46
|
||||
},
|
||||
{
|
||||
"id": "loads",
|
||||
"from": "script",
|
||||
"to": "config",
|
||||
"label": "loads settings",
|
||||
"variant": "security"
|
||||
},
|
||||
{
|
||||
"id": "lists-repos",
|
||||
"from": "script",
|
||||
"to": "github_api",
|
||||
"label": "lists repos",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "repo-source",
|
||||
"from": "github_api",
|
||||
"to": "github_repos",
|
||||
"label": "reads",
|
||||
"variant": "default"
|
||||
},
|
||||
{
|
||||
"id": "checks-mirror",
|
||||
"from": "script",
|
||||
"to": "gitea_api",
|
||||
"label": "checks mirrors",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "mirror-target",
|
||||
"from": "gitea_api",
|
||||
"to": "gitea_mirrors",
|
||||
"label": "create or patch",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "asset-download",
|
||||
"from": "github_releases",
|
||||
"to": "tmp_asset",
|
||||
"label": "streams asset",
|
||||
"variant": "dashed"
|
||||
},
|
||||
{
|
||||
"id": "asset-upload",
|
||||
"from": "tmp_asset",
|
||||
"to": "gitea_api",
|
||||
"label": "uploads asset",
|
||||
"variant": "dashed",
|
||||
"fromSide": "bottom",
|
||||
"toSide": "top"
|
||||
},
|
||||
{
|
||||
"id": "release-api",
|
||||
"from": "gitea_api",
|
||||
"to": "gitea_releases",
|
||||
"label": "create or patch",
|
||||
"variant": "default"
|
||||
}
|
||||
],
|
||||
"cards": [
|
||||
{
|
||||
"dot": "cyan",
|
||||
"title": "Primary responsibility",
|
||||
"items": [
|
||||
"GitHub is the source of repository and release inventory",
|
||||
"The script creates missing Gitea pull mirrors and aligns mirror intervals",
|
||||
"Existing Gitea content is preserved rather than deleted"
|
||||
]
|
||||
},
|
||||
{
|
||||
"dot": "rose",
|
||||
"title": "Trust boundary",
|
||||
"items": [
|
||||
"GitHub requests use a Bearer token when configured",
|
||||
"Gitea requests use token authentication",
|
||||
"Config values come from mirror.env and environment variables"
|
||||
]
|
||||
},
|
||||
{
|
||||
"dot": "emerald",
|
||||
"title": "Asset path",
|
||||
"items": [
|
||||
"Release assets are downloaded in chunks",
|
||||
"A temporary file avoids buffering large assets in memory",
|
||||
"Multipart upload sends the same stream to Gitea"
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,318 @@
|
||||
{
|
||||
"schema_version": 1,
|
||||
"diagram_type": "sequence",
|
||||
"meta": {
|
||||
"title": "GitHub to Gitea Mirror Sync",
|
||||
"subtitle": "Runtime sequence of sync_mirrors.py: config, repository mirroring, release sync, streamed asset copy, orphan check, and exit status",
|
||||
"output": "sync_mirrors.sequence.html",
|
||||
"viewBox": [940, 1060],
|
||||
"animation": "none",
|
||||
"visual_preset": "signal-flow",
|
||||
"quality_profile": "showcase",
|
||||
"views": [
|
||||
{
|
||||
"id": "startup",
|
||||
"label": "Startup and repository list",
|
||||
"focus": ["runner", "script", "config", "github"],
|
||||
"note": "The script merges file and environment config, then lists owned GitHub repositories."
|
||||
},
|
||||
{
|
||||
"id": "repo-loop",
|
||||
"label": "Repository mirror loop",
|
||||
"focus": ["script", "github", "gitea"],
|
||||
"note": "Each GitHub repository is matched against Gitea before migration or interval alignment."
|
||||
},
|
||||
{
|
||||
"id": "release-assets",
|
||||
"label": "Release and asset sync",
|
||||
"focus": ["github", "script", "tmpfile", "gitea"],
|
||||
"note": "Release metadata is reconciled and missing assets stream through a temporary file."
|
||||
}
|
||||
]
|
||||
},
|
||||
"participants": [
|
||||
{
|
||||
"id": "runner",
|
||||
"type": "external",
|
||||
"label": "Runner",
|
||||
"sublabel": "cron or shell"
|
||||
},
|
||||
{
|
||||
"id": "script",
|
||||
"type": "backend",
|
||||
"label": "Sync Script",
|
||||
"sublabel": "mirror coordinator"
|
||||
},
|
||||
{
|
||||
"id": "config",
|
||||
"type": "security",
|
||||
"label": "Config",
|
||||
"sublabel": "mirror.env + env"
|
||||
},
|
||||
{
|
||||
"id": "github",
|
||||
"type": "cloud",
|
||||
"label": "GitHub API",
|
||||
"sublabel": "repos, releases"
|
||||
},
|
||||
{
|
||||
"id": "gitea",
|
||||
"type": "cloud",
|
||||
"label": "Gitea API",
|
||||
"sublabel": "mirrors and releases"
|
||||
},
|
||||
{
|
||||
"id": "tmpfile",
|
||||
"type": "database",
|
||||
"label": "Temp File",
|
||||
"sublabel": "streamed asset buffer"
|
||||
}
|
||||
],
|
||||
"segments": [
|
||||
{
|
||||
"from": 150,
|
||||
"to": 318,
|
||||
"label": "Startup"
|
||||
},
|
||||
{
|
||||
"from": 334,
|
||||
"to": 578,
|
||||
"label": "Mirror loop"
|
||||
},
|
||||
{
|
||||
"from": 596,
|
||||
"to": 844,
|
||||
"label": "Release sync"
|
||||
},
|
||||
{
|
||||
"from": 862,
|
||||
"to": 960,
|
||||
"label": "Finish"
|
||||
}
|
||||
],
|
||||
"messages": [
|
||||
{
|
||||
"id": "run-script",
|
||||
"from": "runner",
|
||||
"to": "script",
|
||||
"y": 180,
|
||||
"label": "start sync run",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "load-config",
|
||||
"from": "script",
|
||||
"to": "config",
|
||||
"y": 222,
|
||||
"label": "load defaults, mirror.env, environment",
|
||||
"variant": "security"
|
||||
},
|
||||
{
|
||||
"id": "config-values",
|
||||
"from": "config",
|
||||
"to": "script",
|
||||
"y": 264,
|
||||
"label": "normalized settings",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "list-repos",
|
||||
"from": "script",
|
||||
"to": "github",
|
||||
"y": 306,
|
||||
"label": "list owned repositories",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "repos-back",
|
||||
"from": "github",
|
||||
"to": "script",
|
||||
"y": 348,
|
||||
"label": "repos + token expiry header",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "check-repo",
|
||||
"from": "script",
|
||||
"to": "gitea",
|
||||
"y": 390,
|
||||
"label": "query matching repository",
|
||||
"variant": "default"
|
||||
},
|
||||
{
|
||||
"id": "repo-state",
|
||||
"from": "gitea",
|
||||
"to": "script",
|
||||
"y": 432,
|
||||
"label": "existing mirror or 404",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "create-or-align",
|
||||
"from": "script",
|
||||
"to": "gitea",
|
||||
"y": 474,
|
||||
"label": "migrate missing mirror or patch interval",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "mirror-result",
|
||||
"from": "gitea",
|
||||
"to": "script",
|
||||
"y": 516,
|
||||
"label": "mirror created or updated",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "get-source-releases",
|
||||
"from": "script",
|
||||
"to": "github",
|
||||
"y": 618,
|
||||
"label": "list repository releases",
|
||||
"variant": "default"
|
||||
},
|
||||
{
|
||||
"id": "source-releases",
|
||||
"from": "github",
|
||||
"to": "script",
|
||||
"y": 660,
|
||||
"label": "source release metadata",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "get-target-releases",
|
||||
"from": "script",
|
||||
"to": "gitea",
|
||||
"y": 702,
|
||||
"label": "list releases and tags",
|
||||
"variant": "default"
|
||||
},
|
||||
{
|
||||
"id": "target-state",
|
||||
"from": "gitea",
|
||||
"to": "script",
|
||||
"y": 744,
|
||||
"label": "target releases, assets, tags",
|
||||
"variant": "return"
|
||||
},
|
||||
{
|
||||
"id": "upsert-release",
|
||||
"from": "script",
|
||||
"to": "gitea",
|
||||
"y": 786,
|
||||
"label": "create or patch changed release",
|
||||
"variant": "emphasis"
|
||||
},
|
||||
{
|
||||
"id": "download-asset",
|
||||
"from": "github",
|
||||
"to": "tmpfile",
|
||||
"y": 828,
|
||||
"label": "stream missing asset",
|
||||
"variant": "dashed"
|
||||
},
|
||||
{
|
||||
"id": "upload-asset",
|
||||
"from": "tmpfile",
|
||||
"to": "gitea",
|
||||
"y": 870,
|
||||
"label": "multipart upload",
|
||||
"variant": "dashed"
|
||||
},
|
||||
{
|
||||
"id": "orphan-check",
|
||||
"from": "script",
|
||||
"to": "gitea",
|
||||
"y": 912,
|
||||
"label": "list mirrors for orphan warning",
|
||||
"variant": "default"
|
||||
},
|
||||
{
|
||||
"id": "exit-code",
|
||||
"from": "script",
|
||||
"to": "runner",
|
||||
"y": 954,
|
||||
"label": "summary log and exit code",
|
||||
"variant": "return"
|
||||
}
|
||||
],
|
||||
"activations": [
|
||||
{
|
||||
"participant": "script",
|
||||
"from": 174,
|
||||
"to": 960,
|
||||
"type": "backend"
|
||||
},
|
||||
{
|
||||
"participant": "config",
|
||||
"from": 216,
|
||||
"to": 270,
|
||||
"type": "security"
|
||||
},
|
||||
{
|
||||
"participant": "github",
|
||||
"from": 300,
|
||||
"to": 354,
|
||||
"type": "cloud"
|
||||
},
|
||||
{
|
||||
"participant": "gitea",
|
||||
"from": 384,
|
||||
"to": 522,
|
||||
"type": "cloud"
|
||||
},
|
||||
{
|
||||
"participant": "github",
|
||||
"from": 612,
|
||||
"to": 666,
|
||||
"type": "cloud"
|
||||
},
|
||||
{
|
||||
"participant": "gitea",
|
||||
"from": 696,
|
||||
"to": 792,
|
||||
"type": "cloud"
|
||||
},
|
||||
{
|
||||
"participant": "tmpfile",
|
||||
"from": 822,
|
||||
"to": 876,
|
||||
"type": "database"
|
||||
},
|
||||
{
|
||||
"participant": "gitea",
|
||||
"from": 864,
|
||||
"to": 918,
|
||||
"type": "cloud"
|
||||
}
|
||||
],
|
||||
"cards": [
|
||||
{
|
||||
"dot": "cyan",
|
||||
"title": "Mirror ownership",
|
||||
"items": [
|
||||
"GitHub repositories drive the run; Gitea state is reconciled per repository",
|
||||
"Existing non-mirror repositories are warned about and left untouched",
|
||||
"Deleted or renamed upstream repositories are reported as orphaned mirrors"
|
||||
]
|
||||
},
|
||||
{
|
||||
"dot": "orange",
|
||||
"title": "Release policy",
|
||||
"items": [
|
||||
"Release metadata is created or patched only when fields differ",
|
||||
"Draft handling waits until the mirrored tag exists in Gitea",
|
||||
"No Gitea-side release or asset is deleted by the script"
|
||||
]
|
||||
},
|
||||
{
|
||||
"dot": "emerald",
|
||||
"title": "Asset streaming",
|
||||
"items": [
|
||||
"GitHub assets download in chunks into a temporary file",
|
||||
"Multipart upload streams the temporary file to Gitea",
|
||||
"Existing same-name assets are preserved, with size mismatch warnings"
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
Reference in New Issue
Block a user