httplog 0.2.15 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 9d6a52cb676f03cfac9c5a01d9ccc94a90fa570c
4
- data.tar.gz: e9df033e0168daa111145d05e325d727f88f17ac
3
+ metadata.gz: cf4cc23f31ff23be6b482a93162f13f24f3a1ff0
4
+ data.tar.gz: 3f649844b6d24e7352d834f24391fff4803270a9
5
5
  SHA512:
6
- metadata.gz: 4547cfe819ebdd84ed7feca3c274d9311528146607a9e6ef3caa5e46800660038cda8e3954761b13658ae09ca0729028c95f64f0e5cc2563252350cd39c40815
7
- data.tar.gz: 016c63b7476a75c47f0e6c0d8eab37d3a1e209d4438689b386f614f85499b42e03c4ac570c5430c6881d096101aecc8fc25908b79b34952d59a74d38bec734ca
6
+ metadata.gz: dc9258c783313ef2293e9681d5cca9bc069cd3f9010bf9c03425e2828d8e8b39e771a5af10d3323598a7dcf84f52dad0f1b662256b55d786124198da250253f2
7
+ data.tar.gz: a8e8e2d9e43241ae5cf017954222ec5ac4dbf5c55a61f76085fcecdb61fd572b365f7464d86f7754f19182a49eef4950ea9d569d0e2499848f7c37f89648bf75
data/README.md CHANGED
@@ -36,7 +36,12 @@ use this in a production environment.
36
36
 
37
37
  require 'httplog'
38
38
 
39
- By default, this will log all outgoing HTTP requests and their responses to $stdout on DEBUG level.
39
+ By default, this will log all outgoing HTTP requests and their responses to $stdout on DEBUG level.
40
+
41
+ ### Notes on content types
42
+
43
+ * Binary data from response bodies (as indicated by the `Content-Type` header)is not logged.
44
+ * Text data (`text/*` and most `application/*` types) is encoded as UTF-8, with invalid characters replaced. If you need to inspect raw non-UTF data exactly as sent over the wire, this tool is probably not for you.
40
45
 
41
46
  ### Configuration
42
47
 
@@ -30,11 +30,13 @@ if defined?(Ethon)
30
30
 
31
31
  # Not sure where the acutal status code is stored - so let's
32
32
  # extract it from the response header.
33
- status = response_headers.scan(/HTTP\/... (\d{3})/).flatten.first
33
+ status = response_headers.scan(/HTTP\/... (\d{3})/).flatten.first
34
+ encoding = response_headers.scan(/Content-Encoding: (\S+)/).flatten.first
35
+ content_type = response_headers.scan(/Content-Type: (\S+(; charset=\S+)?)/).flatten.first
34
36
  HttpLog.log_compact(@action_name, @url, @return_code, bm)
35
37
  HttpLog.log_status(status)
36
38
  HttpLog.log_benchmark(bm)
37
- HttpLog.log_body(response_body)
39
+ HttpLog.log_body(response_body, encoding, content_type)
38
40
  return_code
39
41
  end
40
42
  end
@@ -55,8 +55,10 @@ if defined?(Excon)
55
55
  datum = orig_response(datum)
56
56
  end
57
57
  response = datum[:response]
58
+ headers = response[:headers] || {}
59
+ content_type =
58
60
  HttpLog.log_status(response[:status])
59
- HttpLog.log_body(response[:body])
61
+ HttpLog.log_body(response[:body], headers['Content-Encoding'], headers['Content-Type'])
60
62
  datum
61
63
  end
62
64
  end
@@ -18,11 +18,12 @@ if defined?(::HTTP::Client) and defined?(::HTTP::Connection)
18
18
  end
19
19
 
20
20
  if log_enabled
21
+ headers = @response.headers
21
22
  HttpLog.log_compact(req.verb, req.uri, @response.code, bm)
22
23
  HttpLog.log_status(@response.code)
23
24
  HttpLog.log_benchmark(bm)
24
25
  HttpLog.log_headers(@response.headers.to_h)
25
- HttpLog.log_body(@response.body, @response.headers["Content-Encoding"])
26
+ HttpLog.log_body(@response.body, headers['Content-Encoding'], headers['Content-Type'])
26
27
  end
27
28
 
28
29
  @response
@@ -23,10 +23,11 @@ if defined?(::HTTPClient)
23
23
 
24
24
  if log_enabled
25
25
  res = conn.pop
