DEV Community

lajibolala
lajibolala

Posted on

From Local Project to CI/CD Pipeline: Two Git Workflows (Simple vs Git Flow)

When setting up a CI/CD pipeline, especially in a constrained environment like a fresh VM or a time-limited setup, it is tempting to use a complex Git workflow with multiple branches.

But in practice, complexity often creates more problems than it solves.

If your goal is to get a working CI/CD pipeline running quickly and reliably, the safest approach is often the simplest one.

This article explains a practical, minimal-risk Git workflow that helps you:

  • set up CI/CD quickly
  • avoid common mistakes
  • focus on delivering a working pipeline

Why Keep It Simple

Workflows like Git Flow are powerful, but they also introduce more complexity:

  • pushing to the wrong branch
  • pipelines not triggering
  • misconfigured jobs
  • wasted time debugging Git instead of CI/CD

If your main objective is to get the pipeline working, you want:

  • clarity
  • predictability
  • fewer points of failure

Recommended Strategy: Single Branch Workflow

Core Idea

Use one branch only:

main
Enter fullscreen mode Exit fullscreen mode

Everything happens on that branch.


Why this works

  • Less risk
  • Less confusion
  • Easier debugging
  • Faster setup
  • Enough to demonstrate a full CI/CD workflow

Initial Setup

Start by initializing your project and linking it to GitLab:

git init
git branch -M main
git remote add origin http://gitlab.localdomain/your-username/your-project.git

git add .
git commit -m "Initial project import"
git push -u origin main
Enter fullscreen mode Exit fullscreen mode

Daily Workflow

After that, every change follows the same pattern:

git add .
git commit -m "Describe what you changed"
git push
Enter fullscreen mode Exit fullscreen mode

Each push can trigger the pipeline and show your progression in GitLab.


What to Push and When

Instead of pushing everything at once, follow a logical progression.


Step 1 — Push the raw project

After extracting and verifying the project, push the initial codebase.

Push:

  • application code
  • tests
  • dependencies such as requirements.txt
git add .
git commit -m "Initial import of Python project"
git push -u origin main
Enter fullscreen mode Exit fullscreen mode

This gives you a clean baseline in GitLab.


Step 2 — Push cleanup and setup

Add basic repository hygiene.

Push:

  • .gitignore
  • minor cleanup changes
git add .gitignore
git commit -m "Add gitignore and cleanup"
git push
Enter fullscreen mode Exit fullscreen mode

Step 3 — Push containerization

Once the application works locally, add Docker support.

Push:

  • Dockerfile
  • optionally docker-compose.yml
git add Dockerfile docker-compose.yml
git commit -m "Add Docker setup"
git push
Enter fullscreen mode Exit fullscreen mode

If you do not need Docker Compose, do not create it just for appearance.


Step 4 — Push SonarQube configuration

After setting up code quality analysis, push the local configuration file.

Push:

  • sonar-project.properties
git add sonar-project.properties
git commit -m "Add SonarQube configuration"
git push
Enter fullscreen mode Exit fullscreen mode

Do not push tokens, passwords, or secrets.


Step 5 — Push the CI/CD pipeline

This is often the most important step.

Push:

  • .gitlab-ci.yml
git add .gitlab-ci.yml
git commit -m "Add CI/CD pipeline"
git push
Enter fullscreen mode Exit fullscreen mode

This is usually the push that triggers the full automation flow.


Step 6 — Fix and iterate

If something fails, fix only what is needed and push again.

git add .
git commit -m "Fix pipeline issue"
git push
Enter fullscreen mode Exit fullscreen mode

Then verify the new pipeline run in GitLab.


Full Workflow Step by Step

Here is the full sequence in a clean order.

1. Extract the project

mkdir -p ~/work
cd ~/work
unzip project.zip -d project
cd project
Enter fullscreen mode Exit fullscreen mode

2. Inspect the project

ls -la
find . -maxdepth 2 -type f | sort
Enter fullscreen mode Exit fullscreen mode

3. Test locally first

pip install -r requirements.txt
pytest
python3 app.py
Enter fullscreen mode Exit fullscreen mode

Verify:

curl http://localhost:5000
Enter fullscreen mode Exit fullscreen mode

4. Initialize Git

git init
git branch -M main
git remote add origin http://gitlab.localdomain/your-username/your-project.git
Enter fullscreen mode Exit fullscreen mode

5. Push initial code

git add .
git commit -m "Initial project import"
git push -u origin main
Enter fullscreen mode Exit fullscreen mode

6. Add CI/CD components step by step

git add Dockerfile
git commit -m "Add Dockerfile"
git push
Enter fullscreen mode Exit fullscreen mode
git add sonar-project.properties
git commit -m "Add SonarQube config"
git push
Enter fullscreen mode Exit fullscreen mode
git add .gitlab-ci.yml
git commit -m "Add CI/CD pipeline"
git push
Enter fullscreen mode Exit fullscreen mode

7. Fix and re-push if needed

git add .
git commit -m "Fix CI pipeline"
git push
Enter fullscreen mode Exit fullscreen mode

What Not to Push

Never commit sensitive or unnecessary files.

A good .gitignore:

__pycache__/
*.pyc
.pytest_cache/
.venv/
venv/
.env
.sonar/
Enter fullscreen mode Exit fullscreen mode

Avoid pushing:

  • credentials
  • API keys
  • tokens
  • local environments
  • cache folders

Common Mistakes

Using multiple branches too early

This often leads to:

  • pipelines not triggering
  • confusion about where the code is
  • jobs running on the wrong branch

Pushing to the wrong branch

If your pipeline is configured for main only, pushing to another branch may result in no pipeline execution.


Overengineering too early

Trying to implement Git Flow, release branches, and complex environments before having a working pipeline usually slows everything down.


What If You Still Want Branching

If you want a slightly more structured workflow, keep it simple:

main + develop
Enter fullscreen mode Exit fullscreen mode

Work on develop:

git checkout -b develop
git push -u origin develop
Enter fullscreen mode Exit fullscreen mode

Then merge into main once stable:

git checkout main
git merge develop
git push
Enter fullscreen mode Exit fullscreen mode

Only use this if you are comfortable with branching.


Branch Behavior in GitLab CI

If your pipeline contains:

only:
  - main
Enter fullscreen mode Exit fullscreen mode

and you are pushing to develop, the pipeline may not run.

If you use multiple branches, make sure they are included:

only:
  - main
  - develop
Enter fullscreen mode Exit fullscreen mode

For deployment, it is often better to restrict execution to a single branch:

deploy_dev:
  stage: deploy
  script:
    - docker stop python-app-dev || true
    - docker rm python-app-dev || true
    - docker run -d --network host --name python-app-dev python-app:latest
  only:
    - main
Enter fullscreen mode Exit fullscreen mode

Final Recommendation

If your goal is:

  • getting CI/CD working
  • avoiding unnecessary errors
  • delivering quickly

Then the safest approach is:

Use one branch: main
Push step by step
Keep everything simple
Enter fullscreen mode Exit fullscreen mode

Push in this order:

  1. imported project
  2. .gitignore
  3. Dockerfile
  4. sonar-project.properties
  5. .gitlab-ci.yml
  6. fixes if needed

Start with:

git init
git branch -M main
git remote add origin http://gitlab.localdomain/your-username/your-project.git

git add .
git commit -m "Initial project import"
git push -u origin main
Enter fullscreen mode Exit fullscreen mode

Then continue with small, logical commits.


Final Thought

CI/CD is not about complex workflows. It is about reliability, repeatability, and control over delivery.

Start simple. Make it work. Then improve it.

Top comments (0)