18

I am working on a project on my own and I am using git just to keep track and to get used to a team environment. When should I commit on the main branch (if I should at all), do I need to create a branch for each feature, bug, etc., and then merge them to main or could smaller things (adding one field to get stored in a database) be committed on the main branch?

I looked into the following questions and it didn't really see anyone focusing on the point if the main branch is only for merging or could it also be used for minor commits as well.
Git branching and tagging best practices
Git strategy to use when a file I am going to edit in another branch has been updated in the master branch?

2
  • 5
    you need branches when you want more than one version of your code to exist at the same time. E.g. a teammate working on another feature or in your case let's say you are working on a longer refactor in your free time on a separate branch, but you also want to push important updates to your main branch while the refactor is not done yet
    – hangyas
    Oct 14, 2022 at 19:28
  • 1
    "I am working on my own" and "get used to a team environment" don't match up. Git does support both use cases, but it's used in different ways
    – Bergi
    Oct 15, 2022 at 3:50

7 Answers 7

24

Since you're working on this by yourself, it's up to you to make up your own git branching strategy.

Strict rules like "never commit directly to main" are mostly for actual collaborative work, to e.g. make sure that every code change is reviewed.

For yourself, it's totally OK to use branches only for features that you'll be working on for a longer time but don't want to have in the main branch right away, and commit directly to main for smaller changes.

Do whatever you think is the best balance between ease of use and protecting you from problems.

8