26
+ headers = res.headers
26
27
  HttpLog.log_compact(req.header.request_method, req.header.request_uri, res.status_code, bm)
27
28
  HttpLog.log_status(res.status_code)
28
29
  HttpLog.log_benchmark(bm)
29
- HttpLog.log_body(res.body)
30
+ HttpLog.log_body(res.body, headers['Content-Encoding'], headers['Content-Type'])
30
31
  conn.push(res)
31
32
  end
32
33
 
@@ -26,7 +26,7 @@ module Net
26
26
  HttpLog.log_status(@response.code)
27
27
  HttpLog.log_benchmark(bm)
28
28
  HttpLog.log_headers(@response.each_header.collect)
29
- HttpLog.log_body(@response.body, @response.header["Content-Encoding"])
29
+ HttpLog.log_body(@response.body, @response['Content-Encoding'], @response['Content-Type'])
30
30
  end
31
31
 
32
32
  @response
@@ -16,10 +16,11 @@ if defined?(Patron)
16
16
  end
17
17
 
18
18
  if log_enabled
19
+ headers = @response.headers
19
20
  HttpLog.log_compact(action_name, url, @response.status, bm)
20
21
  HttpLog.log_status(@response.status)
21
22
  HttpLog.log_benchmark(bm)
22
- HttpLog.log_body(@response.body)
23
+ HttpLog.log_body(@response.body, headers['Content-Encoding'], headers['Content-Type'])
23
24
  end
24
25
  end
25
26
  end
@@ -76,26 +76,35 @@ module HttpLog
76
76
  log("Benchmark: #{seconds} seconds")
77
77
  end
78
78
 
79
- def log_body(body, encoding = nil)
79
+ def log_body(body, encoding = nil, content_type=nil)
80
80
  return if options[:compact_log] || !options[:log_response]
81
+
82
+ unless text_based?(content_type)
83
+ log("Response: (not showing binary data)")
84
+ return
85
+ end
86
+
81
87
  if body.is_a?(Net::ReadAdapter)
82
88
  # open-uri wraps the response in a Net::ReadAdapter that defers reading
83
89
  # the content, so the reponse body is not available here.
84
90
  log("Response: (not available yet)")
85
- else
86
- if encoding =~ /gzip/
87
- sio = StringIO.new( body.to_s )
88
- gz = Zlib::GzipReader.new( sio )
89
- log("Response: (deflated)\n#{gz.read}")
90
- else
91
- log("Response:\n#{body.to_s}")
92
- end
91
+ return
93
92
  end
93
+
94
+ if encoding =~ /gzip/
95
+ sio = StringIO.new( body.to_s )
96
+ gz = Zlib::GzipReader.new( sio )
97
+ body = gz.read
98
+ end
99
+
100
+ data = utf_encoded(body.to_s, content_type)
101
+
102
+ log("Response:\n#{data}")
94
103
  end
95
104
 
96
105
  def log_data(data)
97
106
  return if options[:compact_log] || !options[:log_data]
98
- data = data.to_s.encode('UTF-8', :invalid => :replace, :undef => :replace) if data
107
+ data = utf_encoded(data.to_s)
99
108
  log("Data: #{data}")
100
109
  end
101
110
 
@@ -109,5 +118,21 @@ module HttpLog
109
118
  return msg unless options[:color]
110
119
  msg.send(:colorize, options[:color])
111
120
  end
121
+
122
+ private
123
+
124
+ def utf_encoded(data, content_type=nil)
125
+ charset = content_type.to_s.scan(/; charset=(\S+)/).flatten.first || 'UTF-8'
126
+ data.force_encoding(charset) rescue data.force_encoding('UTF-8')
127
+ data.encode('UTF-8', :invalid => :replace, :undef => :replace)
128
+ end
129
+
130
+ def text_based?(content_type)
131
+ # This is a very naive way of determining if the content type is text-based; but
132
+ # it will allow application/json and the like without having to resort to more
133
+ # heavy-handed checks.
134
+ content_type =~ /^text/ ||
135
+ content_type =~ /^application/ && content_type != 'application/octet-stream'
136
+ end
112
137
  end
113
138
  end
@@ -1,4 +1,4 @@
1
1
  module HttpLog
2
- VERSION = "0.2.15"
2
+ VERSION = "0.3.0"
3
3
  end
4
4
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: httplog
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.15
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Thilo Rusche
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-12-06 00:00:00.000000000 Z
11
+ date: 2016-01-15 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rspec