]> Sergey Matveev's repositories - vim-lsp.git/blob - test/common.vim
Add the ":LspDiag" command and add sub-commands for the various Lsp
[vim-lsp.git] / test / common.vim
1 vim9script
2 # Common routines used for running the unit tests
3
4 # Load the LSP plugin.  Also enable syntax, file type detection.
5 def g:LoadLspPlugin()
6   syntax on
7   filetype on
8   filetype plugin on
9   filetype indent on
10
11   # Set the $LSP_PROFILE environment variable to profile the LSP plugin
12   var do_profile: bool = false
13   if exists('$LSP_PROFILE')
14       do_profile = true
15   endif
16
17   if do_profile
18       # profile the LSP plugin
19       profile start lsp_profile.txt
20       profile! file */lsp/*
21   endif
22
23   g:LSPTest = true
24   source ../plugin/lsp.vim
25 enddef
26
27 # The WaitFor*() functions are reused from the Vim test suite.
28 #
29 # Wait for up to five seconds for "assert" to return zero.  "assert" must be a
30 # (lambda) function containing one assert function.  Example:
31 #       call WaitForAssert({-> assert_equal("dead", job_status(job)})
32 #
33 # A second argument can be used to specify a different timeout in msec.
34 #
35 # Return zero for success, one for failure (like the assert function).
36 func g:WaitForAssert(assert, ...)
37   let timeout = get(a:000, 0, 5000)
38   if g:WaitForCommon(v:null, a:assert, timeout) < 0
39     return 1
40   endif
41   return 0
42 endfunc
43
44 # Either "expr" or "assert" is not v:null
45 # Return the waiting time for success, -1 for failure.
46 func g:WaitForCommon(expr, assert, timeout)
47   " using reltime() is more accurate, but not always available
48   let slept = 0
49   if exists('*reltimefloat')
50     let start = reltime()
51   endif
52
53   while 1
54     if type(a:expr) == v:t_func
55       let success = a:expr()
56     elseif type(a:assert) == v:t_func
57       let success = a:assert() == 0
58     else
59       let success = eval(a:expr)
60     endif
61     if success
62       return slept
63     endif
64
65     if slept >= a:timeout
66       break
67     endif
68     if type(a:assert) == v:t_func
69       " Remove the error added by the assert function.
70       call remove(v:errors, -1)
71     endif
72
73     sleep 10m
74     if exists('*reltimefloat')
75       let slept = float2nr(reltimefloat(reltime(start)) * 1000)
76     else
77       let slept += 10
78     endif
79   endwhile
80
81   return -1  " timed out
82 endfunc
83
84 # Wait for up to five seconds for "expr" to become true.  "expr" can be a
85 # stringified expression to evaluate, or a funcref without arguments.
86 # Using a lambda works best.  Example:
87 #       call WaitFor({-> status == "ok"})
88 #
89 # A second argument can be used to specify a different timeout in msec.
90 #
91 # When successful the time slept is returned.
92 # When running into the timeout an exception is thrown, thus the function does
93 # not return.
94 func g:WaitFor(expr, ...)
95   let timeout = get(a:000, 0, 5000)
96   let slept = g:WaitForCommon(a:expr, v:null, timeout)
97   if slept < 0
98     throw 'WaitFor() timed out after ' .. timeout .. ' msec'
99   endif
100   return slept
101 endfunc
102
103 # Wait for diagnostic messages from the LSP server.
104 # Waits for a maximum of (150 * 200) / 1000 = 30 seconds
105 def g:WaitForDiags(errCount: number)
106   var retries = 0
107   while retries < 200
108     var d = lsp#lsp#ErrorCount()
109     if d.Error == errCount
110       break
111     endif
112     retries += 1
113     :sleep 150m
114   endwhile
115
116   assert_equal(errCount, lsp#lsp#ErrorCount().Error)
117   if lsp#lsp#ErrorCount().Error != errCount
118     :LspDiag show
119     assert_report(getloclist(0)->string())
120     :lclose
121   endif
122 enddef
123
124 # Wait for the LSP server to load and process a file.  This works by waiting
125 # for a certain number of diagnostic messages from the server.
126 def g:WaitForServerFileLoad(diagCount: number)
127   :redraw!
128   var waitCount = diagCount
129   if waitCount == 0
130     # Introduce a temporary diagnostic
131     append('$', '-')
132     redraw!
133     waitCount = 1
134   endif
135   g:WaitForDiags(waitCount)
136   if waitCount != diagCount
137     # Remove the temporary line
138     deletebufline('%', '$')
139     redraw!
140     g:WaitForDiags(0)
141   endif
142 enddef
143
144 # Start the language server.  Returns true on success and false on failure.
145 # 'fname' is the name of a dummy file to start the server.
146 def g:StartLangServerWithFile(fname: string): bool
147   # Edit a dummy file to start the LSP server
148   exe ':silent! edit ' .. fname
149   # Wait for the LSP server to become ready (max 10 seconds)
150   var maxcount = 100
151   while maxcount > 0 && !g:LspServerReady()
152     :sleep 100m
153     maxcount -= 1
154   endwhile
155   var serverStatus: bool = g:LspServerReady()
156   :bw!
157
158   if !serverStatus
159     writefile(['FAIL: Not able to start the language server'], 'results.txt')
160     qall!
161   endif
162
163   return serverStatus
164 enddef
165
166 # vim: shiftwidth=2 softtabstop=2 noexpandtab