My Dev's Guide to Git: From Basics to Pro Workflows

Written on: June, 2025

13 min read

Git isn't just version control. It's the backbone of how modern development teams think, collaborate, and ship code. For the first two years of my career, I treated it like a glorified backup system: commit, push, pray nothing breaks. Then I joined a team where Git wasn't just a tool, it was their entire development philosophy. That's when everything clicked. Git shapes how you structure features, how you communicate with teammates, and how you deploy to production. It's the difference between chaos and orchestrated teamwork, between "works on my machine" and bulletproof releases. In this guide, I'll walk you through the journey I wish I'd taken from day one. We'll start with the fundamentals that every developer needs, then build up to the advanced workflows that separate junior developers from senior ones. You'll learn not just the commands, but the thinking behind them, when to rebase versus merge, how to craft commits that tell a story, and how to structure branches that make your team's life easier. Whether you're just getting started or looking to level up your Git game, this is the comprehensive guide I wish someone had given me when I first typed git init. Let's dive into the world of Git.

Steps

  1. The Git Essentials: Creating the repository
  2. A repository is a directory that contains a project and its history. It uses Git to track changes to the project. You can create a repository by running the following command in your terminal or by using github app.

    1git init
  3. Your First Real Commands: Building a Feature
  4. Let's walk through a real scenario from your first week on the job. You've been assigned to build a login feature, and you'll need to download the project to your machine. The first step is cloning the repository, which downloads the entire project history to your local system. Once you have the project locally, you can start working on your assigned feature.

    1git clone https://github.com/your-company/project.git
    1cd project
  5. Creating Your Feature Branch
  6. Before diving into the code, you'll want to create a new branch for your feature. This is a crucial practice that keeps your changes isolated from the main codebase and makes it easy to switch between different tasks. Think of branches as parallel universes where you can experiment freely without affecting the main timeline of your project.

    1git checkout -b feature/login-page
  7. Staging and Committing Changes
  8. As you build the login feature, you'll want to save your progress in logical chunks. Think of commits as checkpoints in a video game. Before creating a checkpoint, you'll want to check which files you've modified using git status. This shows you everything that's changed since your last commit. Then you can stage specific files that are ready to be committed. When creating a commit, think of it as documenting a clear, specific change to the project. Your commit message should tell other developers exactly what this change accomplishes.

    1git status
    2git add src/components/LoginForm.tsx
    3git commit -m "feat(auth): implement login form with validation"
  9. Pushing Your Changes
  10. Once you've made progress on your feature and committed your changes locally, it's time to share your work with the team. Pushing your feature branch uploads your commits to the remote repository where other team members can see them. After pushing, you'll typically create a Pull Request, which signals to your team that your code is ready for review. This is where the collaboration really begins.

    1git push origin feature/login-page
  11. Collaborating with Your Team
  12. Now comes an important part of team development: keeping your code in sync with others. Before starting new work each day, you'll want to make sure you have the latest changes from the main branch. This helps prevent conflicts and keeps you aligned with the team's progress. The process involves switching to the main branch, pulling the latest changes, and then merging those updates into your feature branch.

    1git checkout main
    2git pull origin main
    3git checkout feature/login-page
    4git merge main
  13. Handling Merge Conflicts
  14. Sooner or later, you'll encounter a merge conflict. This happens when you and another developer have changed the same part of a file. While it might seem scary at first, resolving conflicts is a normal part of collaboration. When a conflict occurs, Git will mark the file with special markers showing both versions of the code. Your job is to decide which changes to keep, or how to combine them. After editing the file to resolve the conflict, you'll stage it and create a new commit to complete the merge.

    1# After fixing conflicts in the files
    2git add .
    3git commit -m "fix: resolve merge conflicts in login form"
  15. Power Tools for Developers
  16. As you grow more comfortable with Git, you'll discover powerful commands that can help you work more efficiently. One such tool is git stash, which lets you temporarily save your work-in-progress changes when you need to switch tasks quickly. Think of it as a clipboard for your code changes, letting you paste them back when you're ready to continue working.

    1git stash save "login form validation WIP"
    2git stash list
    3git stash pop
  17. Cleaning Up Your Commits
  18. Before submitting your work for review, you might want to clean up your commit history. Git provides powerful tools for this. Interactive rebase lets you modify your commit history, combining multiple small commits into more logical units, or rewording commit messages to be more clear. This is like editing a document before publication – you want your changes to tell a clear, coherent story.

    1git rebase -i HEAD~3  # Rebase last 3 commits
    2git reset --soft HEAD~3 && git commit -m "feat(auth): complete login feature"
  19. Advanced Power Tools: Cherry-Pick and Bisect
  20. Sometimes you need surgical precision in Git, and that's where cherry-pick comes in. Imagine you're working on a feature when your team lead messages you about an urgent authentication fix you made last week that needs to go to production immediately. Instead of merging your entire branch, you can pluck just that one commit and apply it where needed. Another powerful tool is git bisect, which becomes invaluable when tracking down bugs. Picture this: your team discovers a bug in production, but no one knows when it was introduced. Instead of checking every commit manually, git bisect performs a binary search through your history, helping you pinpoint exactly when the bug appeared. You simply tell Git whether each commit it checks has the bug or not, and it narrows down the search until it finds the culprit.

    1# Cherry-picking a specific commit
    2git log --oneline --grep="auth fix"
    3git checkout production
    4git cherry-pick abc123
    5
    6# Using git bisect to find a bug
    7git bisect start
    8git bisect bad  # current commit has the bug
    9git bisect good v2.0.0  # this version worked
    10# Git will checkout commits for you to test
    11# After testing, mark each commit:
    12git bisect good  # if the bug isn't present
    13git bisect bad   # if the bug is present
    14git bisect reset  # when finished
  21. Setting Up Git Hooks with Husky
  22. Git hooks are like automated guardians for your codebase, running checks and tasks at specific points in your Git workflow. Using Husky, we can easily set up these hooks to ensure code quality. For example, we can automatically run tests before each commit, or ensure commit messages follow team conventions. This automation helps maintain consistency and catches issues before they make it into the codebase.

    1npm install husky --save-dev
    2npx husky install
    3npm pkg set scripts.prepare="husky install"
    4
    5# Add hooks for tests and commit message format
    6npx husky add .husky/pre-commit "npm test"
    7npx husky add .husky/commit-msg "npx --no -- commitlint --edit ${1}"
  23. Securing Your Commits with GPG
  24. In professional environments, it's crucial to verify that code changes genuinely come from the right developers. This is where GPG signed commits come in. By generating a unique GPG key and configuring Git to use it, you can cryptographically sign your commits. This adds an extra layer of security and verification to your development workflow, ensuring that commits attributed to you actually came from you.

    1# Generate a GPG key
    2gpg --full-generate-key
    3# List your keys and copy the ID
    4gpg --list-secret-keys --keyid-format=long
    5# Configure Git to use the key
    6git config --global user.signingkey YOUR_KEY_ID
    7git config --global commit.gpgsign true
  25. Integrating with CI/CD
  26. Modern Git workflows are incomplete without continuous integration and deployment. By integrating your Git repository with CI/CD pipelines, you can automatically test and validate every change. A common setup using GitHub Actions automatically runs your test suite and linting checks on every pull request. This ensures that only quality code makes it into your main branch, catching issues before they affect other team members or reach production.

    1# .github/workflows/main.yml
    2name: CI
    3on:
    4  pull_request:
    5    branches: [ main ]
    6
    7jobs:
    8  test:
    9    runs-on: ubuntu-latest
    10    steps:
    11      - uses: actions/checkout@v2
    12      - name: Setup Node.js
    13        uses: actions/setup-node@v2
    14        with:
    15          node-version: '18'
    16      - run: npm ci
    17      - run: npm test
    18      - run: npm run lint
  27. Automating Code Reviews
  28. Code reviews are essential for maintaining code quality, but they can be time-consuming. Git provides tools to make this process more efficient. By setting up helpful aliases and automated checks, you can streamline the review process. Custom Git commands can help you quickly see changes in a more readable format, while pre-push hooks ensure basic quality checks pass before code is shared with the team.

    1# Add useful aliases to .gitconfig
    2git config --global alias.review "log --patch --reverse"
    3git config --global alias.files "diff-tree --no-commit-id --name-only -r"
    4
    5# Create a pre-push hook
    6cat > .husky/pre-push << 'EOF'
    7#!/bin/sh
    8npm run lint && npm test
    9EOF
    10chmod +x .husky/pre-push

Conclusion

Git is more than just a tool for tracking changes—it's a communication platform that helps teams work together effectively. As you've seen, mastering Git isn't just about memorizing commands; it's about understanding workflows and best practices that make collaboration smoother. Remember that Git proficiency comes with practice. Start with the basics and gradually incorporate advanced techniques. Focus on writing clear commit messages that tell a story. Keep your branches focused and up-to-date. Don't be afraid to use Git's power tools when needed. The more you use Git, the more natural these workflows will become. Soon, you'll find yourself automatically thinking in terms of atomic commits, clean history, and clear communication—skills that will make you a more effective developer and a better team member.
Back to Blogs
Aldi Krasniqi