diff options
| -rw-r--r-- | ebin/rabbit_app.in | 1 | ||||
| -rw-r--r-- | src/rabbit_log.erl | 108 | ||||
| -rw-r--r-- | src/rabbit_reader.erl | 33 |
3 files changed, 67 insertions, 75 deletions
diff --git a/ebin/rabbit_app.in b/ebin/rabbit_app.in index 9301af6bdc..2fee1114aa 100644 --- a/ebin/rabbit_app.in +++ b/ebin/rabbit_app.in @@ -37,6 +37,7 @@ {auth_backends, [rabbit_auth_backend_internal]}, {delegate_count, 16}, {trace_vhosts, []}, + {log_levels, [{connection, info}]}, {tcp_listen_options, [binary, {packet, raw}, {reuseaddr, true}, diff --git a/src/rabbit_log.erl b/src/rabbit_log.erl index 558e095751..98c778077c 100644 --- a/src/rabbit_log.erl +++ b/src/rabbit_log.erl @@ -23,16 +23,28 @@ -export([init/1, handle_call/3, handle_cast/2, handle_info/2, terminate/2, code_change/3]). --export([debug/1, debug/2, message/4, info/1, info/2, +-export([message/4, log/3, log/4, + debug/1, debug/2, info/1, info/2, warning/1, warning/2, error/1, error/2]). -define(SERVER, ?MODULE). +-define(LEVELS, [debug, info, warning, error, none]). + %%---------------------------------------------------------------------------- -ifdef(use_specs). +-export_type([level/0]). + +-type(category() :: atom()). +-type(level() :: 'debug' | 'info' | 'warning' | 'error'). + -spec(start_link/0 :: () -> rabbit_types:ok_pid_or_error()). + +-spec(message/4 :: (_,_,_,_) -> 'ok'). +-spec(log/3 :: (category(), level(), string()) -> 'ok'). +-spec(log/4 :: (category(), level(), string(), [any()]) -> 'ok'). -spec(debug/1 :: (string()) -> 'ok'). -spec(debug/2 :: (string(), [any()]) -> 'ok'). -spec(info/1 :: (string()) -> 'ok'). @@ -42,83 +54,62 @@ -spec(error/1 :: (string()) -> 'ok'). -spec(error/2 :: (string(), [any()]) -> 'ok'). --spec(message/4 :: (_,_,_,_) -> 'ok'). - -endif. %%---------------------------------------------------------------------------- -start_link() -> - gen_server:start_link({local, ?SERVER}, ?MODULE, [], []). +-record(state, {levels, config}). -debug(Fmt) -> - gen_server:cast(?SERVER, {debug, Fmt}). +%%---------------------------------------------------------------------------- -debug(Fmt, Args) when is_list(Args) -> - gen_server:cast(?SERVER, {debug, Fmt, Args}). +start_link() -> + gen_server:start_link({local, ?SERVER}, ?MODULE, [?LEVELS], []). message(Direction, Channel, MethodRecord, Content) -> gen_server:cast(?SERVER, {message, Direction, Channel, MethodRecord, Content}). -info(Fmt) -> - gen_server:cast(?SERVER, {info, Fmt}). - -info(Fmt, Args) when is_list(Args) -> - gen_server:cast(?SERVER, {info, Fmt, Args}). +log(Category, Level, Fmt) -> log(Category, Level, Fmt, []). -warning(Fmt) -> - gen_server:cast(?SERVER, {warning, Fmt}). +log(Category, Level, Fmt, Args) when is_list(Args) -> + gen_server:cast(?SERVER, {log, Category, Level, Fmt, Args}). -warning(Fmt, Args) when is_list(Args) -> - gen_server:cast(?SERVER, {warning, Fmt, Args}). - -error(Fmt) -> - gen_server:cast(?SERVER, {error, Fmt}). - -error(Fmt, Args) when is_list(Args) -> - gen_server:cast(?SERVER, {error, Fmt, Args}). +debug(Fmt) -> log(default, debug, Fmt). +debug(Fmt, Args) -> log(default, debug, Fmt, Args). +info(Fmt) -> log(default, info, Fmt). +info(Fmt, Args) -> log(default, info, Fmt, Args). +warning(Fmt) -> log(default, warning, Fmt). +warning(Fmt, Args) -> log(default, warning, Fmt, Args). +error(Fmt) -> log(default, error, Fmt). +error(Fmt, Args) -> log(default, error, Fmt, Args). %%-------------------------------------------------------------------- -init([]) -> {ok, none}. +init([Levels]) -> + {ok, LevelConfig} = application:get_env(log_levels), + {ok, #state{levels = orddict:from_list( + lists:zip(Levels, lists:seq(1, length(Levels)))), + config = orddict:from_list(LevelConfig)}}. handle_call(_Request, _From, State) -> {noreply, State}. -handle_cast({debug, Fmt}, State) -> - io:format("debug:: "), io:format(Fmt), - error_logger:info_msg("debug:: " ++ Fmt), - {noreply, State}; -handle_cast({debug, Fmt, Args}, State) -> - io:format("debug:: "), io:format(Fmt, Args), - error_logger:info_msg("debug:: " ++ Fmt, Args), - {noreply, State}; -handle_cast({message, Direction, Channel, MethodRecord, Content}, State) -> - io:format("~s ch~p ~p~n", - [case Direction of - in -> "-->"; - out -> "<--" end, - Channel, - {MethodRecord, Content}]), - {noreply, State}; -handle_cast({info, Fmt}, State) -> - error_logger:info_msg(Fmt), - {noreply, State}; -handle_cast({info, Fmt, Args}, State) -> - error_logger:info_msg(Fmt, Args), - {noreply, State}; -handle_cast({warning, Fmt}, State) -> - error_logger:warning_msg(Fmt), - {noreply, State}; -handle_cast({warning, Fmt, Args}, State) -> - error_logger:warning_msg(Fmt, Args), - {noreply, State}; -handle_cast({error, Fmt}, State) -> - error_logger:error_msg(Fmt), - {noreply, State}; -handle_cast({error, Fmt, Args}, State) -> - error_logger:error_msg(Fmt, Args), +handle_cast({log, Category, Level, Fmt, Args}, + State = #state{levels = Levels, config = Config}) -> + CatLevel = case orddict:find(Category, Config) of + {ok, L} -> L; + error -> info + end, + case orddict:fetch(Level, Levels) >= orddict:fetch(CatLevel, Levels) of + false -> ok; + true -> case Level of + debug -> io:format("debug:: " ++ Fmt, Args), + error_logger:info_msg("debug:: " ++ Fmt, Args); + info -> error_logger:info_msg(Fmt, Args); + warning -> error_logger:warning_msg(Fmt, Args); + error -> error_logger:error_msg(Fmt, Args) + end + end, {noreply, State}; handle_cast(_Msg, State) -> {noreply, State}. @@ -131,4 +122,3 @@ terminate(_Reason, _State) -> code_change(_OldVsn, State, _Extra) -> {ok, State}. - diff --git a/src/rabbit_reader.erl b/src/rabbit_reader.erl index 61def40640..31be244b7a 100644 --- a/src/rabbit_reader.erl +++ b/src/rabbit_reader.erl @@ -177,13 +177,15 @@ server_capabilities(rabbit_framing_amqp_0_9_1) -> server_capabilities(_) -> []. +log(Level, Fmt, Args) -> rabbit_log:log(connection, Level, Fmt, Args). + inet_op(F) -> rabbit_misc:throw_on_error(inet_error, F). socket_op(Sock, Fun) -> case Fun(Sock) of {ok, Res} -> Res; - {error, Reason} -> rabbit_log:error("error on AMQP connection ~p: ~p~n", - [self(), Reason]), + {error, Reason} -> log(error, "error on AMQP connection ~p: ~p~n", + [self(), Reason]), exit(normal) end. @@ -194,7 +196,7 @@ start_connection(Parent, ChannelSupSupPid, Collector, StartHeartbeatFun, Deb, rabbit_net:connection_string( Sock0, inbound) end), - rabbit_log:info("accepting AMQP connection ~p (~s)~n", [self(), ConnStr]), + log(info, "accepting AMQP connection ~p (~s)~n", [self(), ConnStr]), ClientSock = socket_op(Sock, SockTransform), erlang:send_after(?HANDSHAKE_TIMEOUT * 1000, self(), handshake_timeout), @@ -225,15 +227,13 @@ start_connection(Parent, ChannelSupSupPid, Collector, StartHeartbeatFun, Deb, State, #v1.stats_timer), handshake, 8)) catch - Ex -> (if Ex == connection_closed_abruptly -> - fun rabbit_log:warning/2; - true -> - fun rabbit_log:error/2 - end)("exception on AMQP connection ~p (~s)~n~p~n", - [self(), ConnStr, Ex]) + Ex -> log(case Ex of + connection_closed_abruptly -> warning; + _ -> error + end, "exception on AMQP connection ~p (~s)~n~p~n", + [self(), ConnStr, Ex]) after - rabbit_log:info("closing AMQP connection ~p (~s)~n", - [self(), ConnStr]), + log(info, "closing AMQP connection ~p (~s)~n", [self(), ConnStr]), %% We don't close the socket explicitly. The reader is the %% controlling process and hence its termination will close %% the socket. Furthermore, gen_tcp:close/1 waits for pending @@ -388,8 +388,8 @@ handle_dependent_exit(ChPid, Reason, State) -> {_Channel, controlled} -> maybe_close(State); {Channel, uncontrolled} -> - rabbit_log:error("connection ~p, channel ~p - error:~n~p~n", - [self(), Channel, Reason]), + log(error, "connection ~p, channel ~p - error:~n~p~n", + [self(), Channel, Reason]), maybe_close(handle_exception(State, Channel, Reason)) end. @@ -431,9 +431,10 @@ wait_for_channel_termination(N, TimerRef) -> {_Channel, controlled} -> wait_for_channel_termination(N-1, TimerRef); {Channel, uncontrolled} -> - rabbit_log:error("connection ~p, channel ~p - " - "error while terminating:~n~p~n", - [self(), Channel, Reason]), + log(error, + "connection ~p, channel ~p - " + "error while terminating:~n~p~n", + [self(), Channel, Reason]), wait_for_channel_termination(N-1, TimerRef) end; cancel_wait -> |
