threads / discuss / 29205

Re: post-receive for web deployment

Subject: Re: post-receive for web deployment

## tl;dr

4 messages between Dec 19, 2011 and Dec 19, 2011.

replies: 3people: 3as markdown or json

Stephen Major· Dec 19, 2011, 02:42 UTC · lore
Hello,

I am having some difficulty understanding what I am doing wrong when working with git to deploy a website through the use of a post-receive hook on the remote.

Here is the script:
#!/bin/sh

staging_path="/home/user/domains/domain.com/public_html/staging" live_path="/home/user/domains/domain.com/public_html/live"

while read oldrev newrev ref do

    branch=$(echo $ref | cut -d/ -f3)
    # ***
    # update the live site
    #
    if [[ "master" == "$branch" ]]; then
        export GIT_WORK_TREE=$live_path
        git checkout -f $branch
        echo "Release has been pushed to production"
    # ***
    # we update the staging server with the latest push
    #
    elif [[ "develop" == "$branch" ]]; then
        echo "Resetting staging tree"
        export GIT_WORK_TREE=$staging_path
        git checkout -f $branch
        echo "Develop has been pushed to staging"
    fi
done
This is what we have done:

git checkout develop touch 1 2 3 4 5 6 git add . git commit -am "added some files" git push origin develop

checking the remote server now all files are found in: /home/user/domains/domain.com/public_html/staging

git checkout master git merge develop git push origin master

checking the remote server now all files are found in: /home/user/domains/domain.com/public_html/live

git checkout develop git rm 4 5 6 git commit -am "removed some files" git push origin develop

checking the remote server now files 4 5 6 have been removed from: /home/user/domains/domain.com/public_html/staging

git checkout master git merge develop git push origin master

checking the remote server files 4 5 6 are still found in: /home/user/domains/domain.com/public_html/live

Why is this happening? checking the local repo for master shows the files are removed there... pulling the latest from origin:master shows the files have been removed... but why were they not removed from the working tree like they were on the staging working tree?

well I think it has something to do with later commits and therefor the working tree of the live server could quickly become out of sync with the development tree

a quick test, lets checkout master again and perform the removes directly on it then push it back:

git checkout master git rm 1 2 3 git commit -am "removed 1 2 3" git push origin master

checking the remote server now files 1 2 3 have been removed from: /home/user/domains/domain.com/public_html/live

Okay weird so they remove when the commit happens directly on that branch and is pushed to the remote but they dont get removed if the removal happened on a different branch and is merged in then pushed to the remote....

anyone have an explanation or a workaround?
Johannes Sixt· Dec 19, 2011, 06:55 UTC · re: Stephen Major · lore
Am 12/19/2011 3:42, schrieb Stephen Major:
> checking the remote server files 4 5 6 are still found in:
> /home/user/domains/domain.com/public_html/live
> 
> Why is this happening?

Before you check out the files, you must ensure that the index matches the content in the GIT_WORK_TREE that you populate by git checkout.

You first push a tree that removes 4 5 6 while the index you happen to have still has those files recorded, the files are removed. Your second push does not have these files anymore, but the index does not record the files anymore, either; therefore, git does not act on the files 4 5 6 that happen to live in the other worktree.

Perhaps you should maintain separate index files and set GIT_INDEX_FILE accordingly before git checkout.

-- Hannes
Sitaram Chamarty· Dec 19, 2011, 10:35 UTC · re: Stephen Major · lore
On Mon, Dec 19, 2011 at 8:12 AM, Stephen Major <smajor@gmail.com> wrote:
Show 5 quoted lines
> Hello,
>
> I am having some difficulty understanding what I am doing wrong when
> working with git to deploy a website through the use of a post-receive
> hook on the remote.

The most common issue I have seen in cases like this is that you need to 'unset GIT_DIR'. In fact, anytime you play around with running stuff from *inside* a hook that works fine when you run it from outside, you need to check what GIT_ variables are present.

I believe 'unset `git rev-parse --local-env-vars`' is a good idea too; probably much simpler.

Stephen Major· Dec 19, 2011, 12:42 UTC · re: Sitaram Chamarty · lore

After some playing I found using git clone to export to the staging path and then doing git checkout -f master for the production path keeps the files in the production tree clean while leaving any un-tracked files in tact, seems what Johannes said was true and this seems like a simple workaround... not sure about working with indexes like he pointed out.

echo "Resetting staging tree" rm -rf staging.git $staging_path git --work-tree=$staging_path clone ./ staging.git

echo "Resetting production tree" git --work-tree=$live_path checkout -f master

On Mon, Dec 19, 2011 at 2:35 AM, Sitaram Chamarty <sitaramc@gmail.com> wrote:
Show 14 quoted lines
> On Mon, Dec 19, 2011 at 8:12 AM, Stephen Major <smajor@gmail.com> wrote:
>> Hello,
>>
>> I am having some difficulty understanding what I am doing wrong when
>> working with git to deploy a website through the use of a post-receive
>> hook on the remote.
>
> The most common issue I have seen in cases like this is that you need
> to 'unset GIT_DIR'.  In fact, anytime you play around with running
> stuff from *inside* a hook that works fine when you run it from
> outside, you need to check what GIT_ variables are present.
>
> I believe 'unset `git rev-parse --local-env-vars`' is a good idea too;
> probably much simpler.

← back to recent threads