{"thread":{"id":"45025","subject":"[PATCH v2] git-prompt.sh: add submodule indicator","startedAt":"2017-02-02T22:51:59Z","lastAt":"2017-02-02T22:52:04Z","messageCount":2,"participants":["Benjamin Fuchs"],"isPatch":true,"patchVersion":2,"patchTotal":null},"messages":[{"id":"310742","messageId":"1486075892-20676-1-git-send-email-email@benjaminfuchs.de","threadId":"45025","inReplyTo":null,"subject":"[PATCH v2] git-prompt.sh: add submodule indicator","fromName":"Benjamin Fuchs","fromEmail":"email@benjaminfuchs.de","sentAt":"2017-02-02T22:51:31Z","receivedAt":"2017-02-02T22:51:59Z","isPatch":true,"sender":{"key":"email@benjaminfuchs.de","avatar":null},"body":"Hi everyone again,\nI guess this time I'm rerolling my patch the right way.\nThanks again Gábor for your feedback.\nAnd thanks to Junio for being patient and explaining the reroll workflow \nGreeting,\nBenjamin\n\nBenjamin Fuchs (1):\n  git-prompt.sh: add submodule indicator\n\n contrib/completion/git-prompt.sh | 40 ++++++++++++++++++++++++++-\n t/t9903-bash-prompt.sh           | 59 ++++++++++++++++++++++++++++++++++++++++\n 2 files changed, 98 insertions(+), 1 deletion(-)\n\n-- \n2.7.4\n\n"},{"id":"310743","messageId":"1486075892-20676-2-git-send-email-email@benjaminfuchs.de","threadId":"45025","inReplyTo":"1486075892-20676-1-git-send-email-email@benjaminfuchs.de","subject":"[PATCH v2] git-prompt.sh: add submodule indicator","fromName":"Benjamin Fuchs","fromEmail":"email@benjaminfuchs.de","sentAt":"2017-02-02T22:51:32Z","receivedAt":"2017-02-02T22:52:04Z","isPatch":true,"sender":{"key":"email@benjaminfuchs.de","avatar":null},"body":"I expirienced that working with submodules can be confusing. A submodule can be\nanywhere in your parent git repository. While walking through the parent\nrepository it would be good to have a reminder to know when you entered a\nsubmodule.\n\nThis new indicator will show if you are in a submodule. The new prompt will look\nlike this: (sub:master). If the currently checked out submodule commit does not\nmatch the SHA-1 found in the index of the containing repository a \"+\" will be\nprepended (+sub:master). Adding a new optional env variable for the new feature.\n\nSigned-off-by: Benjamin Fuchs <email@benjaminfuchs.de>\n---\n contrib/completion/git-prompt.sh | 40 ++++++++++++++++++++++++++-\n t/t9903-bash-prompt.sh           | 59 ++++++++++++++++++++++++++++++++++++++++\n 2 files changed, 98 insertions(+), 1 deletion(-)\n\ndiff --git a/contrib/completion/git-prompt.sh b/contrib/completion/git-prompt.sh\nindex 97eacd7..9a0c4af 100644\n--- a/contrib/completion/git-prompt.sh\n+++ b/contrib/completion/git-prompt.sh\n@@ -93,6 +93,13 @@\n # directory is set up to be ignored by git, then set\n # GIT_PS1_HIDE_IF_PWD_IGNORED to a nonempty value. Override this on the\n # repository level by setting bash.hideIfPwdIgnored to \"false\".\n+#\n+# If you would like __git_ps1 to indicate that you are in a submodule,\n+# set GIT_PS1_SHOWSUBMODULE to a nonempty value. In this case the name\n+# of the submodule will be prepended to the branch name (e.g. module:master).\n+# If you set GIT_PS1_SHOWDIRTYSTATE to a nonempty value, the name will be\n+# prepended by \"+\" if the currently checked out submodule commit does not\n+# match the SHA-1 found in the index of the containing repository.\n \n # check whether printf supports -v\n __git_printf_supports_v=\n@@ -284,6 +291,32 @@ __git_eread ()\n \ttest -r \"$f\" && read \"$@\" <\"$f\"\n }\n \n+# __git_ps1_submodule\n+# Requires the git dir set in $g by the caller.\n+# Returns the name of the submodule in $sub if we are currently inside one.\n+# The name will be prepended by \"+\" if the currently checked out submodule commit\n+# does not match the SHA-1 found in the index of the containing repository.\n+# NOTE: git_dir looks like in a ...\n+# - submodule:\t\"GIT_PARENT/.git/modules/PATH_TO_SUBMODULE\"\n+# - parent:\t\"GIT_PARENT/.git\" (exception \".\" in .git)\n+__git_ps1_submodule ()\n+{\n+\tlocal git_dir=\"$g\"\n+\tlocal submodule_name=\"$(basename \"$git_dir\")\"\n+\tif [ \"$submodule_name\" != \".git\" ] && [ \"$submodule_name\" != \".\" ]; then\n+\t\tlocal status=\"\"\n+\t\tif [ -n \"${GIT_PS1_SHOWDIRTYSTATE-}\" ] &&\n+\t\t   [ \"$(git config --bool bash.showDirtyState)\" != \"false\" ]\n+\t\tthen\n+\t\t\tlocal parent_top=\"${git_dir%.git*}\"\n+\t\t\tlocal submodule_top=\"${git_dir#*modules/}\"\n+\t\t\tgit -C \"$parent_top\" diff --no-ext-diff --ignore-submodules=dirty --quiet -- \"$submodule_top\" 2>/dev/null || status=\"+\"\n+\t\tfi\n+\n+\t\tsub=\"$status$submodule_name:\"\n+\tfi\n+}\n+\n # __git_ps1 accepts 0 or 1 arguments (i.e., format string)\n # when called from PS1 using command substitution\n # in this mode it prints text to add to bash PS1 prompt (includes branch name)\n@@ -513,8 +546,13 @@ __git_ps1 ()\n \t\tb=\"\\${__git_ps1_branch_name}\"\n \tfi\n \n+\tlocal sub=\"\"\n+\tif [ -n \"${GIT_PS1_SHOWSUBMODULE-}\" ]; then\n+\t\t__git_ps1_submodule\n+\tfi\n+\n \tlocal f=\"$w$i$s$u\"\n-\tlocal gitstring=\"$c$b${f:+$z$f}$r$p\"\n+\tlocal gitstring=\"$c$sub$b${f:+$z$f}$r$p\"\n \n \tif [ $pcmode = yes ]; then\n \t\tif [ \"${__git_printf_supports_v-}\" != yes ]; then\ndiff --git a/t/t9903-bash-prompt.sh b/t/t9903-bash-prompt.sh\nindex 97c9b32..ac82c99 100755\n--- a/t/t9903-bash-prompt.sh\n+++ b/t/t9903-bash-prompt.sh\n@@ -16,9 +16,22 @@ c_lblue='\\\\[\\\\e[1;34m\\\\]'\n c_clear='\\\\[\\\\e[0m\\\\]'\n \n test_expect_success 'setup for prompt tests' '\n+\tmkdir .subrepo &&\n+\t(cd .subrepo &&\n+\t\tgit init &&\n+\t\techo 1 >file &&\n+\t\tgit add file &&\n+\t\tgit commit -m initial &&\n+\t\tgit checkout -b dirty &&\n+\t\techo 2 >file &&\n+\t\tgit commit -m \"dirty branch\" file\n+\t) &&\n \tgit init otherrepo &&\n \techo 1 >file &&\n \tgit add file &&\n+\tgit submodule add ./.subrepo sub &&\n+\tgit -C sub checkout master &&\n+\tgit add sub &&\n \ttest_tick &&\n \tgit commit -m initial &&\n \tgit tag -a -m msg1 t1 &&\n@@ -755,4 +768,50 @@ test_expect_success 'prompt - hide if pwd ignored - inside gitdir (stderr)' '\n \ttest_cmp expected \"$actual\"\n '\n \n+test_expect_success 'prompt - submodule indicator' '\n+\tprintf \" (sub:master)\" >expected &&\n+\t(\n+\t\tcd sub &&\n+\t\tGIT_PS1_SHOWSUBMODULE=y &&\n+\t\t__git_ps1 >\"$actual\"\n+\t) &&\n+\ttest_cmp expected \"$actual\"\n+'\n+\n+test_expect_success 'prompt - submodule indicator - disabled' '\n+\tprintf \" (master)\" >expected &&\n+\t(\n+\t\tcd sub &&\n+\t\tGIT_PS1_SHOWSUBMODULE= &&\n+\t\t__git_ps1 >\"$actual\"\n+\t) &&\n+\ttest_cmp expected \"$actual\"\n+'\n+\n+test_expect_success 'prompt - submodule indicator - dirty status indicator' '\n+\tprintf \" (+sub:dirty)\" >expected &&\n+\tgit -C sub checkout dirty &&\n+\ttest_when_finished \"git -C sub checkout master\" &&\n+\t(\n+\t\tcd sub &&\n+\t\tGIT_PS1_SHOWSUBMODULE=y &&\n+\t\tGIT_PS1_SHOWDIRTYSTATE=y &&\n+\t\t__git_ps1 >\"$actual\"\n+\t) &&\n+\ttest_cmp expected \"$actual\"\n+'\n+\n+test_expect_success 'prompt - submodule indicator - dirty status indicator disabled' '\n+\tprintf \" (sub:dirty)\" >expected &&\n+\tgit -C sub checkout dirty &&\n+\ttest_when_finished \"git -C sub checkout master\" &&\n+\t(\n+\t\tcd sub &&\n+\t\tGIT_PS1_SHOWSUBMODULE=y &&\n+\t\tGIT_PS1_SHOWDIRTYSTATE= &&\n+\t\t__git_ps1 >\"$actual\"\n+\t) &&\n+\ttest_cmp expected \"$actual\"\n+'\n+\n test_done\n-- \n2.7.4\n\n"}]}