Uploaded image for project: 'Data Management'
  1. Data Management
  2. DM-3236

Deleting a remote branch is not noticed by Jenkins

    XMLWordPrintable

    Details

      Description

      In working on DM-3182 I created a branch tickets/DM-3182 of meas_deblender. I then made further changes to the main code that eliminated the need for changes to meas_deblender so I deleted its remote branch tickets/DM-3182 using:

      localhost$ git push origin --delete tickets/DM-3182
      To git@github.com:lsst/meas_deblender.git
       - [deleted]         tickets/DM-3182
      

      I then ran Jenkins again and it still found that branch of meas_deblender instead of using master. This may be user error on my part or a quirk of lsstsw. It's not a big deal – I worked around it using "git revert" to undo the changes on that ticket branch (thereby recreating the remote branch, of course). But if it is actually a bug in lsstsw then I'd like to at least report it so we have a record of it in case anyone else stumbles across it.

        Attachments

          Issue Links

            Activity

            Hide
            jhoblitt Joshua Hoblitt added a comment -

            How does git fetch -p result in the local checkout of a branch being removed?

            Consider this simple test:

            #!/bin/bash
             
            set -e
             
            mkdir gittest
            cd gittest/
            # simulate a canonical remote repo
            (
            mkdir canonical_repo
            cd canonical_repo
            git init --bare
            )
            # add a couple of branches to said repo
            (
            git clone canonical_repo user_clone
            cd user_clone
            touch a_file
            git add a_file
            git commit -m"a commit"
            git push origin master
            git checkout -b foo
            touch anotherfile
            git add anotherfile
            git commit -m"another commit"
            git push origin foo
            )
            # lsst-build like checkout of foo branch
            (
            git clone canonical_repo build_clone -b foo
            cd build_clone
            git branch -a
            )
            # rm foo branch from canoncial_repo
            (
            cd user_clone
            git push origin :foo
            )
            # lsst-build like fetch -p
            (
            cd build_clone
            git fetch -p
            git branch -a
            )
            

            This simple example results in a repo that still has a local branch named foo:

            * foo
              remotes/origin/HEAD -> origin/master
              remotes/origin/master
            

            Show
            jhoblitt Joshua Hoblitt added a comment - How does git fetch -p result in the local checkout of a branch being removed? Consider this simple test: #!/bin/bash   set -e   mkdir gittest cd gittest/ # simulate a canonical remote repo ( mkdir canonical_repo cd canonical_repo git init --bare ) # add a couple of branches to said repo ( git clone canonical_repo user_clone cd user_clone touch a_file git add a_file git commit -m "a commit" git push origin master git checkout -b foo touch anotherfile git add anotherfile git commit -m "another commit" git push origin foo ) # lsst-build like checkout of foo branch ( git clone canonical_repo build_clone -b foo cd build_clone git branch -a ) # rm foo branch from canoncial_repo ( cd user_clone git push origin :foo ) # lsst-build like fetch -p ( cd build_clone git fetch -p git branch -a ) This simple example results in a repo that still has a local branch named foo : * foo remotes/origin/HEAD -> origin/master remotes/origin/master
            Hide
            gcomoretto Gabriele Comoretto [X] (Inactive) added a comment -

            Joshua Hoblitt, this does not correspond with what in lsst_build tickets/DM-3236 branch, where I keep both git fetch:

             

                    # update from origin

                    if not self.no_fetch:

                        # the line below should be equivalent to:

                        #     git.fetch("origin", "-force", "-prune")

                        #     git.fetch("origin", "-force", "-tags")

                        # but avoids the overhead of two (possibly remote) git calls.

                        git.fetch("-fup", "origin", "+refs/heads/:refs/heads/", "refs/tags/:refs/tags/")

                        git.fetch("-p")

             

            I know, is not optimal, but this works, as demonstrated above

             

            Show
            gcomoretto Gabriele Comoretto [X] (Inactive) added a comment - Joshua Hoblitt , this does not correspond with what in lsst_build tickets/ DM-3236 branch, where I keep both git fetch:           # update from origin         if not self.no_fetch:             # the line below should be equivalent to:             #     git.fetch("origin", "- force", " -prune")             #     git.fetch("origin", "- force", " -tags")             # but avoids the overhead of two (possibly remote) git calls.             git.fetch("-fup", "origin", "+refs/heads/ :refs/heads/ ", "refs/tags/ :refs/tags/ ")             git.fetch("-p")   I know, is not optimal, but this works, as demonstrated above  
            Hide
            gcomoretto Gabriele Comoretto [X] (Inactive) added a comment -

            PR created:

            https://github.com/lsst/lsst_build/pull/27

            It is probably more easy to discuss on the actual changes done in Git.

            Show
            gcomoretto Gabriele Comoretto [X] (Inactive) added a comment - PR created: https://github.com/lsst/lsst_build/pull/27 It is probably more easy to discuss on the actual changes done in Git.
            Hide
            jhoblitt Joshua Hoblitt added a comment - - edited

            I think I've convinced myself that this works but it is a bit scary. Consider this Dockerfile:

            FROM lsstsqre/newinstall
             
            ARG LSST_BUILD_URL=https://github.com/lsst/lsst_build
            ARG LSST_BUILD_REF=tickets/DM-3236
             
            USER root
             
            # install modern git needed by pkgautoversion
            RUN yum install -y rh-git29
            RUN echo ". /opt/rh/rh-git29/enable" > "/etc/profile.d/rh-git29.sh"
            RUN git config --global user.email "you@example.com" && \
                git config --global user.name "Your Name"
             
            # source loadLSST.bash by default for python + eups
            RUN echo ". $(pwd)/loadLSST.bash" > "/etc/profile.d/loadLSST.sh"
             
            # install lsst-build
            RUN git clone "$LSST_BUILD_URL" -b "$LSST_BUILD_REF"
            RUN cd lsst_build && python setup.py install
             
            # create bare repo testpk1.git with master & feature1
            RUN mkdir -p testpkg1 && \
                cd testpkg1 && \
                git init && \
                mkdir ups && \
                touch ups/testpkg1.table && \
                git add ups/testpkg1.table && \
                git commit -m"fwv" && \
                git checkout -b feature1 && \
                touch feature1 && \
                git add feature1 && \
                git commit -m"add feature1" && \
                git checkout master
            RUN mv testpkg1/.git testpkg1.git && \
                rm -rf testpkg1 && \
                cd testpkg1.git && \
                git config --bool core.bare true
            RUN echo "testpkg1: $(pwd)/testpkg1.git" > repos.yaml
             
            # create testpkg2 which depends on testpkg1
            RUN mkdir -p testpkg2 && \
                cd testpkg2 && \
                git init && \
                mkdir ups && \
                echo "setupRequired(testpkg1)" > ups/testpkg2.table && \
                git add ups/testpkg2.table && \
                git commit -m"fwv" && \
                git checkout -b feature1 && \
                touch feature1 && \
                git add feature1 && \
                git commit -m"add feature1" && \
                git checkout master
            RUN mv testpkg2/.git testpkg2.git && \
                rm -rf testpkg2 && \
                cd testpkg2.git && \
                git config --bool core.bare true
            RUN echo "testpkg2: $(pwd)/testpkg2.git" >> repos.yaml
             
            # lsst-build "build" dir
            RUN mkdir build
             
            # prepare feature1 branch
            RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 \
                --ref feature1
             
            # show clone branch state
            RUN cd build/testpkg1 && \
                git branch -a
            RUN cd build/testpkg2 && \
                git branch -a
             
            # rm feature1 branch from testpkg1
            RUN git clone testpkg1.git testpkg1 && \
                cd testpkg1 && \
                git push origin :feature1 && \
                rm -rf testpkg1
             
            # prepare feature1 branch
            RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 \
                --ref feature1
             
            # show clone branch state
            RUN cd build/testpkg1 && \
                git branch -a
            RUN cd build/testpkg2 && \
                git branch -a
            

            The tail end of the stdout is:

            $ docker build . --no-cache
            ...
            Step 19/25 : RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2     --ref feature1
             ---> Running in fa9099c2d558
                        testpkg2:  ok (0.1 sec).
                        testpkg1:  ok (0.1 sec).
            Removing intermediate container fa9099c2d558
             ---> c9565612a26f
            Step 20/25 : RUN cd build/testpkg1 &&     git branch -a
             ---> Running in a26ab1a987f2
            * feature1
              master
              remotes/origin/HEAD -> origin/master
              remotes/origin/feature1
              remotes/origin/master
            Removing intermediate container a26ab1a987f2
             ---> 4c39ee2ab99a
            Step 21/25 : RUN cd build/testpkg2 &&     git branch -a
             ---> Running in 434fb449b3dd
            * feature1
              master
              remotes/origin/HEAD -> origin/master
              remotes/origin/feature1
              remotes/origin/master
            Removing intermediate container 434fb449b3dd
             ---> 841f3ac618da
            Step 22/25 : RUN git clone testpkg1.git testpkg1 &&     cd testpkg1 &&     git push origin :feature1 &&     rm -rf testpkg1
             ---> Running in 937156873bd7
            Cloning into 'testpkg1'...
            done.
            To /opt/lsst/software/stack/testpkg1.git
             - [deleted]         feature1
            Removing intermediate container 937156873bd7
             ---> 89e11053c5d3
            Step 23/25 : RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2     --ref feature1
             ---> Running in 979b9ba1df7b
                        testpkg2:  ok (0.0 sec).
                        testpkg1:  ok (0.0 sec).
            Removing intermediate container 979b9ba1df7b
             ---> fa1340a7f880
            Step 24/25 : RUN cd build/testpkg1 &&     git branch -a
             ---> Running in b1a759c57cca
            * master
              remotes/origin/HEAD -> origin/master
              remotes/origin/master
            Removing intermediate container b1a759c57cca
             ---> cd2653ea59c0
            Step 25/25 : RUN cd build/testpkg2 &&     git branch -a
             ---> Running in 7500e6b0834e
            * feature1
              master
              remotes/origin/HEAD -> origin/master
              remotes/origin/feature1
              remotes/origin/master
            Removing intermediate container 7500e6b0834e
             ---> 557848e3ba06
            Successfully built 557848e3ba06
            

            What appears to be happening is that the second invocation of git fetch -p is leaving the repo with a broken HEAD – I'm wondering if this is legitimately a bug.

            $ cat .git/HEAD 
            ref: refs/heads/feature1
            $ cat .git/refs/heads/feature1
            cat: .git/refs/heads/feature1: No such file or directory
            

            I think this is probably acceptable, at least in the context of lsstsw where the git version in pinned, but really should have verbose explanation of the problem being solved and why it works as a code comment. An acceptance test that runs under travis is also needed specifically to catch if this breaks with future versions of git.

            Show
            jhoblitt Joshua Hoblitt added a comment - - edited I think I've convinced myself that this works but it is a bit scary. Consider this Dockerfile : FROM lsstsqre/newinstall   ARG LSST_BUILD_URL=https: //github.com/lsst/lsst_build ARG LSST_BUILD_REF=tickets/DM- 3236   USER root   # install modern git needed by pkgautoversion RUN yum install -y rh-git29 RUN echo ". /opt/rh/rh-git29/enable" > "/etc/profile.d/rh-git29.sh" RUN git config --global user.email "you@example.com" && \ git config --global user.name "Your Name"   # source loadLSST.bash by default for python + eups RUN echo ". $(pwd)/loadLSST.bash" > "/etc/profile.d/loadLSST.sh"   # install lsst-build RUN git clone "$LSST_BUILD_URL" -b "$LSST_BUILD_REF" RUN cd lsst_build && python setup.py install   # create bare repo testpk1.git with master & feature1 RUN mkdir -p testpkg1 && \ cd testpkg1 && \ git init && \ mkdir ups && \ touch ups/testpkg1.table && \ git add ups/testpkg1.table && \ git commit -m "fwv" && \ git checkout -b feature1 && \ touch feature1 && \ git add feature1 && \ git commit -m "add feature1" && \ git checkout master RUN mv testpkg1/.git testpkg1.git && \ rm -rf testpkg1 && \ cd testpkg1.git && \ git config --bool core.bare true RUN echo "testpkg1: $(pwd)/testpkg1.git" > repos.yaml   # create testpkg2 which depends on testpkg1 RUN mkdir -p testpkg2 && \ cd testpkg2 && \ git init && \ mkdir ups && \ echo "setupRequired(testpkg1)" > ups/testpkg2.table && \ git add ups/testpkg2.table && \ git commit -m "fwv" && \ git checkout -b feature1 && \ touch feature1 && \ git add feature1 && \ git commit -m "add feature1" && \ git checkout master RUN mv testpkg2/.git testpkg2.git && \ rm -rf testpkg2 && \ cd testpkg2.git && \ git config --bool core.bare true RUN echo "testpkg2: $(pwd)/testpkg2.git" >> repos.yaml   # lsst-build "build" dir RUN mkdir build   # prepare feature1 branch RUN lsst-build prepare --repos= "$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 \ --ref feature1   # show clone branch state RUN cd build/testpkg1 && \ git branch -a RUN cd build/testpkg2 && \ git branch -a   # rm feature1 branch from testpkg1 RUN git clone testpkg1.git testpkg1 && \ cd testpkg1 && \ git push origin :feature1 && \ rm -rf testpkg1   # prepare feature1 branch RUN lsst-build prepare --repos= "$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 \ --ref feature1   # show clone branch state RUN cd build/testpkg1 && \ git branch -a RUN cd build/testpkg2 && \ git branch -a The tail end of the stdout is: $ docker build . --no-cache ... Step 19/25 : RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 --ref feature1 ---> Running in fa9099c2d558 testpkg2: ok (0.1 sec). testpkg1: ok (0.1 sec). Removing intermediate container fa9099c2d558 ---> c9565612a26f Step 20/25 : RUN cd build/testpkg1 && git branch -a ---> Running in a26ab1a987f2 * feature1 master remotes/origin/HEAD -> origin/master remotes/origin/feature1 remotes/origin/master Removing intermediate container a26ab1a987f2 ---> 4c39ee2ab99a Step 21/25 : RUN cd build/testpkg2 && git branch -a ---> Running in 434fb449b3dd * feature1 master remotes/origin/HEAD -> origin/master remotes/origin/feature1 remotes/origin/master Removing intermediate container 434fb449b3dd ---> 841f3ac618da Step 22/25 : RUN git clone testpkg1.git testpkg1 && cd testpkg1 && git push origin :feature1 && rm -rf testpkg1 ---> Running in 937156873bd7 Cloning into 'testpkg1'... done. To /opt/lsst/software/stack/testpkg1.git - [deleted] feature1 Removing intermediate container 937156873bd7 ---> 89e11053c5d3 Step 23/25 : RUN lsst-build prepare --repos="$(pwd)/repos.yaml" "$(pwd)/build" testpkg2 --ref feature1 ---> Running in 979b9ba1df7b testpkg2: ok (0.0 sec). testpkg1: ok (0.0 sec). Removing intermediate container 979b9ba1df7b ---> fa1340a7f880 Step 24/25 : RUN cd build/testpkg1 && git branch -a ---> Running in b1a759c57cca * master remotes/origin/HEAD -> origin/master remotes/origin/master Removing intermediate container b1a759c57cca ---> cd2653ea59c0 Step 25/25 : RUN cd build/testpkg2 && git branch -a ---> Running in 7500e6b0834e * feature1 master remotes/origin/HEAD -> origin/master remotes/origin/feature1 remotes/origin/master Removing intermediate container 7500e6b0834e ---> 557848e3ba06 Successfully built 557848e3ba06 What appears to be happening is that the second invocation of git fetch -p is leaving the repo with a broken HEAD – I'm wondering if this is legitimately a bug. $ cat .git/HEAD ref: refs/heads/feature1 $ cat .git/refs/heads/feature1 cat: .git/refs/heads/feature1: No such file or directory I think this is probably acceptable, at least in the context of lsstsw where the git version in pinned, but really should have verbose explanation of the problem being solved and why it works as a code comment. An acceptance test that runs under travis is also needed specifically to catch if this breaks with future versions of git .
            Hide
            jhoblitt Joshua Hoblitt added a comment -

            I've asked for the changes described in my previous comment on the gh pr.

            Show
            jhoblitt Joshua Hoblitt added a comment - I've asked for the changes described in my previous comment on the gh pr.

              People

              Assignee:
              gcomoretto Gabriele Comoretto [X] (Inactive)
              Reporter:
              rowen Russell Owen
              Reviewers:
              Tim Jenness
              Watchers:
              Chris Morrison, Chris Morrison [X] (Inactive), Frossie Economou, Gabriele Comoretto [X] (Inactive), Jim Bosch, John Parejko, Joshua Hoblitt, Russell Owen, Tim Jenness
              Votes:
              0 Vote for this issue
              Watchers:
              9 Start watching this issue

                Dates

                Created:
                Updated:
                Resolved:

                  Jenkins

                  No builds found.