1%%
2%% %CopyrightBegin%
3%%
4%% Copyright Ericsson AB 1997-2017. All Rights Reserved.
5%%
6%% Licensed under the Apache License, Version 2.0 (the "License");
7%% you may not use this file except in compliance with the License.
8%% You may obtain a copy of the License at
9%%
10%%     http://www.apache.org/licenses/LICENSE-2.0
11%%
12%% Unless required by applicable law or agreed to in writing, software
13%% distributed under the License is distributed on an "AS IS" BASIS,
14%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15%% See the License for the specific language governing permissions and
16%% limitations under the License.
17%%
18%% %CopyrightEnd%
19%%
20%%
21-module(httpd_logger).
22
23-include_lib("kernel/include/logger.hrl").
24-include_lib("inets/include/httpd.hrl").
25
26-export([error_report/4, log/3, format/1]).
27
28error_report(Protocol, Reason, #mod{init_data = #init_data{peername = PeerName,
29                                                         sockname = SockName},
30                                     socket_type = Type,
31                                     request_uri = URI,
32                                    config_db = Db},
33             Location) ->
34    ServerName = httpd_util:lookup(Db, server_name),
35    Report0 = #{protocol => Protocol,
36               reason => Reason,
37               peer => PeerName,
38               host => SockName,
39               server_name => ServerName,
40               metadata => Location},
41    Report1 = case URI of
42                  undefined ->
43                      Report0;
44                  _ ->
45                      Report0#{uri => URI}
46              end,
47    case Protocol of
48        'HTTP' ->
49            Report1#{transport => transport_type(Type)};
50        _ ->
51            Report1
52    end.
53
54log(Level, #{metadata := MetaData} = Report, Domain) ->
55    logger:log(Level, maps:without([metadata], Report),
56               MetaData#{domain => [otp,inets, httpd, Domain, Level],
57                         report_cb => fun ?MODULE:format/1}).
58
59format(#{protocol := Protocol} = Report) when Protocol == 'TLS';
60                                              Protocol == 'TCP' ->
61    #{reason := Desc,
62      peer := {PeerPort, Peer},
63      host := {HostPort, Host},
64      server_name := ServerName
65     } = Report,
66    {
67     "~10s ~s~n"
68     "~10s ~s~n"
69     "~10s ~s:~p~n"
70     "~10s ~s:~p~n"
71     "~10s ~p~n"
72     "~n",
73     ["Server:", ServerName,
74      "Protocol:", atom_to_list(Protocol),
75      "Host:", Host, HostPort,
76      "Peer:", Peer, PeerPort,
77      "Reason:", Desc]
78    };
79format(#{protocol := 'HTTP' = Protocol,  uri := URI} = Report) ->
80    #{reason := Desc,
81      transport := Transport,
82      peer := {PeerPort, Peer},
83      host := {HostPort, Host},
84      server_name := ServerName} = Report,
85    {
86     "~10s ~s~n"
87     "~10s ~s~n"
88     "~10s ~s~n"
89     "~10s ~s~n"
90     "~10s ~s:~p~n"
91     "~10s ~s:~p~n"
92     "~10s ~p~n"
93     "~n",
94     ["Server:", ServerName,
95      "Protocol:", atom_to_list(Protocol),
96      "Transport:", Transport,
97      "URI:", URI,
98      "Host:", Host, HostPort,
99      "Peer:", Peer, PeerPort,
100      "Reason:", Desc]
101    };
102format(#{protocol := 'HTTP' = Protocol} = Report) ->
103    #{reason := Desc,
104      transport := Transport,
105      peer := {PeerPort, Peer},
106      host := {HostPort, Host},
107      server_name := ServerName} = Report,
108    {
109     "~10s ~s~n"
110     "~10s ~s~n"
111     "~10s ~s~n"
112     "~10s ~s:~p~n"
113     "~10s ~s:~p~n"
114     "~10s ~p~n"
115     "~n",
116     ["Server:", ServerName,
117      "Protocol:", atom_to_list(Protocol),
118      "Transport:",  Transport,
119      "Host:", Host, HostPort,
120      "Peer:", Peer, PeerPort,
121      "Reason:", Desc]
122    };
123format(#{protocol := internal = Protocol} = Report) ->
124    #{reason := Desc,
125      host := {HostPort, Host},
126      server_name := ServerName
127     } = Report,
128    {
129     "~10s ~s~n"
130     "~10s ~s~n"
131     "~10s ~s:~p~n"
132     "~10s ~p~n"
133     "~n",
134     ["Server:", ServerName,
135      "Protocol:", atom_to_list(Protocol),
136      "Host:", Host, HostPort,
137      "Reason:", Desc]
138    }.
139
140transport_type(ip_comm) ->
141    "TCP";
142transport_type(_) ->
143    "TLS".
144