From 55e7860ceb04683c74846508479b9aca451b3b19 Mon Sep 17 00:00:00 2001 From: anlicheng <244108715@qq.com> Date: Tue, 3 Sep 2024 18:41:22 +0800 Subject: [PATCH] fix logger --- apps/iot/src/iot_logger.erl | 45 ++++++++++++++++++++++++++++--------- 1 file changed, 34 insertions(+), 11 deletions(-) diff --git a/apps/iot/src/iot_logger.erl b/apps/iot/src/iot_logger.erl index 7f64048..72a4691 100644 --- a/apps/iot/src/iot_logger.erl +++ b/apps/iot/src/iot_logger.erl @@ -19,10 +19,14 @@ -define(SERVER, ?MODULE). +%% 缓冲区大小 +-define(BUFFER_SIZE, 100). + -record(state, { file_name :: string(), date :: calendar:date(), - file + file, + buffer = [] }). %%%=================================================================== @@ -52,6 +56,8 @@ init([FileName]) -> FilePath = make_file(FileName), {ok, File} = file:open(FilePath, [append, binary]), + erlang:start_timer(5000, self(), flush_ticker), + {ok, #state{file = File, file_name = FileName, date = get_date()}}. %% @private @@ -73,19 +79,14 @@ handle_call(_Request, _From, State = #state{}) -> {noreply, NewState :: #state{}} | {noreply, NewState :: #state{}, timeout() | hibernate} | {stop, Reason :: term(), NewState :: #state{}}). -handle_cast({write, Data}, State = #state{file = OldFile, file_name = FileName, date = Date}) -> +handle_cast({write, Data}, State = #state{buffer = Buffer}) -> Line = <<(time_prefix())/binary, " ", (format(Data))/binary, $\n>>, - case maybe_new_file(Date) of + NBuffer = [Line|Buffer], + case length(NBuffer) >= ?BUFFER_SIZE of true -> - file:close(OldFile), - - FilePath = make_file(FileName), - {ok, File} = file:open(FilePath, [append, binary]), - ok = file:write(File, Line), - {noreply, State#state{file = File, date = get_date()}}; + {noreply, flush(State#state{buffer = NBuffer})}; false -> - ok = file:write(OldFile, Line), - {noreply, State} + {noreply, State#state{buffer = NBuffer}} end. %% @private @@ -94,6 +95,9 @@ handle_cast({write, Data}, State = #state{file = OldFile, file_name = FileName, {noreply, NewState :: #state{}} | {noreply, NewState :: #state{}, timeout() | hibernate} | {stop, Reason :: term(), NewState :: #state{}}). +handle_info({timeout, _, flush_ticker}, State) -> + erlang:start_timer(5000, self(), flush_ticker), + {noreply, flush(State)}; handle_info(_Info, State = #state{}) -> {noreply, State}. @@ -119,6 +123,25 @@ code_change(_OldVsn, State = #state{}, _Extra) -> %%% Internal functions %%%=================================================================== +-spec flush(State :: #state{}) -> NState :: #state{}. +flush(State = #state{buffer = []}) -> + State; +flush(State = #state{file = OldFile, file_name = FileName, date = Date, buffer = Buffer}) -> + Content = iolist_to_binary(lists:reverse(Buffer)), + case maybe_new_file(Date) of + true -> + file:close(OldFile), + + FilePath = make_file(FileName), + {ok, File} = file:open(FilePath, [append, binary]), + + ok = file:write(File, Content), + State#state{file = File, buffer = [], date = get_date()}; + false -> + ok = file:write(OldFile, Content), + State#state{buffer = []} + end. + format(Data) when is_binary(Data) -> iolist_to_binary(Data); format(Items) when is_list(Items) ->