Skip to content

Commit 96612b2

Browse files
committed
Stream log for N seconds. Fix line cropping when reading entire log.
1 parent 7a96d09 commit 96612b2

File tree

1 file changed

+33
-24
lines changed

1 file changed

+33
-24
lines changed

src/rabbit_log_tail.erl

Lines changed: 33 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,23 @@
11
-module(rabbit_log_tail).
22

33
-export([tail_n_lines/2]).
4-
-export([init_tail_stream/3]).
4+
-export([init_tail_stream/4]).
55

66
-define(GUESS_OFFSET, 200).
77

8-
init_tail_stream(Filename, Pid, Ref) ->
8+
init_tail_stream(Filename, Pid, Ref, Duration) ->
99
RPCProc = self(),
1010
Reader = spawn(fun() ->
1111
link(Pid),
1212
case file:open(Filename, [read, binary]) of
1313
{ok, File} ->
14+
TimeLimit = case Duration of
15+
infinity -> infinity;
16+
_ -> erlang:system_time(second) + Duration
17+
end,
1418
{ok, _} = file:position(File, eof),
1519
RPCProc ! {Ref, opened},
16-
read_loop(File, Pid, Ref);
20+
read_loop(File, Pid, Ref, TimeLimit);
1721
{error, _} = Err ->
1822
RPCProc ! {Ref, Err}
1923
end
@@ -26,16 +30,20 @@ init_tail_stream(Filename, Pid, Ref) ->
2630
{error, timeout}
2731
end.
2832

29-
read_loop(File, Pid, Ref) ->
30-
case file:read(File, ?GUESS_OFFSET) of
31-
{ok, Data} ->
32-
Pid ! {Ref, Data, confinue},
33-
read_loop(File, Pid, Ref);
34-
eof ->
35-
timer:sleep(1000),
36-
read_loop(File, Pid, Ref);
37-
{error, _} = Err ->
38-
Pid ! {Ref, Err, finished}
33+
read_loop(File, Pid, Ref, TimeLimit) ->
34+
case is_integer(TimeLimit) andalso erlang:system_time(second) > TimeLimit of
35+
true -> Pid ! {Ref, <<>>, finished};
36+
false ->
37+
case file:read(File, ?GUESS_OFFSET) of
38+
{ok, Data} ->
39+
Pid ! {Ref, Data, confinue},
40+
read_loop(File, Pid, Ref, TimeLimit);
41+
eof ->
42+
timer:sleep(1000),
43+
read_loop(File, Pid, Ref, TimeLimit);
44+
{error, _} = Err ->
45+
Pid ! {Ref, Err, finished}
46+
end
3947
end.
4048

4149
tail_n_lines(Filename, N) ->
@@ -46,7 +54,7 @@ tail_n_lines(Filename, N) ->
4654
Result = reverse_read_n_lines(N, N, File, Eof, Eof),
4755
file:close(File),
4856
Result;
49-
Error -> Error
57+
{error, _} = Error -> Error
5058
end.
5159

5260
reverse_read_n_lines(N, OffsetN, File, Position, Eof) ->
@@ -63,23 +71,24 @@ reverse_read_n_lines(N, OffsetN, File, Position, Eof) ->
6371
_ ->
6472
reverse_read_n_lines(N, N - NLines + 1, File, GuessPosition, Eof)
6573
end;
66-
Error -> Error
74+
{error, _} = Error -> Error
6775
end.
6876

6977
read_from_position(File, GuessPosition, Eof) ->
7078
file:pread(File, GuessPosition, max(0, Eof - GuessPosition)).
7179

7280
read_lines_from_position(File, GuessPosition, Eof) ->
7381
case read_from_position(File, GuessPosition, Eof) of
74-
{ok, Data} -> {ok, crop_lines(Data)};
75-
Error -> Error
76-
end.
77-
78-
crop_lines(Data) ->
79-
%% Drop the first line, because it's most likely partial.
80-
case binary:split(Data, <<"\n">>, [global, trim]) of
81-
[_|Rest] -> Rest;
82-
[] -> []
82+
{ok, Data} ->
83+
Lines = binary:split(Data, <<"\n">>, [global, trim]),
84+
case {GuessPosition, Lines} of
85+
%% If position is 0 - there are no partial lines
86+
{0, _} -> {ok, Lines};
87+
%% Remove first line as it can be partial
88+
{_, [_ | Rest]} -> {ok, Rest};
89+
{_, []} -> {ok, []}
90+
end;
91+
{error, _} = Error -> Error
8392
end.
8493

8594
offset(Base, N) ->

0 commit comments

Comments
 (0)