Diagnosing Weblate Git Sync Failures in Self-Hosted Deployments
A diagnostic guide for self-hosted Weblate 4.x–5.x Git sync failures: recognizable alerts, cause table, ordered checks, targeted fixes, escalation criteria, and verification steps.
04 May 2026, 04:42 UTC

Recognizable Condition
Weblate's component dashboard displays Repository push failed or Repository pull failed alerts. Translation changes made in Weblate do not appear in the upstream Git repository, or commits pushed directly to the remote are not reflected in Weblate.
Cause and Diagnostic Quick Reference
| Symptom | Likely Cause | Primary Diagnostic Command |
|---|---|---|
| Non‑fast‑forward push rejected | Diverged history (local and remote branches have different commits) | git log --oneline -10 on the container's repo |
| Authentication failure | Expired SSH key, revoked personal access token, or mis‑configured credential store | ssh -T [contact removed] (or provider equivalent) from the Weblate container |
| Missing remote branch | Component configured for a branch that does not exist on the remote | git ls-remote origin |
| Remote hook rejection | Branch protection rules blocking Weblate's bot user (e.g., require PR, signed commits) | Check remote provider's branch protection settings and webhook delivery logs |
| Lock timeout | Concurrent Celery workers or git gc holding /app/data/vcs/*/lock | ls -la /app/data/vcs/ and ps aux | grep git |
| Merge conflict | Upstream changes conflict with Weblate's pending commits | git status in the component repo |
| Submodule failure | Submodules not initialized or updated | git submodule status |
| Git LFS quota exceeded | Large files tracked by LFS but LFS not installed or quota full | git lfs ls-files |
| Webhook misconfiguration | Secret rotated in Weblate but not updated on remote, or URL incorrect | Inspect remote repository's webhook delivery history |
| API rate limit | Provider limits (GitHub 5 000 req/hr per token, GitLab 600 req/min) exceeded | Check response headers X-RateLimit-Remaining or provider dashboard |
Ordered Diagnostic Checks
- Component Repository status – Open the component in Weblate UI; note the exact error message and timestamp.
- Test connectivity from the container – Run
docker exec weblate ssh -T [contact removed](or HTTPScurl -I https://github.com) to verify credentials and network reachability. - Inspect the on‑disk repository –
docker exec weblate git -C /app/data/vcs/ status. Look for uncommitted changes, detached HEAD, or lock files. - Verify remote branch existence –
docker exec weblate git -C /app/data/vcs/ ls-remote origin. Confirm the branch name matches the component's Repository branch setting. - Review Weblate logs –
docker logs weblate | grep -i -e push -e pull -e vcs. Correlate timestamps with the UI alert. - Check Celery beat/task logs – If Flower is enabled, inspect the
vcs.pullandvcs.pushtask results; otherwise checkdocker logs weblate-celery. - Validate credential store – In Weblate admin (
/admin/), verify the SSH key or token stored for the component's remote is current and has the required scopes. - Look for stale lock files –
docker exec weblate find /app/data/vcs -name 'lock' -type f. Remove any lock older than the last sync interval if no git process is running.
Fixes Mapped to Findings
Non‑fast‑forward (diverged history)
Use Weblate's Reset repository button (Component → Repository → Reset) to force the local clone to match the remote. Alternatively, from the container: docker exec weblate git -C /app/data/vcs/ push --force-with-lease origin . Risk: force‑push rewrites remote history; ensure you have a recent backup of the remote branch.
Authentication failure
Regenerate the SSH key or personal access token on the Git provider, then update the credential in Weblate admin. For SSH, ensure the private key is stored without a passphrase (Weblate cannot prompt).
Missing remote branch
Either create the branch on the remote (git push origin ) or change the component's Repository branch setting to an existing branch.
Remote hook rejection (branch protection)
On GitHub/GitLab, add the Weblate bot user to Allow force pushes or Bypass pull request requirements for the protected branch. If signed commits are required, configure GPG signing in Weblate (Component → Repository → GPG key).
Lock timeout
Reduce Celery concurrency (CELERY_WORKER_CONCURRENCY env var) to avoid simultaneous git operations. Disable automatic git gc in the container (git config --global gc.auto 0) or schedule it outside sync windows.
Merge conflicts
Use Weblate's Resolve conflicts UI action, or manually abort the merge in the container: docker exec weblate git -C /app/data/vcs/ merge --abort, then trigger a fresh pull.
Submodule issues
Enable Initialize submodules in the component's repository settings. Then run docker exec weblate git -C /app/data/vcs/ submodule update --init --recursive.
Git LFS quota
Install git-lfs in the container (Alpine: apk add git-lfs; Debian/Ubuntu: apt-get install git-lfs). Run git lfs install once per repository. Verify quota on the provider and purge unused LFS objects if needed.
Webhook misconfiguration
Regenerate the webhook secret in Weblate (Component → Repository → Webhook secret), then immediately update the webhook URL and secret on the remote repository's settings. Old deliveries will fail until the secret matches.
API rate limit
Increase SYNC_INTERVAL (default 300 s) to reduce polling frequency. Use a dedicated token with higher quota (GitHub Apps, GitLab personal access token with api scope). Enable Lazy commits (Component → Repository → Lazy commits) to batch changes.
Escalation Criteria
- Force‑push is required but no recent backup of the remote branch exists (data‑loss risk).
- Credentials appear compromised – rotate immediately and audit access logs.
- Failures persist after applying the above fixes (indicates deeper configuration or infrastructure issue).
- Multiple components fail simultaneously, suggesting a shared resource problem (e.g., database, Celery broker).
- Compliance mandates signed commits but GPG signing cannot be configured in Weblate.
When escalating, provide: Weblate version (weblate --version), component export (weblate dumpdata), sanitized logs, remote provider name, and steps already attempted.
Verification After Fix
- Trigger a manual sync: Component → Repository → Pull then Push – both should show green checkmarks.
- Make a test translation change in Weblate UI; verify the commit appears in the remote repository within
SYNC_INTERVAL. - Push a commit directly to the remote branch; confirm Weblate pulls it and updates translations.
- Check webhook delivery: remote repository's webhook UI should show
200 OKfor recent ping/push events. - Run
docker exec weblate weblate checkgit --all– should report no errors. - Monitor Celery Flower (if enabled) for successful
vcs.pullandvcs.pushtask completion.
Limitations and Version Notes
- Weblate 5.x switched the default VCS backend from GitPython to dulwich for some operations; the Reset repository behavior may differ between versions.
- Docker deployments must mount
/app/datapersistently; ephemeral storage loses repository state on container restart. - Git LFS requires
git-lfs >= 3.0in the container; Alpine images needapk add git-lfs, notapt. - Branch protection rules on GitHub/GitLab often block the Weblate bot unless explicitly allowed.
- Webhook secret rotation invalidates existing deliveries; update the remote webhook immediately after regenerating in Weblate.
- Rate limits vary by provider and may be shared across runners or apps using the same token.
0 replies
A thoughtful contribution can make all the difference. Be the first to share one.