alog 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 5c99568a04040e5467af6aa0230606d1b3e7e6d12a19da083ce27574a12a67a1
4
+ data.tar.gz: a0f6cfa695a5b1b1874eb2a55cfa88804f1ceccbe34b6e2c07254a01309508ad
5
+ SHA512:
6
+ metadata.gz: c08f58b90258819bc35b63a40da82aa126645d976edb5b2a625c532dcaf9e44bfecc14b8e4d33915f53c7c6ed25ea8ca842e3f77112589d0987f76238a761cbb
7
+ data.tar.gz: 921a75bed5bfb7b861e3bc27fa2bfeb87394055f44c18c8133da03c34b7c0da9d9158cfe8d1bead17f55dc2d1cbe05f86b427ce37dc79b5753c158edbed636c9
data/.gitignore ADDED
@@ -0,0 +1,8 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "https://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in alog.gemspec
4
+ gemspec
data/Gemfile.lock ADDED
@@ -0,0 +1,20 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ alog (0.1.0)
5
+
6
+ GEM
7
+ remote: https://rubygems.org/
8
+ specs:
9
+ rake (10.5.0)
10
+
11
+ PLATFORMS
12
+ ruby
13
+
14
+ DEPENDENCIES
15
+ alog!
16
+ bundler (~> 2.0)
17
+ rake (~> 10.0)
18
+
19
+ BUNDLED WITH
20
+ 2.0.1
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2019 Chris Liaw
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,141 @@
1
+ # Alog
2
+
3
+ Alog (Advanced/Antrapol Logging) is an attempt to tackle the logging issue that is too verbose.
4
+
5
+ Logging is better to be verbose but when working on large project, the development is evolution type of progress instead of revolution. Hence the logging output tends to be increasing over the time of development. Those logging generated during the early stage of the development may not be siginificant in later development work.
6
+
7
+ In other framework there is conditional logging like #IFDEF in C to ignore logging if a key is not defined.
8
+
9
+ This conditional logging however is not related to the log level (DEBUG, ERROR etc) as defined by the log engine.
10
+
11
+ Alog is meant to be allow developer to group the logging under a meaningful tag and if the tag is not defined, the log is skipped therefore removing the log entirely out from the view of the developer and left only the current focusing development work's log.
12
+
13
+ ## Installation
14
+
15
+ Add this line to your application's Gemfile:
16
+
17
+ ```ruby
18
+ gem 'alog'
19
+ ```
20
+
21
+ And then execute:
22
+
23
+ $ bundle
24
+
25
+ Or install it yourself as:
26
+
27
+ $ gem install alog
28
+
29
+ ## Usage
30
+
31
+ First is to include the alog library
32
+ ```ruby
33
+ require 'alog'
34
+ ```
35
+
36
+ Include the namespace into your class and configure the tag that you want the library to show/display.
37
+ Any tag that is not configured will be skipped
38
+
39
+ ```ruby
40
+ class MyApp
41
+ include Alog
42
+
43
+ # STEP 1: Configuration
44
+ #
45
+ # Configure logger and bind the logger to a key
46
+ # Whatever on the right side shall be passed to the standard library Logger object
47
+ # The array construct is necesary because *args is used in
48
+ # passing the parameters to actual standard library Logger object via new()
49
+ LogFacts[:stdout] = [STDOUT]
50
+ # Also multiple loggers can be configured by creating multiple keys
51
+ LogFacts[:app_file] = ['app.log',10, 1024000]
52
+ ...
53
+
54
+ # STEP 2: Define which keys to activate
55
+ # Any block/log output tagged by the key included in this array shall be printed
56
+ LogTag << :feature_1
57
+ LogTag << :feature_2
58
+ ...
59
+ # Any tag that is not configured inside the LogTag will not be printed out
60
+ # If the list is empty, no log under the library shall be printed.
61
+ # Or there is more then dozens tags and want to show all, use this method
62
+ show_all_tags
63
+
64
+
65
+ # STEP 3: Create the logging
66
+ def my_method(p1, p2)
67
+ # Method 1: block logging
68
+ l(:feature_1, type: :debug, logEng: [:stdout]) do
69
+ # All clog() call inside this block will be tagged with key :feature_1
70
+ # enabling the key :feature_1 shall show all log messages inside this block or disabling otherwise
71
+ ...
72
+ ...
73
+ # If only message is given, the following is the default:
74
+ # 1. The system shall use the first logger, in this case it will be using logger with key :stdout
75
+ # 2. The logger will use debug level to log the message
76
+ # (System will use log level debug if the log level is not given in the l() above via key 'type'.
77
+ clog "This is logging message"
78
+ ...
79
+ ...
80
+ # If the message and tag is given
81
+ # 1. The tag shall override the global configuration of logging level debug (to whatever level given by developer)
82
+ # Note that 'error' logging level will ignore the tag-skipping feature since error conditions (and its messages) will likely
83
+ # affect the subsequent code/logic of a system. Therefore 'error' will always be printed.
84
+ clog "Error in defining X", :error
85
+ clog "Reach here means ok", :info
86
+
87
+ # Asking the Alogger to write to other logger at the same time,
88
+ # overriding the parameter given in the l().
89
+ clog "This will written to both :stdout and :app_file", logEng: [:stdout,:app_file]
90
+ ...
91
+ ...
92
+ end
93
+
94
+ (business logic continues...)
95
+ ...
96
+ ...
97
+ # Method 2: Call clog() directly
98
+ # Param 1 : Log messages
99
+ # Param 2 : Log level [:debug|:info|:error] (empty = :debug)
100
+ # Param 3 : Tag of the log message (empty = :global)
101
+ # Param 4 : Log engine to be used (refers to LogFacts hash entries above) (empty = first LogFacts key)
102
+ clog("Business continue up to level 2", :debug, :feature_2, [:stdout])
103
+ ...
104
+
105
+ end
106
+
107
+ def my_method2(p2)
108
+ # Method 3 : Create the AOlogger object
109
+ # AOlogger is meant to be proxy for standard Logger, with the tagging and multiple log engines included
110
+ # The initialize parameter is an array containing key to the LogFacts above...
111
+ # In the following case, the AOlogger shall only configured to :stdout configuration (refers above)
112
+ @log = AOlogger.new([:stdout])
113
+ ...
114
+ ...
115
+ # This behave like standard logging engine
116
+ @log.debug "Code reached here..."
117
+ ...
118
+ @log.error "Oppss... We did it again!"
119
+ ...
120
+ ...
121
+ # This allow application to participate in the conditional logging
122
+ # If the tag :feature_x is not activated, the message will not be printed.
123
+ @log.log("this only shown if tag :feature_x is activated", :debug, :feature_x, [:app_file])
124
+
125
+ end
126
+
127
+ end
128
+ ```
129
+
130
+
131
+ ## TODO
132
+
133
+ Library not yet tested extensively under multi-threaded applications. Some variables may not be thread safe.
134
+
135
+ ## Contributing
136
+
137
+ Bug reports and pull requests are welcome on GitHub at https://github.com/chrisliaw/alog.
138
+
139
+ ## License
140
+
141
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require "bundler/gem_tasks"
2
+ task :default => :spec
data/alog.gemspec ADDED
@@ -0,0 +1,41 @@
1
+
2
+ lib = File.expand_path("../lib", __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require "alog/version"
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "alog"
8
+ spec.version = Alog::VERSION
9
+ spec.authors = ["Chris Liaw"]
10
+ spec.email = ["chrisliaw@antrapol.com"]
11
+
12
+ spec.summary = %q{Conditional logging to provide contextual logging and ability to reconfigure log message visibility during runtime}
13
+ spec.description = %q{Allow contextual log output to ease developer in log management}
14
+ spec.homepage = "https://github.com/chrisliaw/alog"
15
+ spec.license = "MIT"
16
+
17
+ # Prevent pushing this gem to RubyGems.org. To allow pushes either set the 'allowed_push_host'
18
+ # to allow pushing to a single host or delete this section to allow pushing to any host.
19
+ #if spec.respond_to?(:metadata)
20
+ # spec.metadata["allowed_push_host"] = "TODO: Set to 'http://mygemserver.com'"
21
+
22
+ # spec.metadata["homepage_uri"] = spec.homepage
23
+ # spec.metadata["source_code_uri"] = "TODO: Put your gem's public repo URL here."
24
+ # spec.metadata["changelog_uri"] = "TODO: Put your gem's CHANGELOG.md URL here."
25
+ #else
26
+ # raise "RubyGems 2.0 or newer is required to protect against " \
27
+ # "public gem pushes."
28
+ #end
29
+
30
+ # Specify which files should be added to the gem when it is released.
31
+ # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
32
+ spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
33
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
34
+ end
35
+ spec.bindir = "exe"
36
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
37
+ spec.require_paths = ["lib"]
38
+
39
+ spec.add_development_dependency "bundler", "~> 2.0"
40
+ spec.add_development_dependency "rake", "~> 10.0"
41
+ end
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "alog"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,3 @@
1
+ module Alog
2
+ VERSION = "0.1.0"
3
+ end
data/lib/alog.rb ADDED
@@ -0,0 +1,166 @@
1
+ require "alog/version"
2
+
3
+ require 'logger'
4
+
5
+ module Alog
6
+ class AlogException < StandardError; end
7
+
8
+ # allow application to provide which tag should print out
9
+ LogTag = [:global]
10
+
11
+ # allow application to configure multiple logging
12
+ # log factories configurations
13
+ LogFacts = {}
14
+
15
+ # multi logger created from
16
+ # LogFacts entry given by application
17
+ GLog = {}
18
+
19
+ #
20
+ # class Alogger
21
+ # Inherited from standard library Logger
22
+ #
23
+ class Alogger < Logger
24
+ def initialize(args)
25
+ @log = Logger.new(*args)
26
+ end
27
+
28
+ def log(msg, type = :debug, &block)
29
+ @log.send(type, msg)
30
+ end
31
+ end
32
+ # end class Alogger
33
+ #
34
+
35
+ #
36
+ # class AloggerObject
37
+ # Mimiking the original Logger object
38
+ # to be used by application but with
39
+ # the conditioning logging logic available
40
+ # to the application instead
41
+ #
42
+ class AOlogger
43
+ attr_reader :logEng
44
+ def initialize(logEng = [])
45
+ @myMethods = [:debug, :error, :warn, :warning]
46
+ @logEng = logEng || []
47
+ end
48
+
49
+ def log(msg, ltype = :debug, key = :global, logEng = [])
50
+ CondLog.call(msg, { key: key, type: ltype, logEng: logEng || @logEng })
51
+ end
52
+
53
+ def method_missing(mtd, *args, &block)
54
+ if @myMethods.include?(mtd)
55
+ params = {}
56
+ pa = args[1]
57
+ params[:key] = :global
58
+ params[:logEng] = @logEng
59
+ # TODO cases here may not be extensive to
60
+ # the original Logger supported.
61
+ case mtd
62
+ when :debug
63
+ params[:type] = :debug
64
+ CondLog.call(args[0], params, &block)
65
+ when :error
66
+ params[:type] = :error
67
+ CondLog.call(args[0], params, &block)
68
+ when :warn, :warning
69
+ params[:type] = :warn
70
+ CondLog.call(args[0], params, &block)
71
+ end
72
+
73
+ else
74
+ super
75
+ end
76
+ end
77
+ end
78
+ #
79
+ # end class AloggerObject
80
+ #
81
+
82
+ def show_all_tags
83
+ LogTag << :all
84
+ end
85
+
86
+ def selected_tags_only
87
+ LogTag.delete(:all)
88
+ end
89
+
90
+ #
91
+ # Provide a block construct that can set values consistantly for multiple clog() call
92
+ # TODO How to make this thread safe?
93
+ #
94
+ def l(key = :global, params = { type: :debug, logEng: [] } ,&block)
95
+ # this construct try to make the variable private to the block
96
+ # Still not sure will error condition exist for multi threaded application
97
+ b = Proc.new do |key, params, &block|
98
+ @lKey = key
99
+ @lType = params[:type]
100
+ @llEng = params[:logEng]
101
+ if block
102
+ block.call
103
+ end
104
+ end
105
+ b.call(key, params, &block)
106
+ end
107
+
108
+ #
109
+ # Module level clog() method
110
+ # Meant to be called by application INSIDE the l()'s block
111
+ #
112
+ def clog(msg, ltype = :debug, key = :global, logEng = [])
113
+ log(msg, { type: @lType != ltype ? ltype : @lType,
114
+ key: (key == @lKey ? key : @lKey),
115
+ logEng: @llEng })
116
+ end
117
+ #
118
+ # end of module level clob()
119
+ #
120
+
121
+ #
122
+ # Actual logic of detecting a tag should be activated and on which logger should it written to
123
+ #
124
+ CondLog = Proc.new do |msg, params = {}, &block|
125
+ key = params[:key] || :global
126
+ type = params[:type] || :debug
127
+ if defined?(:LogTag) and LogTag.is_a?(Array) and (LogTag.include?(key) or LogTag.include?(:all)) or type == :error
128
+ logEng = params[:logEng]
129
+ if logEng == nil or (logEng != nil and logEng.empty?)
130
+ logEng = (LogFacts.length > 0 ? [LogFacts.keys[0]] : [:default])
131
+ end
132
+
133
+ logEng = [logEng] if not logEng.is_a?(Array)
134
+
135
+ # allow written to multiple logger
136
+ logEng.each do |e|
137
+
138
+ if GLog[e] == nil
139
+
140
+ lp = LogFacts[e]
141
+ if lp == nil
142
+ # default if empty
143
+ lp = [STDOUT]
144
+ end
145
+
146
+ # ensure the same configuration only created a logger object once
147
+ GLog[e] = Alogger.new(lp)
148
+
149
+ end
150
+
151
+ GLog[e].log("#{caller.length > 3 ? "[#{File.basename(caller[4])}]" : ""} [#{key}] #{msg}", type, &block)
152
+ end
153
+
154
+ end
155
+
156
+ end
157
+ # end CondLog() proc
158
+ #
159
+
160
+ # provide module level method to write to the logger object
161
+ def log(msg, params = { }, &block)
162
+ CondLog.call(msg, params, &block)
163
+ end
164
+ # end module level log()
165
+
166
+ end
metadata ADDED
@@ -0,0 +1,84 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: alog
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Chris Liaw
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2019-03-17 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: bundler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '2.0'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '2.0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '10.0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '10.0'
41
+ description: Allow contextual log output to ease developer in log management
42
+ email:
43
+ - chrisliaw@antrapol.com
44
+ executables: []
45
+ extensions: []
46
+ extra_rdoc_files: []
47
+ files:
48
+ - ".gitignore"
49
+ - Gemfile
50
+ - Gemfile.lock
51
+ - LICENSE.txt
52
+ - README.md
53
+ - Rakefile
54
+ - alog.gemspec
55
+ - bin/console
56
+ - bin/setup
57
+ - lib/alog.rb
58
+ - lib/alog/version.rb
59
+ homepage: https://github.com/chrisliaw/alog
60
+ licenses:
61
+ - MIT
62
+ metadata: {}
63
+ post_install_message:
64
+ rdoc_options: []
65
+ require_paths:
66
+ - lib
67
+ required_ruby_version: !ruby/object:Gem::Requirement
68
+ requirements:
69
+ - - ">="
70
+ - !ruby/object:Gem::Version
71
+ version: '0'
72
+ required_rubygems_version: !ruby/object:Gem::Requirement
73
+ requirements:
74
+ - - ">="
75
+ - !ruby/object:Gem::Version
76
+ version: '0'
77
+ requirements: []
78
+ rubyforge_project:
79
+ rubygems_version: 2.7.6
80
+ signing_key:
81
+ specification_version: 4
82
+ summary: Conditional logging to provide contextual logging and ability to reconfigure
83
+ log message visibility during runtime
84
+ test_files: []