summaryrefslogtreecommitdiffstats
path: root/pkg/integration
diff options
context:
space:
mode:
Diffstat (limited to 'pkg/integration')
-rw-r--r--pkg/integration/clients/tui.go5
-rw-r--r--pkg/integration/components/test.go26
-rw-r--r--pkg/integration/components/view_driver.go24
-rw-r--r--pkg/integration/tests/test_list.go1
-rw-r--r--pkg/integration/tests/ui/accordion.go61
-rw-r--r--pkg/integration/types/types.go3
6 files changed, 119 insertions, 1 deletions
diff --git a/pkg/integration/clients/tui.go b/pkg/integration/clients/tui.go
index b931e8954..7d82a6630 100644
--- a/pkg/integration/clients/tui.go
+++ b/pkg/integration/clients/tui.go
@@ -28,7 +28,10 @@ func RunTUI() {
app := newApp(testDir)
app.loadTests()
- g, err := gocui.NewGui(gocui.OutputTrue, false, false, false, gui.RuneReplacements)
+ g, err := gocui.NewGui(gocui.NewGuiOpts{
+ OutputMode: gocui.OutputTrue,
+ RuneReplacements: gui.RuneReplacements,
+ })
if err != nil {
log.Panicln(err)
}
diff --git a/pkg/integration/components/test.go b/pkg/integration/components/test.go
index 464779e38..d17e3f7c5 100644
--- a/pkg/integration/components/test.go
+++ b/pkg/integration/components/test.go
@@ -19,6 +19,11 @@ import (
// to get the test's name via it's file's path.
const unitTestDescription = "test test"
+const (
+ defaultWidth = 100
+ defaultHeight = 100
+)
+
type IntegrationTest struct {
name string
description string
@@ -32,6 +37,8 @@ type IntegrationTest struct {
keys config.KeybindingConfig,
)
gitVersion GitVersionRestriction
+ width int
+ height int
}
var _ integrationTypes.IntegrationTest = &IntegrationTest{}
@@ -52,6 +59,11 @@ type NewIntegrationTestArgs struct {
Skip bool
// to run a test only on certain git versions
GitVersion GitVersionRestriction
+ // width and height when running in headless mode, for testing
+ // the UI in different sizes.
+ // If these are set, the test must be run in headless mode
+ Width int
+ Height int
}
type GitVersionRestriction struct {
@@ -120,6 +132,8 @@ func NewIntegrationTest(args NewIntegrationTestArgs) *IntegrationTest {
setupConfig: args.SetupConfig,
run: args.Run,
gitVersion: args.GitVersion,
+ width: args.Width,
+ height: args.Height,
}
}
@@ -172,6 +186,18 @@ func (self *IntegrationTest) Run(gui integrationTypes.GuiDriver) {
}
}
+func (self *IntegrationTest) HeadlessDimensions() (int, int) {
+ if self.width == 0 && self.height == 0 {
+ return defaultWidth, defaultHeight
+ }
+
+ return self.width, self.height
+}
+
+func (self *IntegrationTest) RequiresHeadless() bool {
+ return self.width != 0 && self.height != 0
+}
+
func testNameFromCurrentFilePath() string {
path := utils.FilePath(3)
return TestNameFromFilePath(path)
diff --git a/pkg/integration/components/view_driver.go b/pkg/integration/components/view_driver.go
index 2c4a23572..d1d1571c7 100644
--- a/pkg/integration/components/view_driver.go
+++ b/pkg/integration/components/view_driver.go
@@ -82,6 +82,20 @@ func (self *ViewDriver) TopLines(matchers ...*TextMatcher) *ViewDriver {
return self.assertLines(0, matchers...)
}
+// Asserts on the visible lines of the view.
+// Note, this assumes that the view's viewport is filled with lines
+func (self *ViewDriver) VisibleLines(matchers ...*TextMatcher) *ViewDriver {
+ self.validateMatchersPassed(matchers)
+ self.validateVisibleLineCount(matchers)
+
+ // Get the origin of the view and offset that.
+ // Note that we don't do any retrying here so if we want to bring back retry logic
+ // we'll need to update this.
+ originY := self.getView().OriginY()
+
+ return self.assertLines(originY, matchers...)
+}
+
// asserts that somewhere in the view there are consequetive lines matching the given matchers.
func (self *ViewDriver) ContainsLines(matchers ...*TextMatcher) *ViewDriver {
self.validateMatchersPassed(matchers)
@@ -212,6 +226,16 @@ func (self *ViewDriver) validateEnoughLines(matchers []*TextMatcher) {
})
}
+// assumes the view's viewport is filled with lines
+func (self *ViewDriver) validateVisibleLineCount(matchers []*TextMatcher) {
+ view := self.getView()
+
+ self.t.assertWithRetries(func() (bool, string) {
+ count := view.InnerHeight() + 1
+ return count == len(matchers), fmt.Sprintf("unexpected number of visible lines in view '%s'. Expected exactly %d, got %d", view.Name(), len(matchers), count)
+ })
+}
+
func (self *ViewDriver) assertLines(offset int, matchers ...*TextMatcher) *ViewDriver {
view := self.getView()
diff --git a/pkg/integration/tests/test_list.go b/pkg/integration/tests/test_list.go
index af0ac1c5b..caaf2039e 100644
--- a/pkg/integration/tests/test_list.go
+++ b/pkg/integration/tests/test_list.go
@@ -209,6 +209,7 @@ var tests = []*components.IntegrationTest{
tag.CrudAnnotated,
tag.CrudLightweight,
tag.Reset,
+ ui.Accordion,
ui.DoublePopup,
ui.SwitchTabFromMenu,
undo.UndoCheckoutAndDrop,
diff --git a/pkg/integration/tests/ui/accordion.go b/pkg/integration/tests/ui/accordion.go
new file mode 100644
index 000000000..abfe27dbb
--- /dev/null
+++ b/pkg/integration/tests/ui/accordion.go
@@ -0,0 +1,61 @@
+package ui
+
+import (
+ "github.com/jesseduffield/lazygit/pkg/config"
+ . "github.com/jesseduffield/lazygit/pkg/integration/components"
+)
+
+// When in acccordion mode, Lazygit looks like this:
+//
+// ╶─Status─────────────────────────╴┌─Patch──────────────────────────────────────────────────────────┐
+// ╶─Files - Submodules──────0 of 0─╴│commit 6e56dd04b70e548976f7f2928c4d9c359574e2bc ▲
+// ╶─Local branches - Remotes1 of 1─╴│Author: CI <CI@example.com> █
+// ┌─Commits - Reflog───────────────┐│Date: Wed Jul 19 22:00:03 2023 +1000 │
+// │7fe02805 CI commit 12 ▲│ ▼
+// │6e56dd04 CI commit 11 █└────────────────────────────────────────────────────────────────┘
+// │a35c687d CI commit 10 ▼┌─Command log────────────────────────────────────────────────────┐
+// └───────────────────────10 of 20─┘│Random tip: To filter commits by path, press '<c-s>' │
+// ╶─Stash───────────────────0 of 0─╴└────────────────────────────────────────────────────────────────┘
+// <pgup>/<pgdown>: Scroll, <esc>: Cancel, q: Quit, ?: Keybindings, 1-Donate Ask Question unversioned
+
+var Accordion = NewIntegrationTest(NewIntegrationTestArgs{
+ Description: "Verify accordion mode kicks in when the screen height is too small",
+ ExtraCmdArgs: []string{},
+ Width: 100,
+ Height: 10,
+ Skip: false,
+ SetupConfig: func(config *config.AppConfig) {},
+ SetupRepo: func(shell *Shell) {
+ shell.CreateNCommits(20)
+ },
+ Run: func(t *TestDriver, keys config.KeybindingConfig) {
+ t.Views().Commits().
+ Focus().
+ VisibleLines(
+ Contains("commit 20").IsSelected(),
+ Contains("commit 19"),
+ Contains("commit 18"),
+ ).
+ // go past commit 11, then come back, so that it ends up in the centre of the viewport
+ NavigateToLine(Contains("commit 11")).
+ NavigateToLine(Contains("commit 10")).
+ NavigateToLine(Contains("commit 11")).
+ VisibleLines(
+ Contains("commit 12"),
+ Contains("commit 11").IsSelected(),
+ Contains("commit 10"),
+ )
+
+ t.Views().Files().
+ Focus()
+
+ // ensure we retain the same viewport upon re-focus
+ t.Views().Commits().
+ Focus().
+ VisibleLines(
+ Contains("commit 12"),
+ Contains("commit 11").IsSelected(),
+ Contains("commit 10"),
+ )
+ },
+})
diff --git a/pkg/integration/types/types.go b/pkg/integration/types/types.go
index a26ac67af..266304bbf 100644
--- a/pkg/integration/types/types.go
+++ b/pkg/integration/types/types.go
@@ -13,6 +13,9 @@ import (
type IntegrationTest interface {
Run(GuiDriver)
SetupConfig(config *config.AppConfig)
+ RequiresHeadless() bool
+ // width and height when running headless
+ HeadlessDimensions() (int, int)
}
// this is the interface through which our integration tests interact with the lazygit gui