The advantage of committing directly to the main branch is simplicity -- if all of your changes are commited to the same branch, then you don't have to keep track of which changes were committed where, and you don't have to deal with (potentially messy) branch-merging later on. It also means that there is only one version of your program that needs testing, which increases the chances of you noticing and fixing any bugs that might creep in to your program (it's hard to notice a bug that's present only in a branch that you're not currently building from).

The advantage of making changes in a separate branch is that if it all goes pear-shaped, you still have a perfectly functional main branch that you never damaged with your ill-fated changes. In the worst-case scenario, you can just delete the messed-up side branch (or keep it but just never merge it back), and life can go on without requiring any cleanup of the main branch.

So my suggestion (when working by yourself) is: small and low-risk changes can go directly into the main branch, but if you're going to make a major and/or a risky change, create a side branch and make the change there first. Then, once you've completed the change, tested it, and verified that you're happy with the results, then you can merge it back into the main branch.

3

Anything you do, you create a branch for it, when you're done you merge into the main branch, and you can leave your old branch or delete it. Usually you It's good to have branches numbered and with a useful title. Having branches makes it easy to work on different things at the same time; say you are working two days on a new feature and in the middle of it you find a bug that needs fixing, you can do that easily by using two branches.

When you have old branches that you don't care about anymore, you can delete them. Make sure that either the git repository is either stored on an external server or gets backed up, so you always have a backup.

And assume you make mistakes-you don’t want your mistakes in your master branch. So never commit directly to master.

1

Always Green

Any commit on the main branch should always be green. That is, I can check it out, run the full test-suite, and it comes back green.

The alternative (not all commits are green) mean that:

  1. Pulling an older version to compare its behavior with the newer one may mean hitting a "dud" and encountering unrelated issues.
  2. And thus bisecting to find which version introduced an issue may not be possible.

In a team setting, it also means that starting work on a new feature may be hampered by first having to figure out whether the latest commit is green or not.

This is what you should be getting used to. Even on private repositories, setup your CI, with linter and test-suite, and get used to have every PR scrutinized.

To branch or not to branch

Branching is orthogonal to a green main branch, and mostly a matter of team preference.

My previous team used an "live-at-head" strategy, so we would all commit to the main branch -- of course, we used CI & Pull-Request so in practice the CI created a branch, ran the tests on that, and then when approved rebased the branch on master and fast-forwarded it. That was behind the curtains, though, and was invisible.

My current team uses a one feature-one branch strategy, so the first step of starting to work on a feature/bug/ticket is to create a branch locally, then do your work there, and then once done (and green, and reviewed), merge the branch into master.

You cannot, in advance, guess which strategy your future team will use. Their strategy may also change depending on the repository and tools.

I do encourage you to become comfortable with branches; but there's no one true way.

4
  • > Pulling an older version to compare its behavior with the newer one may mean hitting a "dud" and encountering unrelated issues. Yes, but that shouldn't be a problem if you have an easy to access list of green versions. A build server will often effectively add an entry to that list as part of the process.
    – bdsl
    Oct 15, 2022 at 18:59
  • 1
    @bdsl: That's possible, but it's definitely not as convenient. Similarly you could probably configure git bisect to work off that list, but similarly it would be more of a hassle. Keep main green, always, it'll make your life easier. Oct 16, 2022 at 10:48
  • @Matthiew M. so does that mean you only merge to main after all checks are completed, and you only allow fast-forward merges?
    – bdsl
    Oct 16, 2022 at 12:54
  • 2
    @bdsl: Ideally, yes. It can be accomplished in multiple ways -- either running the checks on a clone of the repository, or on another branch -- but they only get merged into a "real" repository on main as a fast-forward after having been "greened". In practice, it's not always possible depending on CI, and a close second I've seen is to check, merge, re-check, and have a human surgically amend main in the unlikely case the re-check fails... but it's not as good :( Oct 16, 2022 at 14:20
1

In addition to learning the git behaviour of your future team and learning more about git there are some more advantages to using branches:

  • Branches allow you to experiment and play with your code When you have an idea and are not sure whether it will work (or result in elegant code), you can create one or more branches try out the idea see what works best and pick that option.
  • Branches allow you to alternate working on several features/bug fixes. When you are working on a feature and suddenly discover a bug you can suspend work on the feature and switch to fixing the bug.
    This way of working is even possible if you have started the work on the feature on main
    Create a branch for the feature (now HEAD, Main, and the newly created feature branch point all to the same commit), reset Main to the commit before you started working on the feature, and fix the bug.
  • If you're using git stash, consider using branches, for stashes that live longer that your short term memory can remember.
    Branches allow you better describe what they contain and what your intention was; consider stash@{3} vs experiments/round-robin-routing.
  • (Nested) branches of atomic commits allow you to introduce structure and meaning into your commit history.
    It allows you to later identify which commits where part of what feature. Note that this structure works best if your team mates and git repository platform support it; and the way of merging I propose is not one of the most common merge practices.
1

It doesn't matter.

In Git, a branch is just a label pointing to a commit (the "latest one on this branch"). Editing the labels is basically free. This is unlike other systems such as Subversion, where a branch is a completely new, separate copy of the code.

Consider two scenarios:

  1. The latest commit on your main branch is "added new SQL statements". Someone reports an SQL injection bug. You create a branch called sql-injection-hotfix. You fix the SQL injection and then merge this into the main branch. You delete the sql-injection-hotfix branch. You push the main branch.

  2. The latest commit on your main branch is "added new SQL statements". Someone reports an SQL injection bug. You fix the SQL injection on the main branch and push it.

The end result of each scenario is exactly the same: a branch called main pointing to the commit "fixed SQL injection bug" and that commit's parent is "added new SQL statements". I mean exactly. There's no way for anyone to tell which one you did. If you view the log you'll see a straight line, with no records of branching.

(Exception: the reflog on your computer, which is like an undo log for git commands, will be different since you used more git commands in scenario 1)

If you work on two fixes at the same time you may create a log with a record of branching, but it's still the same, no matter whether you start working on fix 1 on main and then go back and branch fix-2 off an earlier point of main, or whether you branch fix-1 and fix-2 off main - whichever one you merge first will look like it was main all along.

1
  • "a branch is just a label pointing to the latest commit on this branch" -> "a branch is a label pointing to a commit (and there are commands that will automatically move those labels, defaulting to a 'current' branch)"
    – Caleth
    Oct 21, 2022 at 10:06
-2

Generally commit the version that builds and generally works. Write a commit message about changes done. Possibility to navigate between the past versions is often a big help. Seldom, but happens that you do not know where the functionality got broken and need to revert versions one by one till the breaking change is found and can be refined. Put tags on important milestones.

If you make changes that make the application temporarily unusable, or work on experimental features you are not sure about, do this in a branch. You may also need to branch if you suddenly discover that your recent changes break some tests. Doing lots of work without commit and push is still not good, as repository is often also the only place where the work is backed up.

If you need to make some releases, create release branches at that point. You can then put bug fixes into release branches or very minor features without making forcing the user to have other changes you have done on a master branch. This is important when other members of the team need your part as a functional unit for they work.

When sending code into master branch, do the code review for yourself, following same procedures as if you were another person: look into diff. There is no reason why you cannot notice the own mistakes or observe the room for improvement. It may even be possible to find a fragment that has been commented out but should not stay this way, or just typo resulting from the accident hit of the key that due bad luck produced a code that still compiles.

Instead of creating the full blown pull request for himself, it may be simpler to go over changes between workspace and master branch that are also easy to view.

1
  • Sorry, this is my actual flow that I find efficient in my work.
    – h22
    Oct 16, 2022 at 18:41

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.