6

I have a repository consisting of four files in the master branch: two project files (PHP files btw) plus a README.md and .gitignore. I would like to create an additional branch, that consists of just the two PHP files at the same commit-level. What's the best practice to keep those two branches in-sync, if possible I would like to commit once only to update my PHP files?

The reason why I'm looking into this, is that I would like to create a branch called dist, that only comes with the essential files.

idleberg
  • 12,634
  • 7
  • 43
  • 70

2 Answers2

4

Create your dist branch, recording the deletion of the files you don't want.

git checkout master
git checkout -b dist
git rm .gitignore
git rm README.md
git commit -m "Remove non-dist files"

Then, each time you want to update your dist branch, simply rebase it:

git checkout dist
git rebase master

That replay your dist commit (which you made when you created that branch, and where you git rm some files) on top of master, which means it will always remove the extra files.

You will have to force push it to your remote, but that isn't an issue since nobody is supposed to contribute on that branch.


That being said, release management is generally not maintained through branching, but with a script able to package and release from the sources (meaning here one script in the master branch that you execute in order to copy what is needed to where you want to deploy).

Community
  • 1
  • 1
VonC
  • 1,262,500
  • 529
  • 4,410
  • 5,250
  • Thank you @VonC, I will give this a try. I haven't yet worked with rebase before (I think!), but wouldn't I have to repeat all these steps each time I commit? I also just stumbled across [this method](http://lea.verou.me/2011/10/easily-keep-gh-pages-in-sync-with-master/) which probably requires less interaction. – idleberg May 31 '14 at 10:57
  • To give some background on why I'm trying to achieve this. I have created a [basic linter](https://github.com/idleberg/sublimetext-gruntfile.js) for my Sublime Text addons. This linter is basically consists on npm packages, grunt tasks and `.travis.yml`. While the master branch comes with a `README.md` and `.gitignore`, I do not want these files in the dist branch, since this is intended to be used exclusively with Fetch. There's no need to interfere with a user's own `README.md` and `.gitignore` files. – idleberg May 31 '14 at 11:01
3

As @VonC says, Git's not set up as a release-management or a deployment tool. You're far from the first to notice that it's tantalizingly close :-) -- so it's pretty easy to get it to do what you want.

Here's how you make a commit-able tree using just the content you want, without needing a checkout. Put this in .git/post-commit and maybe link to it from .git/hooks/post-merge, from then on the branch is maintained automatically.

#!/bin/sh
files="this.php that/other.php"
branch=pub

# build a tree with selected already-committed content
new_tree=$(
  export GIT_INDEX_FILE=.git/sideband-index
  git read-tree --empty
  git ls-tree HEAD --  $files \
  | git update-index --index-info --add
  git write-tree
);

# commit the new tree to the tip of "$branch"
# if it doesn't match what's already there
current=$(git rev-parse -q --verify $branch:)
test $new_tree != "$current" \
&& git update-ref refs/heads/$branch $(
    git commit-tree ${current:+-p $branch} -m new\ content $new_tree
)

The unfamiliar commands (pretty much all of them, here) are the ones built for use by scripters, they're meant for this.

jthill
  • 55,082
  • 5
  • 77
  • 137
  • I understand what you said in http://stackoverflow.com/questions/23962446/can-i-merge-sync-a-sub-folder-from-one-branch-to-the-root-of-another-in-git/23983197#comment36957117_23983197, but come on: the rebase I proposed? Surely that isn't so much out of the OP's comfort zone ;) Anyway, +1. – VonC Jun 02 '14 at 04:46
  • @VonC You're right, of course, I've been a bit lazy. – jthill Jun 02 '14 at 08:12
  • I'm trying to use the script but it's hiccuping on the last line of the code. I think it's related to the left curly brace not matching the right bracket. Also, is the '+' in '+-p' correct? – Wookiem May 22 '17 at 10:20
  • @Wookiem Yow. Thanks for pointing out the mismatched braces, fixed. The `:+` is shell expansion syntax for "substitute what follows if the variable's not empty", if there's anything in `current` the shell will sub in `-p $branch` there. – jthill May 22 '17 at 13:31