Last modified: June 11, 2024

This article is written in: 🇺🇸

Syncing with a Remote Repository

When collaborating on a project, it's essential to keep your local repository updated with changes made by others in the team. Git provides powerful commands to facilitate this process.

Retrieving Changes from the Remote Repository

git fetch

git pull

git pull --rebase

Fetch vs. Pull

Action Fetch Pull
Purpose Downloads updates from the remote but leaves your local branch untouched. Directly integrates the fetched changes into your current branch.
Provides flexibility as you decide when to integrate those changes. Essentially a combination of fetch and merge.

After fetching, if you decide to integrate the changes, you can either:

Use the merge command:

git fetch
git merge

Or, if you want to override local changes to match the state of the remote branch, employ:

git fetch
git reset --hard origin/branch_name

Note: Ensure any pending work is committed before using reset to avoid potential data loss.

Merging a Feature Branch with the Master Branch

Suppose you've been developing a new feature on a branch called feature_branch. Once you're ready to integrate this feature with the master branch, follow these steps:

  1. First, switch to the master branch:

git checkout master

  1. Pull the latest changes from the remote master branch to ensure you're up to date:

bash
git pull origin master

  1. Merge your feature_branch into the master:

git merge feature_branch

Understanding Merging and Rebasing

When it comes to integrating changes from one branch into another, Git offers two primary strategies:

Aspect Merging Rebasing
Process Combines changes into a new commit Moves commit history onto target branch
Commit History Retains individual commit history of both branches Provides a cleaner, linear commit history
Collaboration Creates a unique commit referencing merged branches Rewrites history, potential collaboration issues

Understanding Merge Conflicts

Master Branch:                      Feature Branch:
                                                                                 
+---------------------------+       +---------------------------+                 
|                           |       |                           |                 
| some code...              |       | some code...              |                 
|                           |       |                           |                 
| ++++++++++++              |       | ++++++++++++              |                 
|                           |       |                           |                 
| the conflicting line      |       | the alternate line        |                 
|                           |       |                           |                 
| ++++++++++++              |       | ++++++++++++              |                 
|                           |       |                           |                 
| more code...              |       | more code...              |                 
|                           |       |                           |                 
+---------------------------+       +---------------------------+                 

Attempt to Merge:

+-------------------------------------+
|                                     |
| some code...                        |
|                                     |
| <<<<<<< HEAD                        |
| the conflicting line               |
| =======                             |
| the alternate line                  |
| >>>>>>> feature-branch              |
|                                     |
| more code...                        |
|                                     |
+-------------------------------------+

Steps to Resolve Conflicts

If you encounter merge conflicts:

  1. Begin by reviewing the terminal's advice. Git often provides context about the nature and location of the conflict.

  2. Use the git diff command to inspect the differences and identify the conflicting areas.

  3. Edit the affected files manually to resolve the conflicts, ensuring the desired code remains while removing Git's conflict markers (<<<<<<<, =======, >>>>>>>).

  4. Once resolved, stage the changes with git add filename.

  5. If you were in the middle of a rebase, continue the process with:

git rebase --continue

  1. Otherwise, if you were merging, finalize with a commit.
  2. Repeat the process until all conflicts are addressed.

Leveraging Git's Mergetool

To list available tools:

git mergetool --tool-help

Popular merge tools include:

Switching to another tool, e.g., meld:

git config --global merge.tool meld

To use mergetool when a conflict arises:

git mergetool

This displays a three-panel view for each conflicted file: - Left: Your local changes - Center: Merged result - Right: Remote changes

Make resolutions in the center panel, save, and exit the editor.

Post-Mergetool Cleanup

After using mergetool, you might notice .orig files. These backups are created during conflict resolution.

To remove these backups:

git clean -i

To prevent creation of these backup files in future:

git config --global mergetool.keepBackup false

Remember, understanding the context of the changes and frequent communication with collaborators can significantly reduce the likelihood and complexity of merge conflicts.

Pushing Local Changes to a Remote Repository

To push local branch changes to the remote repository:

git push origin branch_name

Ensure you replace branch_name with the actual name of your branch.

Note: This will work if the remote branch has no new commits since you last synchronized. If there are newer commits, you'd have to first merge or rebase with the remote branch.

For pushing a new branch and setting up tracking:

git push -u origin branch_name

This not only creates the branch remotely but also establishes a tracking relationship.

Force Pushing: Sometimes, you may need to forcefully push changes, overriding any conflicting changes on the remote. This can be done using:

git push --force origin branch_name

Warning: Use --force carefully, as it can discard remote changes and lead to data loss.

Keeping a Forked Repository Updated

When working with forked repositories, it's common to want to synchronize your fork with the original (or "upstream") repository:

  1. First, ensure you've added the original repository as an upstream:

git remote add upstream original_repo_url

  1. Fetch the changes from the upstream repository:

git fetch upstream

  1. Merge the changes from the upstream's master branch into your current branch:

git merge upstream/master

  1. Push these merged changes to your remote fork:

git push origin branch_name

  1. Alternatively, you can fetch and merge in a single step using:

git pull upstream master

Table of Contents

    Syncing with a Remote Repository
    1. Retrieving Changes from the Remote Repository
      1. Fetch vs. Pull
      2. Merging a Feature Branch with the Master Branch
      3. Understanding Merging and Rebasing
    2. Understanding Merge Conflicts
      1. Steps to Resolve Conflicts
      2. Leveraging Git's Mergetool
      3. Post-Mergetool Cleanup
    3. Pushing Local Changes to a Remote Repository
    4. Keeping a Forked Repository Updated