How to handle two separate but very similar codes with git / github?

What is the best way to handle two separate but very similar code bases in git and git-hub?

Background

I have a git repository for a small script shell project. It has only 2 or 3 code files, and I often work in a single file. Although I originally made a project to fulfill my specific task, I write that it is more useful for others. I write a version of a common use case and then modify it to be specific for my specific purpose. In a specific version, I can change the variables, enter the password, switch around the order of some code, take out the for loop ... whatever.

What ive tried

I tried two different methods and none of them worked as optimal, I would think that it can:

  • Two separate repositories
    • Problem: the code is changed in one, it can not easily and selectively merge with the other
  • Two branches in one repo
    • Problem: Affiliates must ultimately come together. I'm not going to completely combine them together, but to selectively combine parts of the code.
    • Problem: I found that when trying to use merge commands between branches it was very easy to mislead as to which code in which branch merges. I somehow combined the code among the two of them, which was completely unintentional, and there was no indication of incorrect merging until I looked at the contents of the files in both branches.

I also saw How to combine two separate, but similar - code files into one SVN review? which refers to SVN. Tough because I don’t know SVN. I think this is another question because it is not trying to publish one version of this code.

Service cases that I want to solve

In particular, a problem is detected when:

  • Sync comments. I am preparing my own specialized version and notice that I can add an explanatory comment at the end of the line. I am adding it, but the comment is no longer in the generic version.
  • Stuff I do not want to use shared access - I am preparing my own specialized version and adding a password or changing the order of operations. I do NOT want these changes to transition to a generic version.
  • The same file. These two changes will often be in the same file, making it difficult to merge data together. There are interactive merges, but I don't know if the interaction can be done in one file.
  • General β†’ Specialized - I or someone else can update the generalized version to have new content or comments that would be useful in my specialized version. I want to translate them from general β†’ specialized, without delving into any other code differences in the specialized version.

Git vs github

Basically my question is asking how to do this inside git. However, this may have consequences for how to interact with github. My generic version runs on github. The special version should NOT be on github. I think my branching method above did not push both branches if I were careful ... but I was always unsure. In any case, the solution must allow one version to be publicly available and one version to be saved locally ... even if it is a little complicated or requires maintenance.

+6
source share
4 answers

This can easily be done with two branches. I'm not sure why you say that β€œcode is modified by one, cannot easily and selectively merge with another,” because merging is pretty easy in Git.

The structure that I would suggest is to have a branch for your general version and a branch for your personal version. Mergers should take place in only one direction, from a common branch to a personal branch. This means that any changes you make to the general version are included in the personal version.

In other words, this is normal ...

git checkout personal git merge general 

This should never be done ...

 git checkout general git merge personal 

If you make changes to your personal version and decide that it would be nice to have the same code in the general version, you should be able to handle this quite easily with the cherry pick. It takes a little forethought to organize commits in a personal thread. You will need a commit in a personal branch, which contains only those changes that you want to transfer to the general version, and then just cherry select it from the personal branch and lower it to the general branch.

Two repositories can do the same thing. This will reduce the risk of accidentally uploading your personal version to Github, but it would make it more tedious to work with two different versions.

Personally, I would go with two branches in the same repo.

+4
source

To avoid pushing your custom version into github, set push.default to tracking (or upstream for git> = 1.7.4.2). See http://longair.net/blog/2011/02/27/an-asymmetry-between-git-pull-and-git-push/ for gory details.

Mergers should work equally well, whether you use a separate repo or just a branch. As a high-level answer, you will eventually need to merge very well. Much of this will happen due to the fact that git is running at a low level regarding branching, merging, and reloading. Unlike some other version control systems, I found that git requires a deep understanding of the internal components in order to really use it properly.

+1
source

Secondly, the idea of ​​using two branches : a public branch for the general version (which translates to GitHub) and a private branch for your specialized code (which is not published to GitHub). However, I would like to add that git stash is an important tool that allows you to do what you want to do in the script that you draw (you are in the middle of working on a personal version and you will find a change in the general version).

A really good practice is always to make general changes to the shared branch and then do

 git checkout personal git merge general 

Now you can usefully use, in addition, git stash ; let's look at a scenario where you update a custom version and think about a general change:

  • You save the current changes in the specialized version:

     git stash 

    This delays changes compared to the last commit without creating a new commit. This is useful for storing work in progress.

  • You go to the common branch to make the general change you were thinking about:

     git checkout general # or master, or whatever name your general branch has 

    Then you can do your general modification and commit it as usual.

  • Before resuming work on your custom version, you import the general change:

     git checkout personal git merge general 

    git is smart enough to do it nicely: only the last, usually useful update should be made for your code.

  • You resume your work in a specialized branch by importing your hidden work:

     git stash pop 

It's all! The key is to use git stash to save the changes in the middle of your work, without creating a commit just for that, and then apply your changes with git stash pop .

+1
source

Use git submodules . If you want to keep a separate branch of a submodule, create a branch in this repo of the project and save all the changes locally in this branch and use only this branch in checking the submodule.

Merging different sets of changes is what you need to do half manually. git has excellent merge support, and if you don't keep the two branches too far apart, you can get minimal manual intervention. github (or any other hosting provider) really has nothing to do with this. If you want to keep the branch private, do not click on the public repo. Just like that.

0
source

Source: https://habr.com/ru/post/900895/


All Articles