feat(git): branch status switch

resolves #438
This commit is contained in:
Jan De Dobbeleer 2021-02-19 19:31:58 +01:00 committed by Jan De Dobbeleer
parent 0c17b30dc6
commit 2ab7ff94d7
4 changed files with 66 additions and 12 deletions

View file

@ -35,6 +35,7 @@ Local changes can also shown by default using the following syntax for both the
### Standard ### Standard
- branch_icon: `string` - the icon to use in front of the git branch name - defaults to `\uE0A0 ` - branch_icon: `string` - the icon to use in front of the git branch name - defaults to `\uE0A0 `
- display_branch_status: `boolean` - display the branch status or not - defaults to `true`
- branch_identical_icon: `string` - the icon to display when remote and local are identical - defaults to `\uF0C9` - branch_identical_icon: `string` - the icon to display when remote and local are identical - defaults to `\uF0C9`
- branch_ahead_icon: `string` - the icon to display when the local branch is ahead of its remote - defaults to `\uF176` - branch_ahead_icon: `string` - the icon to display when the local branch is ahead of its remote - defaults to `\uF176`
- branch_behind_icon: `string` - the icon to display when the local branch is behind its remote - defaults to `\uF175` - branch_behind_icon: `string` - the icon to display when the local branch is behind its remote - defaults to `\uF175`

View file

@ -52,6 +52,8 @@ type git struct {
const ( const (
// BranchIcon the icon to use as branch indicator // BranchIcon the icon to use as branch indicator
BranchIcon Property = "branch_icon" BranchIcon Property = "branch_icon"
// DisplayBranchStatus show branch status or not
DisplayBranchStatus Property = "display_branch_status"
// BranchIdenticalIcon the icon to display when the remote and local branch are identical // BranchIdenticalIcon the icon to display when the remote and local branch are identical
BranchIdenticalIcon Property = "branch_identical_icon" BranchIdenticalIcon Property = "branch_identical_icon"
// BranchAheadIcon the icon to display when the local branch is ahead of the remote // BranchAheadIcon the icon to display when the local branch is ahead of the remote
@ -153,18 +155,8 @@ func (g *git) string() string {
if !displayStatus { if !displayStatus {
return buffer.String() return buffer.String()
} }
// if ahead, print with symbol if g.props.getBool(DisplayBranchStatus, true) {
if g.repo.ahead > 0 { buffer.WriteString(g.getBranchStatus())
fmt.Fprintf(buffer, " %s%d", g.props.getString(BranchAheadIcon, "\u2191"), g.repo.ahead)
}
// if behind, print with symbol
if g.repo.behind > 0 {
fmt.Fprintf(buffer, " %s%d", g.props.getString(BranchBehindIcon, "\u2193"), g.repo.behind)
}
if g.repo.behind == 0 && g.repo.ahead == 0 && g.repo.upstream != "" {
fmt.Fprintf(buffer, " %s", g.props.getString(BranchIdenticalIcon, "\u2261"))
} else if g.repo.upstream == "" {
fmt.Fprintf(buffer, " %s", g.props.getString(BranchGoneIcon, "\u2262"))
} }
if g.repo.staging.changed { if g.repo.staging.changed {
fmt.Fprint(buffer, g.getStatusDetailString(g.repo.staging, StagingColor, LocalStagingIcon, " \uF046")) fmt.Fprint(buffer, g.getStatusDetailString(g.repo.staging, StagingColor, LocalStagingIcon, " \uF046"))
@ -186,6 +178,25 @@ func (g *git) init(props *properties, env environmentInfo) {
g.env = env g.env = env
} }
func (g *git) getBranchStatus() string {
if g.repo.ahead > 0 && g.repo.behind > 0 {
return fmt.Sprintf(" %s%d %s%d", g.props.getString(BranchAheadIcon, "\u2191"), g.repo.ahead, g.props.getString(BranchBehindIcon, "\u2193"), g.repo.behind)
}
if g.repo.ahead > 0 {
return fmt.Sprintf(" %s%d", g.props.getString(BranchAheadIcon, "\u2191"), g.repo.ahead)
}
if g.repo.behind > 0 {
return fmt.Sprintf(" %s%d", g.props.getString(BranchBehindIcon, "\u2193"), g.repo.behind)
}
if g.repo.behind == 0 && g.repo.ahead == 0 && g.repo.upstream != "" {
return fmt.Sprintf(" %s", g.props.getString(BranchIdenticalIcon, "\u2261"))
}
if g.repo.upstream == "" {
return fmt.Sprintf(" %s", g.props.getString(BranchGoneIcon, "\u2262"))
}
return ""
}
func (g *git) getStatusDetailString(status *gitStatus, color, icon Property, defaultIcon string) string { func (g *git) getStatusDetailString(status *gitStatus, color, icon Property, defaultIcon string) string {
prefix := g.props.getString(icon, defaultIcon) prefix := g.props.getString(icon, defaultIcon)
foregroundColor := g.props.getColor(color, g.props.foreground) foregroundColor := g.props.getColor(color, g.props.foreground)

View file

@ -701,3 +701,39 @@ func TestGetStatusDetailStringNoStatusColorOverride(t *testing.T) {
} }
assert.Equal(t, expected, g.getStatusDetailString(status, WorkingColor, LocalWorkingIcon, "icon")) assert.Equal(t, expected, g.getStatusDetailString(status, WorkingColor, LocalWorkingIcon, "icon"))
} }
func TestGetBranchStatus(t *testing.T) {
cases := []struct {
Case string
Expected string
Ahead int
Behind int
Upstream string
}{
{Case: "Equal with remote", Expected: " equal", Upstream: "main"},
{Case: "Ahead", Expected: " up2", Ahead: 2},
{Case: "Behind", Expected: " down8", Behind: 8},
{Case: "Behind and ahead", Expected: " up7 down8", Behind: 8, Ahead: 7},
{Case: "Gone", Expected: " gone"},
{Case: "Default (bug)", Expected: "", Behind: -8, Upstream: "wonky"},
}
for _, tc := range cases {
g := &git{
props: &properties{
values: map[Property]interface{}{
BranchAheadIcon: "up",
BranchBehindIcon: "down",
BranchIdenticalIcon: "equal",
BranchGoneIcon: "gone",
},
},
repo: &gitRepo{
ahead: tc.Ahead,
behind: tc.Behind,
upstream: tc.Upstream,
},
}
assert.Equal(t, tc.Expected, g.getBranchStatus(), tc.Case)
}
}

View file

@ -484,6 +484,12 @@
"description": "The icon to use in front of the git branch name", "description": "The icon to use in front of the git branch name",
"default": "\uE0A0 " "default": "\uE0A0 "
}, },
"display_branch_status": {
"type": "boolean",
"title": "Display Branch Status",
"description": "Display the branch status or not",
"default": true
},
"branch_identical_icon": { "branch_identical_icon": {
"type": "string", "type": "string",
"title": "Branch Identical Icon", "title": "Branch Identical Icon",