blob: 744f2ab60fe7748cdd3ccd73a41a82b60a8743d7 [file] [log] [blame]
Bram Moolenaarda650582018-02-20 15:51:40 +01001" Functions shared by tests making screen dumps.
2
3" Only load this script once.
Bram Moolenaar7a39dd72019-06-23 00:50:15 +02004if exists('*VerifyScreenDump')
Bram Moolenaarda650582018-02-20 15:51:40 +01005 finish
6endif
7
Bram Moolenaar7a39dd72019-06-23 00:50:15 +02008source shared.vim
9source term_util.vim
Bram Moolenaarf2732452018-06-03 14:47:35 +020010
11" Skip the rest if there is no terminal feature at all.
12if !has('terminal')
Bram Moolenaar6bb2cdf2018-02-24 19:53:53 +010013 finish
14endif
15
Bram Moolenaar11901392022-09-26 19:50:44 +010016" Read a dump file "fname" and if "filter" exists apply it to the text.
17def ReadAndFilter(fname: string, filter: string): list<string>
18 var contents = readfile(fname)
19
20 if filereadable(filter)
21 # do this in the bottom window so that the terminal window is unaffected
22 wincmd j
23 enew
24 setline(1, contents)
25 exe "source " .. filter
26 contents = getline(1, '$')
27 enew!
28 wincmd k
29 redraw
30 endif
31
32 return contents
33enddef
34
35
Bram Moolenaarda650582018-02-20 15:51:40 +010036" Verify that Vim running in terminal buffer "buf" matches the screen dump.
Bram Moolenaar6bb2cdf2018-02-24 19:53:53 +010037" "options" is passed to term_dumpwrite().
Bram Moolenaar3e794272022-05-06 11:21:19 +010038" Additionally, the "wait" entry can specify the maximum time to wait for the
39" screen dump to match in msec (default 1000 msec).
Bram Moolenaarda650582018-02-20 15:51:40 +010040" The file name used is "dumps/{filename}.dump".
Bram Moolenaar11901392022-09-26 19:50:44 +010041"
42" To ignore part of the dump, provide a "dumps/{filename}.vim" file with
43" Vim commands to be applied to both the reference and the current dump, so
44" that parts that are irrelevant are not used for the comparison. The result
45" is NOT written, thus "term_dumpdiff()" shows the difference anyway.
46"
Bram Moolenaar6f8bdab2018-09-09 22:02:24 +020047" Optionally an extra argument can be passed which is prepended to the error
48" message. Use this when using the same dump file with different options.
Bram Moolenaar6f8bdab2018-09-09 22:02:24 +020049" Returns non-zero when verification fails.
50func VerifyScreenDump(buf, filename, options, ...)
Bram Moolenaarda650582018-02-20 15:51:40 +010051 let reference = 'dumps/' . a:filename . '.dump'
Bram Moolenaar11901392022-09-26 19:50:44 +010052 let filter = 'dumps/' . a:filename . '.vim'
Bram Moolenaaref7f0e32019-03-30 15:59:51 +010053 let testfile = 'failed/' . a:filename . '.dump'
54
Yee Cheng Chine70587d2025-02-13 20:55:45 +010055 let max_loops = get(a:options, 'wait', 1000) / 1
Bram Moolenaar3e794272022-05-06 11:21:19 +010056
Bram Moolenaar3cdcb092020-03-18 19:18:10 +010057 " Starting a terminal to make a screendump is always considered flaky.
Bram Moolenaar30d53e22020-03-18 21:10:44 +010058 let g:test_is_flaky = 1
Millybaab7c02024-10-28 21:56:14 +010059 let g:giveup_same_error = 0
Bram Moolenaar3cdcb092020-03-18 19:18:10 +010060
Yegappan Lakshmanan560dff42022-02-10 19:52:10 +000061 " wait for the pending updates to be handled.
Yee Cheng Chine70587d2025-02-13 20:55:45 +010062 call TermWait(a:buf, 0)
Yegappan Lakshmanan560dff42022-02-10 19:52:10 +000063
Bram Moolenaar1bc353b2019-09-01 14:45:28 +020064 " Redraw to execute the code that updates the screen. Otherwise we get the
Bram Moolenaar87dcfd72019-04-13 22:35:29 +020065 " text and attributes only from the internal buffer.
66 redraw
67
Bram Moolenaar11901392022-09-26 19:50:44 +010068 if filereadable(reference)
69 let refdump = ReadAndFilter(reference, filter)
70 else
71 " Must be a new screendump, always fail
72 let refdump = []
73 endif
74
Bram Moolenaaref7f0e32019-03-30 15:59:51 +010075 let did_mkdir = 0
76 if !isdirectory('failed')
77 let did_mkdir = 1
78 call mkdir('failed')
79 endif
Bram Moolenaarda650582018-02-20 15:51:40 +010080
81 let i = 0
82 while 1
Yee Cheng Chine70587d2025-02-13 20:55:45 +010083 " leave a bit of time for updating the original window while we spin wait.
84 sleep 1m
Bram Moolenaarda650582018-02-20 15:51:40 +010085 call delete(testfile)
Bram Moolenaar6bb2cdf2018-02-24 19:53:53 +010086 call term_dumpwrite(a:buf, testfile, a:options)
Millybaab7c02024-10-28 21:56:14 +010087
88 if refdump->empty()
89 let msg = 'See new dump file: call term_dumpload("testdir/' .. testfile .. '")'
90 call assert_report(msg)
91 " no point in retrying
92 let g:run_nr = 10
93 return 1
94 endif
95
Bram Moolenaar11901392022-09-26 19:50:44 +010096 let testdump = ReadAndFilter(testfile, filter)
Bram Moolenaar353aca12019-02-21 17:05:59 +010097 if refdump == testdump
Bram Moolenaarda650582018-02-20 15:51:40 +010098 call delete(testfile)
Bram Moolenaaref7f0e32019-03-30 15:59:51 +010099 if did_mkdir
100 call delete('failed', 'd')
101 endif
Millybaab7c02024-10-28 21:56:14 +0100102 if i > 0
103 call remove(v:errors, -1)
104 endif
Bram Moolenaarda650582018-02-20 15:51:40 +0100105 break
106 endif
Millybaab7c02024-10-28 21:56:14 +0100107
108 " Leave the failed dump around for inspection.
109 let msg = 'See dump file difference: call term_dumpdiff("testdir/' .. testfile .. '", "testdir/' .. reference .. '")'
110 if a:0 == 1
111 let msg = a:1 . ': ' . msg
112 endif
113 if len(testdump) != len(refdump)
114 let msg = msg . '; line count is ' . len(testdump) . ' instead of ' . len(refdump)
115 endif
116 for j in range(len(refdump))
117 if j >= len(testdump)
118 break
Bram Moolenaar353aca12019-02-21 17:05:59 +0100119 endif
Millybaab7c02024-10-28 21:56:14 +0100120 if testdump[j] != refdump[j]
121 let msg = msg . '; difference in line ' . (j + 1) . ': "' . testdump[j] . '"'
122 endif
123 endfor
124
125 " Always add the last error so that it is displayed on timeout.
126 " See TestTimeout() in runtest.vim.
127 if i > 0
128 call remove(v:errors, -1)
129 endif
130 call assert_report(msg)
131
132 let i += 1
133 if i >= max_loops
Bram Moolenaar6f8bdab2018-09-09 22:02:24 +0200134 return 1
Bram Moolenaarda650582018-02-20 15:51:40 +0100135 endif
Bram Moolenaarda650582018-02-20 15:51:40 +0100136 endwhile
Bram Moolenaar6f8bdab2018-09-09 22:02:24 +0200137 return 0
Bram Moolenaarda650582018-02-20 15:51:40 +0100138endfunc