{"id":20669764,"url":"https://github.com/linuxfabrik/mirror","last_synced_at":"2025-12-25T03:12:03.809Z","repository":{"id":106416726,"uuid":"572497706","full_name":"Linuxfabrik/mirror","owner":"Linuxfabrik","description":"A script to create and update mirrors of RPM repositories using reposync. Runs on RHEL 8+.","archived":false,"fork":false,"pushed_at":"2025-12-01T09:29:08.000Z","size":80,"stargazers_count":3,"open_issues_count":1,"forks_count":3,"subscribers_count":0,"default_branch":"main","last_synced_at":"2025-12-03T20:59:45.700Z","etag":null,"topics":["linux","linuxfabrik","mirror","mirror-server","repositories","repository-management","reposync","rpm"],"latest_commit_sha":null,"homepage":"https://linuxfabrik.ch","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"unlicense","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Linuxfabrik.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2022-11-30T12:03:38.000Z","updated_at":"2025-12-01T09:29:13.000Z","dependencies_parsed_at":"2024-10-25T10:55:40.399Z","dependency_job_id":"098d228f-761b-45ce-b7bf-e77f947df408","html_url":"https://github.com/Linuxfabrik/mirror","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/Linuxfabrik/mirror","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Linuxfabrik%2Fmirror","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Linuxfabrik%2Fmirror/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Linuxfabrik%2Fmirror/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Linuxfabrik%2Fmirror/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Linuxfabrik","download_url":"https://codeload.github.com/Linuxfabrik/mirror/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Linuxfabrik%2Fmirror/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28017821,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-12-25T02:00:05.988Z","response_time":58,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["linux","linuxfabrik","mirror","mirror-server","repositories","repository-management","reposync","rpm"],"created_at":"2024-11-16T20:16:02.064Z","updated_at":"2025-12-25T03:12:03.802Z","avatar_url":"https://github.com/Linuxfabrik.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Mirror\n\nA script to create and update mirrors of RPM repositories using `reposync`.\n\nRuns on\n\n* RHEL 8 (and compatible)\n* RHEL 9 (and compatible)\n\n\n## Installation\n\nClone this repo:\n\n```bash\ncd /opt\ngit clone --recurse-submodules https://github.com/Linuxfabrik/mirror.git\n```\n\nCreate your configuration. The default path is `/etc/mirror.yml`. Have a look at the `example.yml` file and the synopsis below.\n\nInstall `yum-utils` and `createrepo`.\n\nUse a web server that points to the directory named `base_path` in the configuration file.\n\nIf using systemd, set up the timer and service to update your mirror at regular intervals:\n\n```bash\nuseradd --system --home-dir /opt/mirror --shell /bin/false mirror\n\ncd /opt/mirror\ncp -v systemd/mirror-update.service /etc/systemd/system/mirror-update.service\ncp -v systemd/mirror-update.timer /etc/systemd/system/mirror-update.timer\n\n# adjust the OnCalendar option\n$EDITOR /etc/systemd/system/mirror-update.timer\n\nsystemctl daemon-reload\nsystemctl enable --now mirror-update.timer\n\n# allow the mirror user to run dnf via sudo\ncp -v mirror.sudoers /etc/sudoers.d/mirror\n\n# make sure the base path exists and can be access both by the webserver user and the mirror user\nwebserver_user=apache\nbase_path='/var/www/html/github-repos'\n\nmkdir -p \"$base_path\"\n\nsetfacl --recursive --modify user:$webserver_user:rwx \"$base_path\"\nsetfacl --default --recursive --modify user:$webserver_user:rwx \"$base_path\"\n\nsetfacl --recursive --modify group:$webserver_user:rx \"$base_path\"\nsetfacl --default --recursive --modify group:$webserver_user:rx \"$base_path\"\n\nsetfacl --recursive --modify user:mirror:rwx \"$base_path\"\nsetfacl --default --recursive --modify user:mirror:rwx \"$base_path\"\n```\n\n\n## How to Provide a RPM-based Repository on your Mirror Server\n\nIf you want to provide an RPM-based repository, it must be present in `/etc/yum.repos.d`. However, it does not need to be enabled, so we generally recommend disabling it (to prevent the mirror server itself from accidentally using it).\n\nBest practice: Create a repo file named `/etc/yum.repos.d/mirror-\u003cOS\u003e-\u003cPackage\u003e-\u003cVersion\u003e.repo`. Use the same scheme for the repo filename and the repoid. Make sure you have `enabled=0` set so that the mirror itself is not using the repo.\n\nExample: `/etc/yum.repos.d/mirror-rhel8-mariadb-10.6.repo`\n\n```ini\n[mirror-rhel8-mariadb-10.6]\nname = MariaDB Server\nbaseurl = https://downloads.mariadb.com/MariaDB/mariadb-10.6/yum/rhel/8/$basearch\ngpgkey = file:///etc/pki/rpm-gpg/MariaDB-Server-GPG-KEY\ngpgcheck = 1\nenabled=0\nmodule_hotfixes = 1\n```\n\nIn `/etc/mirror.yml`, set the location for the repo to be mirrored. This path should be unique to prevent multiple repos from overwriting each other. The path will then be created by the script.\n\n```yaml\nbase_path: '/var/www/html/mirror'\nreposync_repos:\n  - repoid: 'mirror-rhel8-mariadb-10.6'\n    relative_target_path: 'MariaDB/mariadb-10.6/yum/rhel/8/x86_64'\n```\n\nDetermine whether or not it is necessary to run `createrepo`. If the mirrored repo is not identical to the upstream repo (e.g. due to `includepkgs` or `excludepkgs` directives), you need to run `createrepo`. If this is not the case, you should avoid running it, as it will destroy RHEL's module information.\n\nNow run the commands manually for the first time to accept the GPG keys. For example:\n\n```bash\nBASE_PATH='/var/www/html/mirror'\nREPOID='mirror-rhel8-mariadb-10.6'\nRELATIVE_TARGET_PATH='MariaDB/mariadb-10.6/yum/rhel/8/x86_64'\nsudo -u mirror reposync --repoid=\"$REPOID\" --download-path=\"$BASE_PATH/$RELATIVE_TARGET_PATH\" --norepopath --downloadcomps --download-metadata\n\n# createrepo \"$BASE_PATH/$RELATIVE_TARGET_PATH\"\n\nchown -R apache:apache $BASE_PATH\nrestorecon -Fvr $BASE_PATH\n```\n\n## Synopsis - The Configuration File\n\n`base_path`: Mandatory, string. Directory under which all the repos will be placed. This directory has to exist already and should be served by a webserver.\n\n`reposync_repos`: Optional, list. List of repositories to mirror using `reposync`.\u003cbr\u003eSubkeys:\n\n* `repoid`: Mandatory, string. Repo-ID. Can be found using `dnf repolist`.\n* `relative_target_path`: Mandatory, string. Target path where the repo should be placed, relative to `base_path`.\n* `createrepo`: Optional, boolean. If `createrepo` should be ran on the repo after mirroring or not. Only use this if the mirrored repo is not idential to the upstream repo (for example due to `includepkgs` or `excludepkgs` directives). Else, you should avoid running it, since it destroys RHEL's module information. Defaults to `false`.\n\n\n## Exit Codes\n\n* 0: success / config valid\n* 1: failed to read config / config invalid\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flinuxfabrik%2Fmirror","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flinuxfabrik%2Fmirror","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flinuxfabrik%2Fmirror/lists"}