From ab5d442d9f87c1f19731b5b6cb52e4a65bd4f51c Mon Sep 17 00:00:00 2001 From: Fabio Salvini Date: Mon, 26 Jun 2017 11:39:16 +0200 Subject: [PATCH] Save emails to send to Mnesia --- TODO.md | 7 +++ apps/log_monitor/src/log_monitor_app.erl | 16 ++++++- apps/log_monitor/src/mailer.erl | 59 +++++++++++++++++++++--- apps/log_monitor/src/mnesia_tables.hrl | 1 + 4 files changed, 75 insertions(+), 8 deletions(-) create mode 100644 TODO.md diff --git a/TODO.md b/TODO.md new file mode 100644 index 0000000..5789005 --- /dev/null +++ b/TODO.md @@ -0,0 +1,7 @@ +TODO +===== + + - Manage problem of "infinite" consecutive errors. + - Limit number of emails that can be sent in a period of time. + - Store the logfiles in a configuration file. + - gen_fsm for gatherer? diff --git a/apps/log_monitor/src/log_monitor_app.erl b/apps/log_monitor/src/log_monitor_app.erl index 5631820..b798e4e 100644 --- a/apps/log_monitor/src/log_monitor_app.erl +++ b/apps/log_monitor/src/log_monitor_app.erl @@ -31,7 +31,7 @@ stop(_State) -> start_mnesia() -> Nodes = [node()], - %% Stop Mnesia if is running, cannot create schema otherwise. + %% Stop Mnesia if it is running, cannot create schema otherwise. mnesia:stop(), mnesia:create_schema(Nodes), mnesia:start(), @@ -46,4 +46,16 @@ start_mnesia() -> {index, [#log_monitor_file.group]}, {disc_copies, Nodes} ]), - ok = mnesia:wait_for_tables([log_monitor_group, log_monitor_file], 30000). + mnesia:create_table(log_monitor_error, + [ + {attributes, record_info(fields, log_monitor_error)}, + {disc_copies, Nodes} + ]), + ok = mnesia:wait_for_tables( + [ + log_monitor_group, + log_monitor_file, + log_monitor_error + ], + 30000 + ). diff --git a/apps/log_monitor/src/mailer.erl b/apps/log_monitor/src/mailer.erl index c47d950..8e0e71f 100644 --- a/apps/log_monitor/src/mailer.erl +++ b/apps/log_monitor/src/mailer.erl @@ -1,6 +1,8 @@ -module(mailer). -behaviour(gen_server). +-include_lib("mnesia_tables.hrl"). + -export([start_link/0, init/1, terminate/2]). -export([handle_info/2, handle_cast/2, handle_call/3]). -export([code_change/3]). @@ -10,15 +12,27 @@ start_link() -> init([]) -> register(mailer, self()), + timer:send_after(1000, {send_emails}), {ok, []}. -handle_info({error, File, Text}, []) -> - case send_email(File, Text) of - {error, Reason, Message} -> - error_logger:error_msg("Error sending email: ~s ~p~n", [Reason, Message]); - _ -> ok +handle_info({error, File, Text}, State) -> + mnesia:activity( + transaction, + fun() -> + Id = erlang:monotonic_time(), + mnesia:write(#log_monitor_error{id = Id, file = File, text = Text}) + end), + {noreply, State}; +handle_info({send_emails}, State) -> + Emails = emails_to_send(), + try send_emails(Emails) of + _ -> timer:send_after(1000, {send_emails}) + catch + _Throw -> + error_logger:info_msg("Waiting 60s before sending new emails~n"), + timer:send_after(60000, {send_emails}) end, - {noreply, []}. + {noreply, State}. handle_cast(_Msg, State) -> {noreply, State}. @@ -32,6 +46,31 @@ terminate(_Reason, _State) -> code_change(_OldVsn, State, _Extra) -> {ok, State}. +emails_to_send() -> + mnesia:activity( + transaction, + fun() -> + mnesia:foldl( + fun(#log_monitor_error{id = Id, file = File, text = Text}, Acc) -> + [{Id, File, Text}] ++ Acc + end, [], log_monitor_error) + end). + +send_emails(Emails) -> + case Emails of + [] -> {ok}; + [{Id, File, Text} | Others] -> + case send_email(File, Text) of + {error, Reason, Message} -> + error_logger:error_msg("Error sending email: ~s ~p~n", [Reason, Message]), + throw(cannot_send_email); + _ -> + remove_email(Id), + send_emails(Others), + {ok} + end + end. + send_email(File, Text) -> {ok, EmailConfig} = application:get_env(log_monitor, email_config), Sender = proplists:get_value(sender, EmailConfig), @@ -43,3 +82,11 @@ send_email(File, Text) -> io_lib:format("Subject: Error notification\r\nFrom: Fabio\r\n\r\nLogfile: ~s~nError: ~n~s~n", [File, Text])}, Connection ). + +remove_email(Id) -> + mnesia:activity( + transaction, + fun() -> + mnesia:delete({log_monitor_error, Id}) + end), + ok. diff --git a/apps/log_monitor/src/mnesia_tables.hrl b/apps/log_monitor/src/mnesia_tables.hrl index ecf98ab..9b907ee 100644 --- a/apps/log_monitor/src/mnesia_tables.hrl +++ b/apps/log_monitor/src/mnesia_tables.hrl @@ -4,5 +4,6 @@ %% Mnesia tables -record(log_monitor_group, {name, email_receivers=[]}). -record(log_monitor_file, {file, error_regex, status, group}). +-record(log_monitor_error, {id, file, text}). -endif.