Giter VIP home page Giter VIP logo

gitworkflow's Introduction

Gitworkflow

The git.git project, responsible for the creation and maintenance of the git tool itself, uses a powerful workflow I call "gitworkflow", in deference to its creators and the man page in which it is described.

I describe the advantages of this workflow, in comparison to the popular GitFlow by Vincent Drieesen and Adam Ruka’s OneFlow in a blog post titled How the Creators of Git do Branching.

This repository is meant to be a place in which tools and documentation related to gitworkflow can be created.

Key Advantages

The key advantages gitworkflow over GitFlow and OneFlow all come from treating topics as first-class citizens, not just temporary placeholders for unfinished code.

Amazing History

Gitworkflow presents a history that code historians, and conscientious developers can love. It can easily present both summary (e.g. "show me all the topics merged into a release") and highly detailed views (e.g. "show me all the commits related to a topic").

A graph of a specific topic’s history contains all of that topics commits, not interspersed with other topics:

Topic History

but all of that detail can be elided to understand what was merged at a high level:

Integration History

(both examples from the git.git repository)

Continuous Integration, Done Right

Ever struggled with the decision about when to merge a topic branch to the main branch (develop in GitFlow / master everywhere else)?

With GitFlow and OneFlow, in order to get the benefit of Continuous Integration, you have to either test each topic branch in isolation, OR you have to merge it to the main line. Testing the topic in isolation, well, tests in isolation, which is "continuous", but isn’t "integration". Waiting to merge until the topic is "done" means you can only test it along with other work that is also "done". This is "integration", but it isn’t "continuous".

This tension exists between "continuous" and "integration" because in most non-trivial projects, topics don’t have a binary done/not done state: they are almost always a work in progress, with their stability being an analog continuum, not a digital value. We really want to do "continuous integration" of topics, even before they are considered "done" (i.e. released).

With gitworkflow, the stability level of a topic is explicit — and we can do true "continuous integration" of all the unreleased alpha-quality topics merged together to create an "alpha" release, all the unreleased beta-quality topics merged to create a "beta" release, and lastly all of the released topics.

The early "continuous integration" of topics before they are "done" allows identification of conflicting work on different topics early in their development, prompting the right conversations and coordination between devs at the right time.

Make Your Topics Great

Gitworkflow allows the alpha and beta-quality integration branches to be rewound and rebuild. This property allows topics to be massaged via interactive rebase until they form a series of easily understandable and reviewable chunks of work. With other flows, this is only an option until the topic is considered "done" and is merged to the main line for CI and user testing. Gitworkflow removes the limitation that a topic branch cannot be interactively rebased after it has been merged for CI and user testing, and especially for alpha-quality topics, this would be expected by most team leads and code reviewers, rather than frowned on.

Flexibility

Sometimes features take longer to develop than expected. Sometimes they don’t work well with other work in progress and need to be thrown away and a new approach taken. Sometimes everyone thinks they are "done", but they don’t test well or they cause regressions.

In most flows, this code is already on the main line of development. It has to be reverted (which can be easy or hard depending on the flow and the method used to merge the topic).

In contrast, Gitworkflow defines a range of stability levels that the code "graduates" through, from raw unfinished code ("alpha") to code ready for testing ("beta") to code ready for release. Code can spend as much time as it needs to at each of these "levels", and when code is merged to the main line, it is production-ready. Thus gitworkflow supports continuous deployment scenarios as well.

Gitworkflow allows you to define your own stability levels if you wish: add or remove integration branches as necessary.

Main Insights

One key insight that makes gitworkflow work over flows like GitFlow and OneFlow is that: git is smarter than your average source control system. Topics don’t have to be merged only into the branch they were started from, which seems to be the implicit or explicit assumption most flow authors make. In git, the topic can be merged into any branch that it shares a common ancestor with.

This means that topic branches can be merged to multiple integration branches, each with a different purpose corresponding to the stability levels defined above.

A related insight is that topics can be merged into other topics to explicitly deal with conflicts and encode dependencies.

A second key insight is that, when topics are first-class citizens, early integration branches are just ephemeral placeholders for various combinations of topics, and can easily be recreated (rewind and rebuild). The integration branches are therefore unimportant and don’t need to be a limiting factor for work on topics, such as rebasing, and we are free to experiment with moving topics in and out of them.

The third key insight is that merge commits — the ability to explicitly join two lines of development — offer the ability to accomplish all of the above, as well as to continue to track topic history, long after the topic is no longer being developed, making code history spelunking great.

Disadvantages

Gitworkfow is more complicated, and harder to understand than most (probably all) other flows. It requires more understanding of git concepts and capabilities. It offers significant powerful capabilities to complex multi-dimensional products with a team of developers, but does have more "overhead" in the sense of multiple things to track and understand. This means that:

  • Gitworkflow should not be used without significant team maturity using, or willingness to learn, git, and

  • Gitworkflow is serious overkill for trivial or one-man projects (but these might be a good place to try it out).

Interested in Learning More?

Questions?

Feel free to ask questions about gitworkflow in the issues of this repository. Please prefix your issue subject with [Q].

The Gitworfkow Awesome List

A curated list of related external articles and documentation.

Git.git Documentation

All of the following are git.git resources by the git.git team.

Articles and Blog Posts

TODOs

gitworkflow's People

Contributors

rocketraman avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

gitworkflow's Issues

Specify merging type from topic branch to master

Hi all,

