1
0
mirror of https://github.com/jesseduffield/lazygit.git synced 2025-06-15 00:15:32 +02:00

always specify upstream when pushing/pulling

This commit is contained in:
Jesse Duffield
2022-01-15 14:20:09 +11:00
parent 8d8bdb948b
commit 1c84f77319
60 changed files with 209 additions and 96 deletions

View File

@ -136,7 +136,7 @@ func NewGitCommandAux(
Tag: tagCommands, Tag: tagCommands,
WorkingTree: workingTreeCommands, WorkingTree: workingTreeCommands,
Loaders: Loaders{ Loaders: Loaders{
Branches: loaders.NewBranchLoader(cmn, branchCommands.GetRawBranches, branchCommands.CurrentBranchName), Branches: loaders.NewBranchLoader(cmn, branchCommands.GetRawBranches, branchCommands.CurrentBranchName, configCommands),
CommitFiles: loaders.NewCommitFileLoader(cmn, cmd), CommitFiles: loaders.NewCommitFileLoader(cmn, cmd),
Commits: loaders.NewCommitLoader(cmn, cmd, dotGitDir, branchCommands.CurrentBranchName, statusCommands.RebaseMode), Commits: loaders.NewCommitLoader(cmn, cmd, dotGitDir, branchCommands.CurrentBranchName, statusCommands.RebaseMode),
Files: fileLoader, Files: fileLoader,

View File

@ -108,13 +108,8 @@ func (self *BranchCommands) GetGraphCmdObj(branchName string) oscommands.ICmdObj
return self.cmd.New(utils.ResolvePlaceholderString(branchLogCmdTemplate, templateValues)).DontLog() return self.cmd.New(utils.ResolvePlaceholderString(branchLogCmdTemplate, templateValues)).DontLog()
} }
func (self *BranchCommands) SetCurrentBranchUpstream(upstream string) error { func (self *BranchCommands) SetCurrentBranchUpstream(remoteName string, remoteBranchName string) error {
return self.cmd.New("git branch --set-upstream-to=" + self.cmd.Quote(upstream)).Run() return self.cmd.New(fmt.Sprintf("git branch --set-upstream-to=%s/%s", self.cmd.Quote(remoteName), self.cmd.Quote(remoteBranchName))).Run()
}
func (self *BranchCommands) GetUpstream(branchName string) (string, error) {
output, err := self.cmd.New(fmt.Sprintf("git rev-parse --abbrev-ref --symbolic-full-name %s@{u}", self.cmd.Quote(branchName))).DontLog().RunWithOutput()
return strings.TrimSpace(output), err
} }
func (self *BranchCommands) SetUpstream(remoteName string, remoteBranchName string, branchName string) error { func (self *BranchCommands) SetUpstream(remoteName string, remoteBranchName string, branchName string) error {

View File

@ -4,6 +4,7 @@ import (
"regexp" "regexp"
"strings" "strings"
"github.com/jesseduffield/go-git/v5/config"
"github.com/jesseduffield/lazygit/pkg/commands/models" "github.com/jesseduffield/lazygit/pkg/commands/models"
"github.com/jesseduffield/lazygit/pkg/common" "github.com/jesseduffield/lazygit/pkg/common"
"github.com/jesseduffield/lazygit/pkg/utils" "github.com/jesseduffield/lazygit/pkg/utils"
@ -20,27 +21,34 @@ import (
// if we find out we need to use one of these functions in the git.go file, we // if we find out we need to use one of these functions in the git.go file, we
// can just pull them out of here and put them there and then call them from in here // can just pull them out of here and put them there and then call them from in here
type BranchLoaderConfigCommands interface {
Branches() (map[string]*config.Branch, error)
}
// BranchLoader returns a list of Branch objects for the current repo // BranchLoader returns a list of Branch objects for the current repo
type BranchLoader struct { type BranchLoader struct {
*common.Common *common.Common
getRawBranches func() (string, error) getRawBranches func() (string, error)
getCurrentBranchName func() (string, string, error) getCurrentBranchName func() (string, string, error)
config BranchLoaderConfigCommands
} }
func NewBranchLoader( func NewBranchLoader(
cmn *common.Common, cmn *common.Common,
getRawBranches func() (string, error), getRawBranches func() (string, error),
getCurrentBranchName func() (string, string, error), getCurrentBranchName func() (string, string, error),
config BranchLoaderConfigCommands,
) *BranchLoader { ) *BranchLoader {
return &BranchLoader{ return &BranchLoader{
Common: cmn, Common: cmn,
getRawBranches: getRawBranches, getRawBranches: getRawBranches,
getCurrentBranchName: getCurrentBranchName, getCurrentBranchName: getCurrentBranchName,
config: config,
} }
} }
// Load the list of branches for the current repo // Load the list of branches for the current repo
func (self *BranchLoader) Load(reflogCommits []*models.Commit) []*models.Branch { func (self *BranchLoader) Load(reflogCommits []*models.Commit) ([]*models.Branch, error) {
branches := self.obtainBranches() branches := self.obtainBranches()
reflogBranches := self.obtainReflogBranches(reflogCommits) reflogBranches := self.obtainReflogBranches(reflogCommits)
@ -77,11 +85,25 @@ outer:
if !foundHead { if !foundHead {
currentBranchName, currentBranchDisplayName, err := self.getCurrentBranchName() currentBranchName, currentBranchDisplayName, err := self.getCurrentBranchName()
if err != nil { if err != nil {
panic(err) return nil, err
} }
branches = append([]*models.Branch{{Name: currentBranchName, DisplayName: currentBranchDisplayName, Head: true, Recency: " *"}}, branches...) branches = append([]*models.Branch{{Name: currentBranchName, DisplayName: currentBranchDisplayName, Head: true, Recency: " *"}}, branches...)
} }
return branches
configBranches, err := self.config.Branches()
if err != nil {
return nil, err
}
for _, branch := range branches {
match := configBranches[branch.Name]
if match != nil {
branch.UpstreamRemote = match.Remote
branch.UpstreamBranch = match.Merge.Short()
}
}
return branches, nil
} }
func (self *BranchLoader) obtainBranches() []*models.Branch { func (self *BranchLoader) obtainBranches() []*models.Branch {
@ -116,12 +138,13 @@ func (self *BranchLoader) obtainBranches() []*models.Branch {
upstreamName := split[2] upstreamName := split[2]
if upstreamName == "" { if upstreamName == "" {
// if we're here then it means we do not have a local version of the remote.
// The branch might still be tracking a remote though, we just don't know
// how many commits ahead/behind it is
branches = append(branches, branch) branches = append(branches, branch)
continue continue
} }
branch.UpstreamName = upstreamName
track := split[3] track := split[3]
re := regexp.MustCompile(`ahead (\d+)`) re := regexp.MustCompile(`ahead (\d+)`)
match := re.FindStringSubmatch(track) match := re.FindStringSubmatch(track)

View File

@ -9,8 +9,12 @@ type Branch struct {
Recency string Recency string
Pushables string Pushables string
Pullables string Pullables string
UpstreamName string
Head bool Head bool
// if we have a named remote locally this will be the name of that remote e.g.
// 'origin' or 'tiwood'. If we don't have the remote locally it'll look like
// 'git@github.com:tiwood/lazygit.git'
UpstreamRemote string
UpstreamBranch string
} }
func (b *Branch) RefName() string { func (b *Branch) RefName() string {
@ -25,22 +29,26 @@ func (b *Branch) Description() string {
return b.RefName() return b.RefName()
} }
// this method does not consider the case where the git config states that a branch is tracking the config.
// The Pullables value here is based on whether or not we saw an upstream when doing `git branch`
func (b *Branch) IsTrackingRemote() bool { func (b *Branch) IsTrackingRemote() bool {
return b.IsRealBranch() && b.Pullables != "?" return b.UpstreamRemote != ""
}
// we know that the remote branch is not stored locally based on our pushable/pullable
// count being question marks.
func (b *Branch) RemoteBranchStoredLocally() bool {
return b.IsTrackingRemote() && b.Pushables != "?" && b.Pullables != "?"
} }
func (b *Branch) MatchesUpstream() bool { func (b *Branch) MatchesUpstream() bool {
return b.IsRealBranch() && b.Pushables == "0" && b.Pullables == "0" return b.RemoteBranchStoredLocally() && b.Pushables == "0" && b.Pullables == "0"
} }
func (b *Branch) HasCommitsToPush() bool { func (b *Branch) HasCommitsToPush() bool {
return b.IsRealBranch() && b.Pushables != "0" return b.RemoteBranchStoredLocally() && b.Pushables != "0"
} }
func (b *Branch) HasCommitsToPull() bool { func (b *Branch) HasCommitsToPull() bool {
return b.IsRealBranch() && b.Pullables != "0" return b.RemoteBranchStoredLocally() && b.Pullables != "0"
} }
// for when we're in a detached head state // for when we're in a detached head state

View File

@ -60,7 +60,12 @@ func (gui *Gui) refreshBranches() {
} }
} }
gui.State.Branches = gui.Git.Loaders.Branches.Load(reflogCommits) branches, err := gui.Git.Loaders.Branches.Load(reflogCommits)
if err != nil {
_ = gui.surfaceError(err)
}
gui.State.Branches = branches
if err := gui.postRefreshUpdate(gui.State.Contexts.Branches); err != nil { if err := gui.postRefreshUpdate(gui.State.Contexts.Branches); err != nil {
gui.Log.Error(err) gui.Log.Error(err)
@ -392,25 +397,19 @@ func (gui *Gui) handleFastForward() error {
if !branch.IsTrackingRemote() { if !branch.IsTrackingRemote() {
return gui.createErrorPanel(gui.Tr.FwdNoUpstream) return gui.createErrorPanel(gui.Tr.FwdNoUpstream)
} }
if !branch.RemoteBranchStoredLocally() {
return gui.createErrorPanel(gui.Tr.FwdNoLocalUpstream)
}
if branch.HasCommitsToPush() { if branch.HasCommitsToPush() {
return gui.createErrorPanel(gui.Tr.FwdCommitsToPush) return gui.createErrorPanel(gui.Tr.FwdCommitsToPush)
} }
upstream, err := gui.Git.Branch.GetUpstream(branch.Name)
if err != nil {
return gui.surfaceError(err)
}
action := gui.Tr.Actions.FastForwardBranch action := gui.Tr.Actions.FastForwardBranch
split := strings.Split(upstream, "/")
remoteName := split[0]
remoteBranchName := strings.Join(split[1:], "/")
message := utils.ResolvePlaceholderString( message := utils.ResolvePlaceholderString(
gui.Tr.Fetching, gui.Tr.Fetching,
map[string]string{ map[string]string{
"from": fmt.Sprintf("%s/%s", remoteName, remoteBranchName), "from": fmt.Sprintf("%s/%s", branch.UpstreamRemote, branch.UpstreamBranch),
"to": branch.Name, "to": branch.Name,
}, },
) )
@ -421,7 +420,7 @@ func (gui *Gui) handleFastForward() error {
_ = gui.pullWithLock(PullFilesOptions{action: action, FastForwardOnly: true}) _ = gui.pullWithLock(PullFilesOptions{action: action, FastForwardOnly: true})
} else { } else {
gui.logAction(action) gui.logAction(action)
err := gui.Git.Sync.FastForward(branch.Name, remoteName, remoteBranchName) err := gui.Git.Sync.FastForward(branch.Name, branch.UpstreamRemote, branch.UpstreamBranch)
gui.handleCredentialsPopup(err) gui.handleCredentialsPopup(err)
_ = gui.refreshSidePanels(refreshOptions{mode: ASYNC, scope: []RefreshableView{BRANCHES}}) _ = gui.refreshSidePanels(refreshOptions{mode: ASYNC, scope: []RefreshableView{BRANCHES}})
} }

View File

@ -36,8 +36,8 @@ type askOpts struct {
type promptOpts struct { type promptOpts struct {
title string title string
initialContent string initialContent string
handleConfirm func(string) error
findSuggestionsFunc func(string) []*types.Suggestion findSuggestionsFunc func(string) []*types.Suggestion
handleConfirm func(string) error
} }
func (gui *Gui) ask(opts askOpts) error { func (gui *Gui) ask(opts askOpts) error {

View File

@ -44,8 +44,8 @@ func (gui *Gui) currentDiffTerminals() []string {
branch := gui.getSelectedBranch() branch := gui.getSelectedBranch()
if branch != nil { if branch != nil {
names := []string{branch.ID()} names := []string{branch.ID()}
if branch.UpstreamName != "" { if branch.IsTrackingRemote() {
names = append(names, branch.UpstreamName) names = append(names, branch.ID()+"@{u}")
} }
return names return names
} }

View File

@ -655,42 +655,40 @@ func (gui *Gui) handlePullFiles() error {
// if we have no upstream branch we need to set that first // if we have no upstream branch we need to set that first
if !currentBranch.IsTrackingRemote() { if !currentBranch.IsTrackingRemote() {
// see if we have this branch in our config with an upstream
branches, err := gui.Git.Config.Branches()
if err != nil {
return gui.surfaceError(err)
}
for branchName, branch := range branches {
if branchName == currentBranch.Name {
return gui.pullFiles(PullFilesOptions{RemoteName: branch.Remote, BranchName: branch.Name, action: action})
}
}
suggestedRemote := getSuggestedRemote(gui.State.Remotes) suggestedRemote := getSuggestedRemote(gui.State.Remotes)
return gui.prompt(promptOpts{ return gui.prompt(promptOpts{
title: gui.Tr.EnterUpstream, title: gui.Tr.EnterUpstream,
initialContent: suggestedRemote + "/" + currentBranch.Name, initialContent: suggestedRemote + " " + currentBranch.Name,
findSuggestionsFunc: gui.getRemoteBranchesSuggestionsFunc("/"), findSuggestionsFunc: gui.getRemoteBranchesSuggestionsFunc(" "),
handleConfirm: func(upstream string) error { handleConfirm: func(upstream string) error {
if err := gui.Git.Branch.SetCurrentBranchUpstream(upstream); err != nil { var upstreamBranch, upstreamRemote string
split := strings.Split(upstream, " ")
if len(split) != 2 {
return gui.createErrorPanel(gui.Tr.InvalidUpstream)
}
upstreamRemote = split[0]
upstreamBranch = split[1]
if err := gui.Git.Branch.SetCurrentBranchUpstream(upstreamRemote, upstreamBranch); err != nil {
errorMessage := err.Error() errorMessage := err.Error()
if strings.Contains(errorMessage, "does not exist") { if strings.Contains(errorMessage, "does not exist") {
errorMessage = fmt.Sprintf("upstream branch %s not found.\nIf you expect it to exist, you should fetch (with 'f').\nOtherwise, you should push (with 'shift+P')", upstream) errorMessage = fmt.Sprintf("upstream branch %s not found.\nIf you expect it to exist, you should fetch (with 'f').\nOtherwise, you should push (with 'shift+P')", upstream)
} }
return gui.createErrorPanel(errorMessage) return gui.createErrorPanel(errorMessage)
} }
return gui.pullFiles(PullFilesOptions{action: action}) return gui.pullFiles(PullFilesOptions{UpstreamRemote: upstreamRemote, UpstreamBranch: upstreamBranch, action: action})
}, },
}) })
} }
return gui.pullFiles(PullFilesOptions{action: action}) return gui.pullFiles(PullFilesOptions{UpstreamRemote: currentBranch.UpstreamRemote, UpstreamBranch: currentBranch.UpstreamBranch, action: action})
} }
type PullFilesOptions struct { type PullFilesOptions struct {
RemoteName string UpstreamRemote string
BranchName string UpstreamBranch string
FastForwardOnly bool FastForwardOnly bool
action string action string
} }
@ -714,8 +712,8 @@ func (gui *Gui) pullWithLock(opts PullFilesOptions) error {
err := gui.Git.Sync.Pull( err := gui.Git.Sync.Pull(
git_commands.PullOptions{ git_commands.PullOptions{
RemoteName: opts.RemoteName, RemoteName: opts.UpstreamRemote,
BranchName: opts.BranchName, BranchName: opts.UpstreamBranch,
FastForwardOnly: opts.FastForwardOnly, FastForwardOnly: opts.FastForwardOnly,
}, },
) )
@ -782,28 +780,18 @@ func (gui *Gui) pushFiles() error {
} }
if currentBranch.IsTrackingRemote() { if currentBranch.IsTrackingRemote() {
if currentBranch.HasCommitsToPull() { opts := pushOpts{
return gui.requestToForcePush()
} else {
return gui.push(pushOpts{})
}
} else {
// see if we have an upstream for this branch in our config
upstreamRemote, upstreamBranch, err := gui.upstreamForBranchInConfig(currentBranch.Name)
if err != nil {
return gui.surfaceError(err)
}
if upstreamBranch != "" {
return gui.push(
pushOpts{
force: false, force: false,
upstreamRemote: upstreamRemote, upstreamRemote: currentBranch.UpstreamRemote,
upstreamBranch: upstreamBranch, upstreamBranch: currentBranch.UpstreamBranch,
},
)
} }
if currentBranch.HasCommitsToPull() {
opts.force = true
return gui.requestToForcePush(opts)
} else {
return gui.push(opts)
}
} else {
suggestedRemote := getSuggestedRemote(gui.State.Remotes) suggestedRemote := getSuggestedRemote(gui.State.Remotes)
if gui.Git.Config.GetPushToCurrent() { if gui.Git.Config.GetPushToCurrent() {
@ -850,7 +838,7 @@ func getSuggestedRemote(remotes []*models.Remote) string {
return remotes[0].Name return remotes[0].Name
} }
func (gui *Gui) requestToForcePush() error { func (gui *Gui) requestToForcePush(opts pushOpts) error {
forcePushDisabled := gui.UserConfig.Git.DisableForcePushing forcePushDisabled := gui.UserConfig.Git.DisableForcePushing
if forcePushDisabled { if forcePushDisabled {
return gui.createErrorPanel(gui.Tr.ForcePushDisabled) return gui.createErrorPanel(gui.Tr.ForcePushDisabled)
@ -860,26 +848,11 @@ func (gui *Gui) requestToForcePush() error {
title: gui.Tr.ForcePush, title: gui.Tr.ForcePush,
prompt: gui.Tr.ForcePushPrompt, prompt: gui.Tr.ForcePushPrompt,
handleConfirm: func() error { handleConfirm: func() error {
return gui.push(pushOpts{force: true}) return gui.push(opts)
}, },
}) })
} }
func (gui *Gui) upstreamForBranchInConfig(branchName string) (string, string, error) {
branches, err := gui.Git.Config.Branches()
if err != nil {
return "", "", err
}
for configBranchName, configBranch := range branches {
if configBranchName == branchName {
return configBranch.Remote, configBranchName, nil
}
}
return "", "", nil
}
func (gui *Gui) switchToMerge() error { func (gui *Gui) switchToMerge() error {
file := gui.getSelectedFile() file := gui.getSelectedFile()
if file == nil { if file == nil {

View File

@ -43,7 +43,13 @@ func getBranchDisplayStrings(b *models.Branch, fullDescription bool, diffed bool
res := []string{recencyColor.Sprint(b.Recency), coloredName} res := []string{recencyColor.Sprint(b.Recency), coloredName}
if fullDescription { if fullDescription {
return append(res, style.FgYellow.Sprint(b.UpstreamName)) return append(
res,
fmt.Sprintf("%s %s",
style.FgYellow.Sprint(b.UpstreamRemote),
style.FgYellow.Sprint(b.UpstreamBranch),
),
)
} }
return res return res
} }

View File

@ -188,6 +188,7 @@ type TranslationSet struct {
ConfirmRebase string ConfirmRebase string
ConfirmMerge string ConfirmMerge string
FwdNoUpstream string FwdNoUpstream string
FwdNoLocalUpstream string
FwdCommitsToPush string FwdCommitsToPush string
ErrorOccurred string ErrorOccurred string
NoRoom string NoRoom string
@ -281,6 +282,7 @@ type TranslationSet struct {
LcEnterFile string LcEnterFile string
ExitLineByLineMode string ExitLineByLineMode string
EnterUpstream string EnterUpstream string
InvalidUpstream string
ReturnToRemotesList string ReturnToRemotesList string
LcAddNewRemote string LcAddNewRemote string
LcNewRemoteName string LcNewRemoteName string
@ -738,6 +740,7 @@ func EnglishTranslationSet() TranslationSet {
ConfirmRebase: "Are you sure you want to rebase '{{.checkedOutBranch}}' onto '{{.selectedBranch}}'?", ConfirmRebase: "Are you sure you want to rebase '{{.checkedOutBranch}}' onto '{{.selectedBranch}}'?",
ConfirmMerge: "Are you sure you want to merge '{{.selectedBranch}}' into '{{.checkedOutBranch}}'?", ConfirmMerge: "Are you sure you want to merge '{{.selectedBranch}}' into '{{.checkedOutBranch}}'?",
FwdNoUpstream: "Cannot fast-forward a branch with no upstream", FwdNoUpstream: "Cannot fast-forward a branch with no upstream",
FwdNoLocalUpstream: "Cannot fast-forward a branch whose remote is not registered locally",
FwdCommitsToPush: "Cannot fast-forward a branch with commits to push", FwdCommitsToPush: "Cannot fast-forward a branch with commits to push",
ErrorOccurred: "An error occurred! Please create an issue at", ErrorOccurred: "An error occurred! Please create an issue at",
NoRoom: "Not enough room", NoRoom: "Not enough room",
@ -831,6 +834,7 @@ func EnglishTranslationSet() TranslationSet {
LcEnterFile: "enter file to add selected lines to the patch (or toggle directory collapsed)", LcEnterFile: "enter file to add selected lines to the patch (or toggle directory collapsed)",
ExitLineByLineMode: `exit line-by-line mode`, ExitLineByLineMode: `exit line-by-line mode`,
EnterUpstream: `Enter upstream as '<remote> <branchname>'`, EnterUpstream: `Enter upstream as '<remote> <branchname>'`,
InvalidUpstream: "Invalid upstream. Must be in the format '<remote> <branchname>'",
ReturnToRemotesList: `Return to remotes list`, ReturnToRemotesList: `Return to remotes list`,
LcAddNewRemote: `add new remote`, LcAddNewRemote: `add new remote`,
LcNewRemoteName: `New remote name:`, LcNewRemoteName: `New remote name:`,

View File

@ -0,0 +1 @@
myfile4

View File

@ -0,0 +1 @@
766e681a51daa75233c1c4ae8845be2c893577d5 branch 'master' of ../actual_remote

View File

@ -0,0 +1 @@
ref: refs/heads/master

View File

@ -0,0 +1 @@
c9fd61f40de25556977e063683d1de612f931ccb

View File

@ -0,0 +1,16 @@
[core]
repositoryformatversion = 0
filemode = true
bare = false
logallrefupdates = true
ignorecase = true
precomposeunicode = true
[user]
email = CI@example.com
name = CI
[remote "origin"]
url = ../actual_remote
fetch = +refs/heads/*:refs/remotes/origin/*
[branch "master"]
remote = origin
merge = refs/heads/master

View File

@ -0,0 +1 @@
Unnamed repository; edit this file 'description' to name the repository.

View File

@ -0,0 +1,7 @@
# git ls-files --others --exclude-from=.git/info/exclude
# Lines that start with '#' are comments.
# For a project mostly in C, the following would be a good set of
# exclude patterns (uncomment them if you want to use them):
# *.[oa]
# *~
.DS_Store

View File

@ -0,0 +1,7 @@
0000000000000000000000000000000000000000 972fb9caab8b8536ae38687fec98304b76748b9d CI <CI@example.com> 1642217132 +1100 commit (initial): myfile1
972fb9caab8b8536ae38687fec98304b76748b9d c9fd61f40de25556977e063683d1de612f931ccb CI <CI@example.com> 1642217132 +1100 commit: myfile2
c9fd61f40de25556977e063683d1de612f931ccb 06d3929607b7519beb45ca67165a1f2b5c0e578b CI <CI@example.com> 1642217132 +1100 commit: myfile3
06d3929607b7519beb45ca67165a1f2b5c0e578b 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217132 +1100 commit: myfile4
766e681a51daa75233c1c4ae8845be2c893577d5 c9fd61f40de25556977e063683d1de612f931ccb CI <CI@example.com> 1642217132 +1100 reset: moving to HEAD~2
c9fd61f40de25556977e063683d1de612f931ccb 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217139 +1100 rebase -i (start): checkout 766e681a51daa75233c1c4ae8845be2c893577d5
766e681a51daa75233c1c4ae8845be2c893577d5 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217139 +1100 rebase -i (finish): returning to refs/heads/master

View File

@ -0,0 +1,6 @@
0000000000000000000000000000000000000000 972fb9caab8b8536ae38687fec98304b76748b9d CI <CI@example.com> 1642217132 +1100 commit (initial): myfile1
972fb9caab8b8536ae38687fec98304b76748b9d c9fd61f40de25556977e063683d1de612f931ccb CI <CI@example.com> 1642217132 +1100 commit: myfile2
c9fd61f40de25556977e063683d1de612f931ccb 06d3929607b7519beb45ca67165a1f2b5c0e578b CI <CI@example.com> 1642217132 +1100 commit: myfile3
06d3929607b7519beb45ca67165a1f2b5c0e578b 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217132 +1100 commit: myfile4
766e681a51daa75233c1c4ae8845be2c893577d5 c9fd61f40de25556977e063683d1de612f931ccb CI <CI@example.com> 1642217132 +1100 reset: moving to HEAD~2
c9fd61f40de25556977e063683d1de612f931ccb 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217139 +1100 rebase -i (finish): refs/heads/master onto 766e681a51daa75233c1c4ae8845be2c893577d5

View File

@ -0,0 +1 @@
0000000000000000000000000000000000000000 766e681a51daa75233c1c4ae8845be2c893577d5 CI <CI@example.com> 1642217132 +1100 fetch origin: storing head

View File

@ -0,0 +1 @@
766e681a51daa75233c1c4ae8845be2c893577d5

View File

@ -0,0 +1 @@
766e681a51daa75233c1c4ae8845be2c893577d5

View File

@ -0,0 +1 @@
test1

View File

@ -0,0 +1 @@
test2

View File

@ -0,0 +1 @@
test3

View File

@ -0,0 +1 @@
test4

View File

@ -0,0 +1 @@
ref: refs/heads/master

View File

@ -0,0 +1,8 @@
[core]
repositoryformatversion = 0
filemode = true
bare = true
ignorecase = true
precomposeunicode = true
[remote "origin"]
url = /Users/jesseduffieldduffield/go/src/github.com/jesseduffield/lazygit/test/integration/pullAndSetUpstream/./actual

View File

@ -0,0 +1 @@
Unnamed repository; edit this file 'description' to name the repository.

View File

@ -0,0 +1,7 @@
# git ls-files --others --exclude-from=.git/info/exclude
# Lines that start with '#' are comments.
# For a project mostly in C, the following would be a good set of
# exclude patterns (uncomment them if you want to use them):
# *.[oa]
# *~
.DS_Store

View File

@ -0,0 +1,2 @@
# pack-refs with: peeled fully-peeled sorted
766e681a51daa75233c1c4ae8845be2c893577d5 refs/heads/master

View File

@ -0,0 +1 @@
{"KeyEvents":[{"Timestamp":423,"Mod":0,"Key":256,"Ch":112},{"Timestamp":1032,"Mod":0,"Key":127,"Ch":127},{"Timestamp":1216,"Mod":0,"Key":127,"Ch":127},{"Timestamp":1376,"Mod":0,"Key":127,"Ch":127},{"Timestamp":1536,"Mod":0,"Key":127,"Ch":127},{"Timestamp":1687,"Mod":0,"Key":127,"Ch":127},{"Timestamp":1847,"Mod":0,"Key":127,"Ch":127},{"Timestamp":2016,"Mod":0,"Key":127,"Ch":127},{"Timestamp":2240,"Mod":0,"Key":13,"Ch":13},{"Timestamp":3044,"Mod":0,"Key":27,"Ch":0},{"Timestamp":3768,"Mod":0,"Key":256,"Ch":112},{"Timestamp":4184,"Mod":0,"Key":256,"Ch":97},{"Timestamp":4232,"Mod":0,"Key":256,"Ch":115},{"Timestamp":4288,"Mod":0,"Key":256,"Ch":100},{"Timestamp":4728,"Mod":0,"Key":13,"Ch":13},{"Timestamp":5488,"Mod":0,"Key":27,"Ch":0},{"Timestamp":5799,"Mod":0,"Key":256,"Ch":112},{"Timestamp":6273,"Mod":0,"Key":13,"Ch":13},{"Timestamp":7207,"Mod":0,"Key":256,"Ch":113}],"ResizeEvents":[{"Timestamp":0,"Width":272,"Height":74}]}

View File

@ -0,0 +1,33 @@
#!/bin/sh
set -e
cd $1
git init
git config user.email "CI@example.com"
git config user.name "CI"
echo test1 > myfile1
git add .
git commit -am "myfile1"
echo test2 > myfile2
git add .
git commit -am "myfile2"
echo test3 > myfile3
git add .
git commit -am "myfile3"
echo test4 > myfile4
git add .
git commit -am "myfile4"
cd ..
git clone --bare ./actual actual_remote
cd actual
# the test is to ensure that we actually can pull these two commits back from the origin
git reset --hard HEAD~2
git remote add origin ../actual_remote
git fetch origin

View File

@ -0,0 +1,4 @@
{
"description": "pull changes from the remote, setting upstream",
"speed": 10
}