debug_logging 1.0.11 → 1.0.12
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 +4 -4
- data/.travis.yml +1 -3
- data/README.md +14 -5
- data/debug_logging.gemspec +1 -0
- data/lib/debug_logging.rb +15 -3
- data/lib/debug_logging/class_logger.rb +22 -9
- data/lib/debug_logging/configuration.rb +29 -0
- data/lib/debug_logging/instance_logger_modulizer.rb +15 -7
- data/lib/debug_logging/version.rb +1 -1
- metadata +16 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: fd9ac9873cb177a6864e30599bdcfe3093837415
|
|
4
|
+
data.tar.gz: cde61e395a53bf5289ead7d0cd823de06c2925a3
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 31bf8b39f62289b7bf0e8ef845cdca2a8049ba492ce259ba9c19b2cf11fb364a004228d710e1d791ef6c83251e029a8f65c884ff0bcff03d39d901a47a7299c6
|
|
7
|
+
data.tar.gz: f6a1ec5e93ad0c074a3fa91ff50a676db59afaff1406d7b382616cfc383a54690769e763ef1b4b2d9f7bd7342c0446e903b71a633857e1dfd9eaaba9d63bfc29
|
data/.travis.yml
CHANGED
data/README.md
CHANGED
|
@@ -7,9 +7,11 @@ Unobtrusive, inheritable-overridable-configurable, drop-in debug logging, that w
|
|
|
7
7
|
* *colorization by class/method*
|
|
8
8
|
* *robust argument printer with customizable ellipsis*
|
|
9
9
|
* *unique invocation identifiers*
|
|
10
|
-
* *single line config*
|
|
11
|
-
* *separate logger*
|
|
12
|
-
*
|
|
10
|
+
* *single line config, per class/instance/method config*
|
|
11
|
+
* *separate logger, if needed*
|
|
12
|
+
* *log method calls, also when exit scope*
|
|
13
|
+
* *Prevents heavy computation of strings with `logger.debug { 'log me' }` block format.*
|
|
14
|
+
* **so many free ponies** 🎠🐴🎠🐴🎠🐴
|
|
13
15
|
|
|
14
16
|
| Project | DebugLogging |
|
|
15
17
|
|------------------------ | ----------------- |
|
|
@@ -65,7 +67,9 @@ Or install it yourself as:
|
|
|
65
67
|
|
|
66
68
|
## Usage
|
|
67
69
|
|
|
68
|
-
|
|
70
|
+
NOTE: Starting with version `1.0.12` this gem utilizes the `logger.debug { "block format" }` to avoid heavy debug processing when the log level threshold is set higher than the level of the statements produced as a result of the configuration of this gem.
|
|
71
|
+
|
|
72
|
+
Crack open the specs for more complex usage examples than the ones below.
|
|
69
73
|
|
|
70
74
|
### Without Rails
|
|
71
75
|
|
|
@@ -90,6 +94,7 @@ DebugLogging.configuration.colorized_chain_for_method = false # e.g. ->(colorize
|
|
|
90
94
|
DebugLogging.configuration.colorized_chain_for_class = false # e.g. ->(colorized_string) { colorized_string.colorize(:light_blue ).colorize( :background => :red) }
|
|
91
95
|
DebugLogging.configuration.add_invocation_id = true # identify a method call uniquely in a log, pass a proc for colorization, e.g. ->(colorized_string) { colorized_string.light_black }
|
|
92
96
|
DebugLogging.configuration.ellipsis = " ✂️ …".freeze
|
|
97
|
+
DebugLogging.configuration.mark_scope_exit = true # Only has an effect if benchmarking is off, since benchmarking always marks the scope exit
|
|
93
98
|
```
|
|
94
99
|
|
|
95
100
|
If you prefer to use the block style:
|
|
@@ -108,14 +113,18 @@ DebugLogging.configure do |config|
|
|
|
108
113
|
config.colorized_chain_for_class = false # e.g. ->(colorized_string) { colorized_string.colorize(:light_blue ).colorize( :background => :red) }
|
|
109
114
|
config.add_invocation_id = true # identify a method call uniquely in a log, pass a proc for colorization, e.g. ->(colorized_string) { colorized_string.light_black }
|
|
110
115
|
config.ellipsis = " ✂️ …".freeze
|
|
116
|
+
config.mark_scope_exit = true # Only has an effect if benchmarking is off, since benchmarking always marks the scope exit
|
|
111
117
|
end
|
|
112
118
|
```
|
|
113
119
|
|
|
114
120
|
**All** of the above **config** is **inheritable** and **configurable** at the **per-class** level as well!
|
|
115
121
|
Just prepend `debug_` to any config value you want to override in a class.
|
|
116
122
|
|
|
123
|
+
**All** of the above **config** is **inheritable** and **configurable** at the **per-instance** level as well!
|
|
124
|
+
Just prepend `debug_` to any config value you want to override on an instance of a class.
|
|
125
|
+
|
|
117
126
|
**All** of the above **config** is **inheritable** and **configurable** at the **per-method** level as well!
|
|
118
|
-
Just send along a hash of the config options when you call `logged` or `include DebugLogging::InstanceLogger.new(i_methods: [:drive, :stop])`. See the example class below, and the specs.
|
|
127
|
+
Just send along a hash of the config options when you call `logged` or `include DebugLogging::InstanceLogger.new(i_methods: [:drive, :stop], config: { ellipsis = " ✂️ 2 much" })`. See the example class below, and the specs.
|
|
119
128
|
|
|
120
129
|
**NOTE ON** `Rails.logger` - It will probably be nil in your initializer, so setting the `config.logger` to `Rails.logger` there will result in setting it to `nil`, which means the default will end up being used: `Logger.new(STDOUT)`. Instead just config the logger in your application.rb, or anytime later, but *before your classes get loaded* and start inheriting the config:
|
|
121
130
|
|
data/debug_logging.gemspec
CHANGED
|
@@ -31,4 +31,5 @@ Automatically log selected methods and their arguments as they are called at run
|
|
|
31
31
|
spec.add_development_dependency "coveralls", "~> 0.8"
|
|
32
32
|
spec.add_development_dependency "rake", "~> 10.0"
|
|
33
33
|
spec.add_development_dependency "rspec", "~> 3.0"
|
|
34
|
+
spec.add_development_dependency "activesupport", "~> 5.1"
|
|
34
35
|
end
|
data/lib/debug_logging.rb
CHANGED
|
@@ -60,9 +60,15 @@ module DebugLogging
|
|
|
60
60
|
end
|
|
61
61
|
|
|
62
62
|
#### API ####
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
63
|
+
# Not used by this gem internally, but provides an external interface for
|
|
64
|
+
# classes to also use this logging tool directly,
|
|
65
|
+
# with configured options like benchmarking, colors, or leg level.
|
|
66
|
+
def debug_log(message = nil, config_proxy = nil, &block)
|
|
67
|
+
# If a, instance-method-level, or class-method-level custom config is not
|
|
68
|
+
# passed in, then fall back to the class' default config, which is a
|
|
69
|
+
# potentially customized copy of the default config for the whole app.
|
|
70
|
+
config_proxy ||= debug_config
|
|
71
|
+
config_proxy.log(message, &block)
|
|
66
72
|
end
|
|
67
73
|
|
|
68
74
|
# There are times when the class will need access to the configuration object,
|
|
@@ -161,6 +167,12 @@ module DebugLogging
|
|
|
161
167
|
def debug_add_invocation_id=(add_invocation_id)
|
|
162
168
|
@debug_logging_configuration.add_invocation_id = add_invocation_id
|
|
163
169
|
end
|
|
170
|
+
def debug_mark_scope_exit
|
|
171
|
+
@debug_logging_configuration.mark_scope_exit
|
|
172
|
+
end
|
|
173
|
+
def debug_mark_scope_exit=(mark_scope_exit)
|
|
174
|
+
@debug_logging_configuration.mark_scope_exit = mark_scope_exit
|
|
175
|
+
end
|
|
164
176
|
def debug_ellipsis
|
|
165
177
|
@debug_logging_configuration.ellipsis
|
|
166
178
|
end
|
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
module DebugLogging
|
|
2
2
|
module ClassLogger
|
|
3
3
|
def logged(*methods_to_log)
|
|
4
|
+
# When opts are present it will always be a new configuration instance per method
|
|
5
|
+
# When opts are not present it will reuse the class' configuration object
|
|
4
6
|
opts = methods_to_log.last.is_a?(Hash) && methods_to_log.pop
|
|
5
7
|
if methods_to_log.first.is_a?(Array)
|
|
6
8
|
methods_to_log = methods_to_log.shift
|
|
7
9
|
else
|
|
8
|
-
# logged :meth1, :meth2, :meth3 is valid
|
|
10
|
+
# logged :meth1, :meth2, :meth3 without options is valid too
|
|
9
11
|
end
|
|
10
12
|
methods_to_log.each do |method_to_log|
|
|
11
13
|
# method name must be a symbol
|
|
@@ -19,24 +21,35 @@ module DebugLogging
|
|
|
19
21
|
proxy = if opts
|
|
20
22
|
Configuration.new(**(debug_config.to_hash.merge(opts)))
|
|
21
23
|
else
|
|
22
|
-
|
|
24
|
+
debug_config
|
|
23
25
|
end
|
|
26
|
+
proxy.register(method_to_log)
|
|
24
27
|
instance_variable_set("@debug_config_proxy_for_k_#{method_to_log}".to_sym, proxy)
|
|
25
28
|
proxy
|
|
26
29
|
end
|
|
27
30
|
method_return_value = nil
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
31
|
+
log_prefix = nil
|
|
32
|
+
invocation_id = nil
|
|
33
|
+
config_proxy.log do
|
|
34
|
+
log_prefix = debug_invocation_to_s(klass: to_s, separator: ".", method_to_log: method_to_log, config_proxy: config_proxy)
|
|
35
|
+
invocation_id = debug_invocation_id_to_s(args: args, config_proxy: config_proxy)
|
|
36
|
+
signature = debug_signature_to_s(args: args, config_proxy: config_proxy)
|
|
37
|
+
"#{log_prefix}#{signature}#{invocation_id}"
|
|
38
|
+
end
|
|
39
|
+
if config_proxy.benchmarkable_for?(:debug_class_benchmarks)
|
|
34
40
|
tms = Benchmark.measure do
|
|
35
41
|
method_return_value = original_method.call(*args, &block)
|
|
36
42
|
end
|
|
37
|
-
|
|
43
|
+
config_proxy.log do
|
|
44
|
+
"#{log_prefix} #{debug_benchmark_to_s(tms: tms)}#{invocation_id}"
|
|
45
|
+
end
|
|
38
46
|
else
|
|
39
47
|
method_return_value = original_method.call(*args, &block)
|
|
48
|
+
if config_proxy.exit_scope_markable? && invocation_id && !invocation_id.empty?
|
|
49
|
+
config_proxy.log do
|
|
50
|
+
"#{log_prefix} completed#{invocation_id}"
|
|
51
|
+
end
|
|
52
|
+
end
|
|
40
53
|
end
|
|
41
54
|
method_return_value
|
|
42
55
|
end
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
module DebugLogging
|
|
2
2
|
class Configuration
|
|
3
3
|
DEFAULT_ELLIPSIS = " ✂️ …".freeze
|
|
4
|
+
# LEVELS = { 0 => :debug, 1 => :info, 2 => :warn, 3 => :error, 4 => :fatal, 5 => :unknown }
|
|
4
5
|
attr_accessor :logger
|
|
5
6
|
attr_accessor :log_level
|
|
6
7
|
attr_accessor :multiple_last_hashes
|
|
@@ -13,6 +14,8 @@ module DebugLogging
|
|
|
13
14
|
attr_accessor :colorized_chain_for_class
|
|
14
15
|
attr_accessor :add_invocation_id
|
|
15
16
|
attr_accessor :ellipsis
|
|
17
|
+
attr_accessor :mark_scope_exit
|
|
18
|
+
attr_reader :methods_to_log
|
|
16
19
|
# alias the readers to the debug_* prefix so an instance of this class
|
|
17
20
|
# can have the same API granted by `extend DebugLogging`
|
|
18
21
|
#
|
|
@@ -43,6 +46,7 @@ module DebugLogging
|
|
|
43
46
|
alias :debug_colorized_chain_for_class :colorized_chain_for_class
|
|
44
47
|
alias :debug_add_invocation_id :add_invocation_id
|
|
45
48
|
alias :debug_ellipsis :ellipsis
|
|
49
|
+
alias :debug_mark_scope_exit :mark_scope_exit
|
|
46
50
|
def initialize(**options)
|
|
47
51
|
@logger = options.key?(:logger) ? options[:logger] : Logger.new(STDOUT)
|
|
48
52
|
@log_level = options.key?(:log_level) ? options[:log_level] : :debug
|
|
@@ -56,6 +60,28 @@ module DebugLogging
|
|
|
56
60
|
@colorized_chain_for_class = options.key?(:colorized_chain_for_class) ? options[:colorized_chain_for_class] : false
|
|
57
61
|
@add_invocation_id = options.key?(:add_invocation_id) ? options[:add_invocation_id] : true
|
|
58
62
|
@ellipsis = options.key?(:ellipsis) ? options[:ellipsis] : DEFAULT_ELLIPSIS
|
|
63
|
+
@mark_scope_exit = options.key?(:mark_scope_exit) ? options[:mark_scope_exit] : false
|
|
64
|
+
@methods_to_log = []
|
|
65
|
+
end
|
|
66
|
+
def log(message = nil, &block)
|
|
67
|
+
return unless logger
|
|
68
|
+
if block_given?
|
|
69
|
+
logger.send(log_level, &block)
|
|
70
|
+
else
|
|
71
|
+
logger.send(log_level, message)
|
|
72
|
+
end
|
|
73
|
+
end
|
|
74
|
+
def loggable?
|
|
75
|
+
return @loggable if defined?(@loggable)
|
|
76
|
+
@loggable = logger.send("#{log_level}?")
|
|
77
|
+
end
|
|
78
|
+
def benchmarkable_for?(benchmarks)
|
|
79
|
+
return @benchmarkable if defined?(@benchmarkable)
|
|
80
|
+
@benchmarkable = loggable? && self.send(benchmarks)
|
|
81
|
+
end
|
|
82
|
+
def exit_scope_markable?
|
|
83
|
+
return @exit_scope_markable if defined?(@exit_scope_markable)
|
|
84
|
+
@exit_scope_markable = loggable? && mark_scope_exit
|
|
59
85
|
end
|
|
60
86
|
def instance_benchmarks=(instance_benchmarks)
|
|
61
87
|
require "benchmark" if instance_benchmarks
|
|
@@ -81,5 +107,8 @@ module DebugLogging
|
|
|
81
107
|
ellipsis: ellipsis
|
|
82
108
|
}
|
|
83
109
|
end
|
|
110
|
+
def register(method_lo_log)
|
|
111
|
+
@methods_to_log << method_lo_log
|
|
112
|
+
end
|
|
84
113
|
end
|
|
85
114
|
end
|
|
@@ -4,7 +4,6 @@ module DebugLogging
|
|
|
4
4
|
Module.new do
|
|
5
5
|
Array(methods_to_log).each do |method_to_log|
|
|
6
6
|
# method name must be a symbol
|
|
7
|
-
|
|
8
7
|
define_method(method_to_log.to_sym) do |*args, &block|
|
|
9
8
|
method_return_value = nil
|
|
10
9
|
config_proxy = if (proxy = instance_variable_get("@debug_config_proxy_for_#{method_to_log}".to_sym))
|
|
@@ -13,23 +12,32 @@ module DebugLogging
|
|
|
13
12
|
proxy = if config
|
|
14
13
|
Configuration.new(**(self.class.debug_config.to_hash.merge(config)))
|
|
15
14
|
else
|
|
16
|
-
self.class
|
|
15
|
+
self.class.debug_config
|
|
17
16
|
end
|
|
17
|
+
proxy.register(method_to_log)
|
|
18
18
|
instance_variable_set("@debug_config_proxy_for_#{method_to_log}".to_sym, proxy)
|
|
19
19
|
proxy
|
|
20
20
|
end
|
|
21
|
-
# TODO: Put all the logic into a logger block, so it will never be computed at runtime if the log level is too high
|
|
22
21
|
log_prefix = self.class.debug_invocation_to_s(klass: self.class.to_s, separator: "#", method_to_log: method_to_log, config_proxy: config_proxy)
|
|
23
|
-
signature = self.class.debug_signature_to_s(args: args, config_proxy: config_proxy)
|
|
24
22
|
invocation_id = self.class.debug_invocation_id_to_s(args: args, config_proxy: config_proxy)
|
|
25
|
-
|
|
26
|
-
|
|
23
|
+
config_proxy.log do
|
|
24
|
+
signature = self.class.debug_signature_to_s(args: args, config_proxy: config_proxy)
|
|
25
|
+
"#{log_prefix}#{signature}#{invocation_id}"
|
|
26
|
+
end
|
|
27
|
+
if config_proxy.benchmarkable_for?(:debug_instance_benchmarks)
|
|
27
28
|
tms = Benchmark.measure do
|
|
28
29
|
method_return_value = super(*args, &block)
|
|
29
30
|
end
|
|
30
|
-
|
|
31
|
+
config_proxy.log do
|
|
32
|
+
"#{log_prefix} #{self.class.debug_benchmark_to_s(tms: tms)}#{invocation_id}"
|
|
33
|
+
end
|
|
31
34
|
else
|
|
32
35
|
method_return_value = super(*args, &block)
|
|
36
|
+
if config_proxy.exit_scope_markable? && invocation_id && !invocation_id.empty?
|
|
37
|
+
config_proxy.log do
|
|
38
|
+
"#{log_prefix} completed#{invocation_id}"
|
|
39
|
+
end
|
|
40
|
+
end
|
|
33
41
|
end
|
|
34
42
|
method_return_value
|
|
35
43
|
end
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: debug_logging
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.0.
|
|
4
|
+
version: 1.0.12
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Peter Boling
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2017-10-
|
|
11
|
+
date: 2017-10-08 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: colorize
|
|
@@ -94,6 +94,20 @@ dependencies:
|
|
|
94
94
|
- - "~>"
|
|
95
95
|
- !ruby/object:Gem::Version
|
|
96
96
|
version: '3.0'
|
|
97
|
+
- !ruby/object:Gem::Dependency
|
|
98
|
+
name: activesupport
|
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
|
100
|
+
requirements:
|
|
101
|
+
- - "~>"
|
|
102
|
+
- !ruby/object:Gem::Version
|
|
103
|
+
version: '5.1'
|
|
104
|
+
type: :development
|
|
105
|
+
prerelease: false
|
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
107
|
+
requirements:
|
|
108
|
+
- - "~>"
|
|
109
|
+
- !ruby/object:Gem::Version
|
|
110
|
+
version: '5.1'
|
|
97
111
|
description: |2
|
|
98
112
|
|
|
99
113
|
Unobtrusive debug logging for Ruby. NO LITTERING.
|