I found that there's a bit of confusion when you document the merging of a topic branch inside master, there is no description on what type of merging is used (fast-forward or --no-ff).

By looking to the visual image it seems that's a --no-ff (hope it is) merge but it's never clearly mentioned in the description.

Thank you guys

Integrate 'create-pu' script

For my own project I wrote a script witch can automate the creation of a pu branch.

First it merges all mature feature/topic branches which are already in next into pu.
When this task is done, an empty ### Match 'next' commit helps to identify is state.
Then all branches which are not in master and not in next are merged into pu

Branches which are labeled with wip/ will not be automatically merged into pu.

The script is licensed under GPLv3 and if you like it can be integrated into your project.

[Q] Why can't i merge next into master?

I remember you mentioning this in your tute, but you didn't explain why.

Ok, I have the four branches and I have created a topic and all went well. Then I went thru pu and then next processes. Did the same to other nine topics and eventually had 10 of them.

Now we want to cut a release after CI passes on next. If I got it right you said master and next never merge nor does pu and next nor pu and master. It means I have to merge those topic branches one by one into master, so why not just merge next into master seeing that is the state of the project we want to release?

This is similar in concept to GitFlow’s release branch, but far more flexible and powerful, since master has no dependencies on next whatsoever, nor is next ever merged wholesale into master (unlike the corresponding GitFlow branches develop and release).

The keyphrase here is:

nor is next ever merged wholesale into master

What's wrong with that since they all have a common ancestor?
Will something bad happen when we reset next and pu to master?
Is there a caveat in git checkout master && git merge --no-ff next && git checkout next && git reset --hard master approach, when the state of next branch is what we want to release?

Document empty commit technique to allow merge commits on already merged branches

In some cases, a branch may be merged into an integration branch as part of another topic. Generally, one should explicitly merge in dependent branches first, but in some cases this does not happen.

If so, sometimes it is useful to document the merge of that branch in the first-parent log. However, git will refuse to merge the branch because it will report "Already up to date".

We should document the use of empty commits on the topic branch, that will allow git to merge the topic into an integration branch, despite it already being there via another topic.

Document Git 2.18 feature `--rebase-merges`

Git 2.18 has an option for interactive rebase called --rebase-merges, which will eventually replace the clunky --preserve-merges. This capability can be used to rebase a topic with merges interactively, and can therefore be very useful for topic-based development with gitworkflow.

See https://git-scm.com/docs/git-rebase#_rebasing_merges

Add information to the docs about how this option can be used e.g.:

  • Redoing merges of other topics (for example, if that other topic was itself rebased)
  • Splitting topic branches up into separate topics
  • Adding additional merge commits to the topic without rebuilding it with reset, merge, and cherry-pick

Depending on another topic

Hi! Big fan of this workflow, thanks for all the write up around it. It has been working great for us with our CI/CD.

One question about merging topics into other topics when they depend on each other.
Your recommendation is to:

create your topic and merge the other topic into it. This explicitly records the dependency relationship between the topics, and puts the commit resolutions (if any) on the right branch.

But

if topic B depends on another topic A that has not yet graduated to master, topic A may be merged into topic B. This complicates interactive branch rebases so this should be avoided when possible, however if necessary, git should handle this situation without too much problem.

Interactive rebasing to clean up commit history etc is an obvious pain point here, that would be nice to avoid.

But my main concern is this use case:
If Topic B depends on Topic A and both are in development, I merge Topic A into Topic B and do some work. But Topic A is still being developed and I need to pull in the newest features again into Topic B, a second merge commit in this case would complicate rebasing and history even more. What would be your thoughts in this case?

Instead of merging topic dependencies, wouldn't it be better to keep them rebased during development? And maybe only merge the dependency when it graduates by first getting rid of the depending commits:
git rebase --onto master topic-a topic-b
and then merge topic a into topic b to record the dependency?

While this is a solution, it's not the cleanest one imho, as it relies on best effort from everyone to rebase and merge correctly when necessary.

I'd love to hear any ideas for a better approach :)

Discussion about the git stacked diffs / git stacks workflow

A post about stacked diffs:

This is a very interesting approach that works quite well, and with a slight tweak (stacked branches vs stacked diffs), is not mutually exlusive with gitworkflow.

Stacked branches essentially takes all the pain out of managing topic branch dependencies -- in gitworkflow these are handled via recording topic dependencies i.e. topic B depends on topic A, by merging A into B, and then continuing to work on B. In stacked branches, B is simply "stacked" on top of A, and the tooling manages the stack i.e. if A changes, B is automatically rebased.

Stacked diffs / branches is more about developing code and doing code reviews and managing a developer's stack of work, while gitworkflow is more about CI and deploying code, so I believe these tools and techniques are complementary.

I've been playing around with https://graphite.dev/ and its really very nice. See this introductory video: https://www.youtube.com/watch?v=cE59cfwWL7M.

[Q] Create release is different from git.git

I'm looking at implementing this, and comparing man gitworkflows with what is here.
I noticed that gitworkflows says:

https://git-scm.com/docs/gitworkflows#_maintenance_branch_management_after_a_feature_release


Recipe: Update maint to new release

    git checkout maint

    git merge --ff-only master

But https://github.com/rocketraman/gitworkflow/blob/c3cb27618e5fcd41dc96508c403b35de50a296cc/docs/task-oriented-primer.adoc#create-a-release create a release suggests instead:

$ git checkout maint
(maint) $ git reset --hard v2.7.0
(maint) $ git push --set-upstream origin +maint

Why the difference?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.