Syncs files and Git history between a remote instance (e.g. AWS) and your Git repository. Use it when the remote cannot reach the Git host (e.g. network segmentation or restricted access): your machine runs the sync and acts as the bridge.
Your machine sits between the remote instance and the Git repo: it pulls from the remote via SSH, syncs with Git (pull/push), then pushes the result back to the remote via SSH.
┌─────────────────────┐ ┌─────────────────────┐ ┌─────────────────────┐
│ Remote Instance │ │ Local PC │ │ Git Repository │
│ (e.g. AWS, RDP) │ │ (Your Machine) │ │ (Bitbucket/GitHub) │
│ │ │ │ │ │
│ No Git access │ │ Has Git access │ │ Internal/Cloud │
│ │ │ │ │ │
│ ├── dags/ │ │ ├── dags/ │ │ • main branch │
│ ├── plugins/ │ │ ├── plugins/ │ │ • commit history │
│ └── .git/ │ │ └── .git/ │ │ • pull requests │
└─────────────────────┘ └─────────────────────┘ └─────────────────────┘
│ │ │
│ │ │
│◄───────────── STEP 1 ────────────────────►│ │
│ (rsync: remote → local) │ │
│ │ │
│ │◄──────────── STEP 2 ──────────────────────►│
│ │ (git pull/push) │
│ │ │
│◄───────────── STEP 3 ────────────────────►│ │
│ (rsync: local → remote) │ │
│ │ │
| Step | Direction | Method | Description |
|---|---|---|---|
| 1 | Remote → Local | rsync | Pull files from remote instance to your machine |
| 2 | Local ↔ Git | git | Fetch, pull, and push changes to/from repository |
| 3 | Local → Remote | rsync | Push updated files back to remote instance |
What it does: Pull the repo (files + Git history) from the remote instance via SSH, sync it with your Git repository (push/pull), then push the updated state back to the remote over SSH. Your machine is the bridge when the remote cannot reach the Git host.
This is ideal when:
- The remote instance (e.g. AWS EC2, RDP host) cannot reach your organization’s Git server—e.g. different network segment or restricted outbound access
- You still need to keep that environment’s code in sync with the same Git repo
- You want to preserve history and version control
- You run the sync from your own machine (where Git access is allowed); commits are made locally before or after sync
- 🔄 Bidirectional synchronization between local and remote folders
- 📦 Git version control integration (pull and push)
- 🔒 Secure file transfer using SSH and rsync
- 🎯 Configurable file exclusion patterns via
.env - 🎨 Colored logging with timestamps and log levels
⚠️ Comprehensive error handling and status reporting- 🔐 Lock mechanism to prevent concurrent execution
- 🌿 Dynamic branch detection (main/master)
- A machine that can reach both the remote instance (SSH) and the Git host—this is where you run the script
- SSH key pair for remote instance authentication
- Git credentials for repository access (script uses
credential.helper storefor the repo host) rsyncon local and remote- Bash (e.g. WSL on Windows)
git clone https://github.com/volkanncicek/bidirectional-git-sync-tool.git
cd bidirectional-git-sync-tool
chmod +x bidirectional-git-sync-tool.sh
cp .env.example .env
# Edit .env with your values (see Configuration below)Set the variables in .env. All except EXCLUDE_PATTERNS are required; exclusion patterns have a built-in default if omitted. See .env.example for the full list (Git credentials, remote/local paths, SSH key, optional EXCLUDE_PATTERNS).
# Run the sync
./bidirectional-git-sync-tool.sh-
Environment Check
- Validates presence of
.envfile - Verifies all required environment variables
- Checks SSH key existence
- Validates presence of
-
Remote to Local Sync (rsync)
- Pulls files from remote instance to your machine
- Applies configured exclusion patterns
- Uses
--deleteflag to mirror remote state
-
Git Operations
- Configures git credentials securely
- Automatically detects default branch (main/master)
- Fetches and pulls remote changes with rebase
- Pushes any unpushed local commits
-
Local to Remote Sync (rsync)
- Pushes updated files back to remote instance
- Applies same exclusion patterns
- Maintains file permissions
Note: Git commits are made manually by you (before or after running the script). The script only handles pull/push operations.
The script provides detailed logging with color-coded levels:
- 🔴 ERROR (Red) - Critical issues requiring immediate attention
- 🟢 SUCCESS (Green) - Successful operations
- 🟡 WARN (Yellow) - Warning messages
- 🔵 INFO (Blue) - General information and progress updates
The script implements robust error handling:
- Immediate exit on any command failure (
set -e) - Validation of all required environment variables
- SSH key existence verification
- Git repository status checks
- Detailed error messages with timestamps
- Lock file mechanism to prevent concurrent runs
- Automatic cleanup of stale lock files
This project is licensed under the MIT License - see the LICENSE file for details.
Contributions are welcome! Please feel free to submit a Pull Request.
For issues and feature requests, please create an issue in the GitHub repository.