Skip to content

Commit 766a4f2

Browse files
authored
fix(job): Line buffer needs same life cycle as the pipe reader (#387)
Problem: Data is lost when a chunk ends with an incomplete line. The line buffer only lives for the duration of processing a single chunk. Solution: Make the line buffer exist for the entire life cycle of the pipe reader.
1 parent 7d6cc4a commit 766a4f2

File tree

1 file changed

+31
-29
lines changed

1 file changed

+31
-29
lines changed

lua/diffview/job.lua

Lines changed: 31 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -165,47 +165,49 @@ end
165165
---@param pipe uv_pipe_t
166166
---@param out string[]
167167
---@param line_listeners? diffview.Job.OnOutCallback[]
168-
---@param err? string
169-
---@param data? string
170-
function Job:line_reader(pipe, out, line_listeners, err, data)
168+
function Job:line_reader(pipe, out, line_listeners)
171169
local line_buffer
172170

173-
if err then
174-
logger:error("[Job:line_reader()] " .. err)
175-
end
171+
---@param err? string
172+
---@param data? string
173+
return function (err, data)
174+
if err then
175+
logger:error("[Job:line_reader()] " .. err)
176+
end
176177

177-
if data then
178-
local has_eol = data:sub(-1) == "\n"
179-
local lines = vim.split(data, "\r?\n")
178+
if data then
179+
local has_eol = data:sub(-1) == "\n"
180+
local lines = vim.split(data, "\r?\n")
180181

181-
lines[1] = (line_buffer or "") .. lines[1]
182-
line_buffer = nil
182+
lines[1] = (line_buffer or "") .. lines[1]
183+
line_buffer = nil
183184

184-
for i, line in ipairs(lines) do
185-
if not has_eol and i == #lines then
186-
line_buffer = line
187-
else
188-
out[#out+1] = line
185+
for i, line in ipairs(lines) do
186+
if not has_eol and i == #lines then
187+
line_buffer = line
188+
else
189+
out[#out+1] = line
189190

190-
if line_listeners then
191-
for _, listener in ipairs(line_listeners) do
192-
listener(nil, line, self)
191+
if line_listeners then
192+
for _, listener in ipairs(line_listeners) do
193+
listener(nil, line, self)
194+
end
193195
end
194196
end
195197
end
196-
end
197-
else
198-
if line_buffer then
199-
out[#out+1] = line_buffer
198+
else
199+
if line_buffer then
200+
out[#out+1] = line_buffer
200201

201-
if line_listeners then
202-
for _, listener in ipairs(line_listeners) do
203-
listener(nil, line_buffer, self)
202+
if line_listeners then
203+
for _, listener in ipairs(line_listeners) do
204+
listener(nil, line_buffer, self)
205+
end
204206
end
205207
end
206-
end
207208

208-
try_close(pipe)
209+
try_close(pipe)
210+
end
209211
end
210212
end
211213

@@ -221,7 +223,7 @@ function Job:handle_reader(pipe, out, kind)
221223
out = self.on_stdout_listeners,
222224
err = self.on_stderr_listeners,
223225
})[kind] or {}
224-
pipe:read_start(utils.bind(self.line_reader, self, pipe, out, listeners))
226+
pipe:read_start(self:line_reader(pipe, out, listeners))
225227
end
226228
end
227229

0 commit comments

Comments
 (0)