mirror of
https://github.com/mfussenegger/nvim-jdtls
synced 2024-09-16 14:34:13 +02:00
Show Junit test failures as ERROR diagnostics (#665)
This commit is contained in:
parent
6e99fc8076
commit
be5c8d49e0
2 changed files with 120 additions and 16 deletions
|
@ -482,7 +482,7 @@ local function run(lens, config, context, opts)
|
|||
server:shutdown()
|
||||
server:close()
|
||||
end
|
||||
local items = test_results.show()
|
||||
local items = test_results.show(lens)
|
||||
maybe_repeat(lens, config, context, opts, items)
|
||||
if opts.after_test then
|
||||
opts.after_test(items)
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
local M = {}
|
||||
|
||||
local ns = vim.api.nvim_create_namespace('junit')
|
||||
|
||||
local MessageId = {
|
||||
TestStart = '%TESTS',
|
||||
|
@ -12,7 +12,6 @@ local MessageId = {
|
|||
ASSUMPTION_FAILED_TEST_PREFIX = '@AssumptionFailure: ',
|
||||
}
|
||||
|
||||
|
||||
local function parse_test_case(line)
|
||||
local matches = vim.fn.matchlist(line, '\\v\\d+,(\\@AssumptionFailure: |\\@Ignore: )?(.*)(\\[\\d+\\])?\\((.*)\\)')
|
||||
if #matches == 0 then
|
||||
|
@ -64,7 +63,6 @@ end
|
|||
|
||||
M.__parse = parse
|
||||
|
||||
|
||||
local function mk_buf_loop(sock, handle_buffer)
|
||||
local buffer = ''
|
||||
return function(err, chunk)
|
||||
|
@ -78,43 +76,150 @@ local function mk_buf_loop(sock, handle_buffer)
|
|||
end
|
||||
end
|
||||
|
||||
|
||||
function M.mk_test_results(bufnr)
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, ns, 0, -1)
|
||||
vim.diagnostic.reset(ns, bufnr)
|
||||
local tests = {}
|
||||
|
||||
local handle_buffer = function(buf)
|
||||
parse(buf, tests)
|
||||
end
|
||||
|
||||
local function get_test_start_line_num(lenses, test)
|
||||
if test.method ~= nil then
|
||||
if #lenses > 0 then
|
||||
for _, v in ipairs(lenses) do
|
||||
if vim.startswith(v.label, test.method) then
|
||||
return v.range.start.line
|
||||
end
|
||||
end
|
||||
else
|
||||
if vim.startswith(lenses.label, test.method) then
|
||||
return lenses.range.start.line
|
||||
end
|
||||
end
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
return {
|
||||
show = function()
|
||||
show = function(lens)
|
||||
local items = {}
|
||||
local repl = require('dap.repl')
|
||||
local num_failures = 0
|
||||
local lenses = lens.children or lens
|
||||
local failures = {}
|
||||
local results = {}
|
||||
local error_symbol = '❌'
|
||||
local success_symbol = '✔️ '
|
||||
for _, test in ipairs(tests) do
|
||||
local start_line_num = get_test_start_line_num(lenses, test)
|
||||
if test.failed then
|
||||
num_failures = num_failures + 1
|
||||
if test.method then
|
||||
repl.append('❌' .. test.method, '$')
|
||||
if start_line_num ~= nil then
|
||||
table.insert(results, {
|
||||
lnum = start_line_num,
|
||||
success = false
|
||||
})
|
||||
end
|
||||
|
||||
if test.method then
|
||||
repl.append(error_symbol .. ' ' .. test.method, '$')
|
||||
end
|
||||
local testMatch
|
||||
for _, msg in ipairs(test.traces) do
|
||||
local match = msg:match(string.format('at %s.%s', test.fq_class, test.method) .. '%(([%a%p]*:%d+)%)')
|
||||
local match = msg:match(string.format('at %s.%s', test.fq_class, test.method) .. '%(([%w%p]*:%d+)%)')
|
||||
if match then
|
||||
testMatch = true
|
||||
local lnum = vim.split(match, ':')[2]
|
||||
local trace = table.concat(test.traces, '\n')
|
||||
local cause = trace:sub(1, trace:find(msg, 1, true) - 1)
|
||||
if #trace > 140 then
|
||||
trace = trace:sub(1, 140) .. '...'
|
||||
end
|
||||
table.insert(items, {
|
||||
bufnr = bufnr,
|
||||
lnum = lnum,
|
||||
text = test.method .. ' ' .. trace
|
||||
text = test.method .. ' ' .. trace,
|
||||
})
|
||||
table.insert(failures, {
|
||||
bufnr = bufnr,
|
||||
lnum = tonumber(lnum) - 1,
|
||||
col = 0,
|
||||
severity = vim.diagnostic.severity.ERROR,
|
||||
source = 'junit',
|
||||
message = cause,
|
||||
})
|
||||
break
|
||||
end
|
||||
repl.append(msg, '$')
|
||||
end
|
||||
if not testMatch then
|
||||
for _, msg in ipairs(test.traces) do
|
||||
local match = msg:match(string.format('at %s', test.fq_class) .. '[%w%p]+%(([%a%p]*:%d+)%)')
|
||||
if match then
|
||||
testMatch = true
|
||||
local lnum = vim.split(match, ':')[2]
|
||||
local trace = table.concat(test.traces, '\n')
|
||||
local cause = trace:sub(1, trace:find(msg, 1, true) - 1)
|
||||
table.insert(failures, {
|
||||
bufnr = bufnr,
|
||||
lnum = tonumber(lnum) - 1,
|
||||
col = 0,
|
||||
severity = vim.diagnostic.severity.ERROR,
|
||||
source = 'junit',
|
||||
message = cause,
|
||||
})
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if not testMatch then
|
||||
local cause = test.traces[1] .. '\n'
|
||||
if #test.traces > 2 then
|
||||
cause = cause .. test.traces[2] .. '\n'
|
||||
end
|
||||
table.insert(failures, {
|
||||
bufnr = bufnr,
|
||||
-- Generic error. Avoid overlay conflicts with virtual text
|
||||
lnum = start_line_num - 1,
|
||||
col = 0,
|
||||
severity = vim.diagnostic.severity.ERROR,
|
||||
source = 'junit',
|
||||
message = cause,
|
||||
})
|
||||
end
|
||||
else
|
||||
repl.append('✔️ ' .. test.method, '$')
|
||||
if start_line_num ~= nil then
|
||||
table.insert(results, {
|
||||
lnum = start_line_num,
|
||||
success = true
|
||||
})
|
||||
end
|
||||
repl.append(success_symbol .. ' ' .. test.method, '$')
|
||||
end
|
||||
end
|
||||
vim.diagnostic.set(ns, bufnr, failures, {})
|
||||
|
||||
local unique_lnums = {}
|
||||
-- Traverse in reverse order to preserve the mark position in case of Repeated/Parameterized Tests
|
||||
-- right_align doesn't seems to work correctly when set to false
|
||||
for i = #results, 1, -1 do
|
||||
local result = results[i]
|
||||
local symbol = result.success and success_symbol or error_symbol
|
||||
vim.api.nvim_buf_set_extmark(bufnr, ns, result.lnum, 0, {
|
||||
virt_text = { { symbol } },
|
||||
invalidate = true
|
||||
})
|
||||
unique_lnums[result.lnum] = true
|
||||
end
|
||||
for key, _ in pairs(unique_lnums) do
|
||||
local indent = '\t'
|
||||
vim.api.nvim_buf_set_extmark(bufnr, ns, key, 0, {
|
||||
virt_text = { { indent } },
|
||||
invalidate = true
|
||||
})
|
||||
end
|
||||
|
||||
if num_failures > 0 then
|
||||
vim.fn.setqflist({}, 'r', {
|
||||
|
@ -124,18 +229,17 @@ function M.mk_test_results(bufnr)
|
|||
print(
|
||||
'Tests finished. Results printed to dap-repl.',
|
||||
#items > 0 and 'Errors added to quickfix list' or '',
|
||||
string.format('(❌%d / %d)', num_failures, #tests)
|
||||
string.format('(%s %d / %d)', error_symbol, num_failures, #tests)
|
||||
)
|
||||
else
|
||||
print('Tests finished. Results printed to dap-repl. All', #tests, 'succeeded')
|
||||
print('Tests finished. Results printed to dap-repl.', success_symbol, #tests, 'succeeded')
|
||||
end
|
||||
return items
|
||||
end;
|
||||
end,
|
||||
mk_reader = function(sock)
|
||||
return vim.schedule_wrap(mk_buf_loop(sock, handle_buffer))
|
||||
end;
|
||||
end,
|
||||
}
|
||||
end
|
||||
|
||||
|
||||
return M
|
||||
|
|
Loading…
Reference in a new issue