easy_app_helper 0.0.9 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +376 -172
- data/lib/easy_app_helper/core/base.rb +123 -0
- data/lib/easy_app_helper/core/config.rb +203 -0
- data/lib/easy_app_helper/core/logger.rb +101 -0
- data/lib/easy_app_helper/core/merge_policies.rb +37 -0
- data/lib/easy_app_helper/core/places.rb +52 -0
- data/lib/easy_app_helper/module_manager.rb +61 -0
- data/lib/easy_app_helper/version.rb +1 -2
- data/lib/easy_app_helper.rb +8 -13
- data/test/test.yml +7 -0
- data/test/test2_app.rb +33 -0
- data/test/test3_app.rb +90 -0
- data/test/test4_app.rb +36 -0
- data/test/test_app.rb +56 -0
- metadata +19 -8
- data/lib/easy_app_helper/base.rb +0 -211
- data/lib/easy_app_helper/common.rb +0 -88
- data/lib/easy_app_helper/config.rb +0 -129
- data/lib/easy_app_helper/logger.rb +0 -104
- data/lib/easy_app_helper/places.rb +0 -42
@@ -1,88 +0,0 @@
|
|
1
|
-
################################################################################
|
2
|
-
# EasyAppHelper
|
3
|
-
#
|
4
|
-
# Copyright (c) 2013 L.Briais under MIT license
|
5
|
-
# http://opensource.org/licenses/MIT
|
6
|
-
################################################################################
|
7
|
-
|
8
|
-
require 'singleton'
|
9
|
-
require 'logger'
|
10
|
-
|
11
|
-
##
|
12
|
-
# This contains very basic default values and methods.
|
13
|
-
#
|
14
|
-
module EasyAppHelper::Common
|
15
|
-
|
16
|
-
# Default log-level
|
17
|
-
DEFAULT_LOG_LEVEL = Logger::Severity::WARN
|
18
|
-
|
19
|
-
def self.override_config(h1, h2)
|
20
|
-
EasyAppHelper::Common::HashesMergePolicies.merge_hashes_second_level h1, h2
|
21
|
-
end
|
22
|
-
|
23
|
-
end
|
24
|
-
|
25
|
-
|
26
|
-
# Ancestor of all module instanciators.
|
27
|
-
module EasyAppHelper::Common::Instanciator
|
28
|
-
# Default module priority
|
29
|
-
MODULE_PRIORITY = 10000
|
30
|
-
|
31
|
-
def self.add_cmd_line_options(app, opt)
|
32
|
-
# Does nothing
|
33
|
-
end
|
34
|
-
|
35
|
-
def self.provides_config(app, script_filename, app_name, app_description, app_version)
|
36
|
-
# Does nothing
|
37
|
-
{}
|
38
|
-
end
|
39
|
-
|
40
|
-
def self.post_config_action(app)
|
41
|
-
# Does nothing
|
42
|
-
end
|
43
|
-
end
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
# This guy will never log something anywhere... :)
|
50
|
-
# It mays be used as the logger until someone replaces by a real one
|
51
|
-
# EasyAppHelper::Logger would do that efficiently
|
52
|
-
class EasyAppHelper::Common::DummyLogger
|
53
|
-
include Singleton
|
54
|
-
def method_missing(method_name, *args, &block)
|
55
|
-
# Do nothing !
|
56
|
-
end
|
57
|
-
end
|
58
|
-
|
59
|
-
# Implements different merge policies for the configs.
|
60
|
-
module EasyAppHelper::Common::HashesMergePolicies
|
61
|
-
# Performs a merge at the second level of hashes.
|
62
|
-
# simple entries and arrays are overriden.
|
63
|
-
def self.merge_hashes_second_level(h1, h2)
|
64
|
-
h2.each do |key, v|
|
65
|
-
if h1[key] and h1[key].is_a?(Hash)
|
66
|
-
# Merges hashes
|
67
|
-
h1[key].merge! h2[key]
|
68
|
-
else
|
69
|
-
# Overrides the rest
|
70
|
-
h1[key] = h2[key] unless h2[key].nil?
|
71
|
-
end
|
72
|
-
end
|
73
|
-
h1
|
74
|
-
end
|
75
|
-
|
76
|
-
# Uses the standard "merge!" method
|
77
|
-
def self.simple_merge(h1, h2)
|
78
|
-
h1.merge! h2
|
79
|
-
end
|
80
|
-
|
81
|
-
# Brutal override
|
82
|
-
def self.complete_override(h1, h2)
|
83
|
-
h1 = nil
|
84
|
-
h1 = h2
|
85
|
-
|
86
|
-
end
|
87
|
-
|
88
|
-
end
|
@@ -1,129 +0,0 @@
|
|
1
|
-
################################################################################
|
2
|
-
# EasyAppHelper
|
3
|
-
#
|
4
|
-
# Copyright (c) 2013 L.Briais under MIT license
|
5
|
-
# http://opensource.org/licenses/MIT
|
6
|
-
################################################################################
|
7
|
-
|
8
|
-
# Config file format
|
9
|
-
require 'yaml'
|
10
|
-
|
11
|
-
# This module defines:
|
12
|
-
# - Some basic command line options(see --help), with their underlying
|
13
|
-
# mechanism.
|
14
|
-
# - A mechanism (based on Slop) to add your own command line options.
|
15
|
-
# - A generated inline help.
|
16
|
-
# This module provides the following 5 levels of configuration:
|
17
|
-
# - Admin wide YAML config file, for options common to all your EasyAppHelper applications.
|
18
|
-
# - System wide YAML config file.
|
19
|
-
# - User YAML config file.
|
20
|
-
# These 3 levels depends on you OS (see EasyAppHelper::Config::Places).
|
21
|
-
# - Command line options.
|
22
|
-
# - Command line supplied YAML config file(any option defined here will override the previous).
|
23
|
-
# All these 5 levels of configuration override with consistent override mechanism.
|
24
|
-
# Config files are in YAML but can have different extensions.
|
25
|
-
module EasyAppHelper::Config
|
26
|
-
|
27
|
-
include EasyAppHelper::Common
|
28
|
-
|
29
|
-
# If the option --config-file has been specified, it will be loaded and override
|
30
|
-
# current configuration according to rules
|
31
|
-
def load_custom_config
|
32
|
-
end
|
33
|
-
|
34
|
-
end
|
35
|
-
|
36
|
-
|
37
|
-
module EasyAppHelper::Config::Instanciator
|
38
|
-
extend EasyAppHelper::Common::Instanciator
|
39
|
-
|
40
|
-
# Default module priority
|
41
|
-
MODULE_PRIORITY = 10
|
42
|
-
ADMIN_CONFIG_FILENAME = EasyAppHelper.name
|
43
|
-
|
44
|
-
# include paths specific to the OS
|
45
|
-
include EasyAppHelper::Config::Places.get_OS_module
|
46
|
-
|
47
|
-
# Potential extensions a config file can have
|
48
|
-
CONFIG_FILE_POSSIBLE_EXTENSIONS = ['conf', 'yml', 'cfg', 'yaml', 'CFG', 'YML', 'YAML', 'Yaml']
|
49
|
-
|
50
|
-
# Adds a command line options for this module.
|
51
|
-
# - +--config-file+ +filename+ To specify a config file from the command line.
|
52
|
-
def self.add_cmd_line_options(app, slop_definition)
|
53
|
-
slop_definition.separator "\n-- Configuration options -------------------------------------"
|
54
|
-
slop_definition.on 'config-file', 'Specify a config file.', :argument => true
|
55
|
-
end
|
56
|
-
|
57
|
-
|
58
|
-
# Loads the configuration files (admin, system, user).
|
59
|
-
#
|
60
|
-
# Config files may define any type of structure supported by YAML.
|
61
|
-
# The override policy is that, if an entry in the config is a hash and the next
|
62
|
-
# level defines the same hash, they are merged.
|
63
|
-
# For any other type (scalar, array), the overrider... overrides ;)
|
64
|
-
#
|
65
|
-
# Config files can be at different places and have different extensions (see
|
66
|
-
# CONFIG_FILE_POSSIBLE_EXTENSIONS). They have the same base name as the script_filename.
|
67
|
-
def self.provides_config(app, script_filename, app_name, app_description, app_version)
|
68
|
-
config = load_admin_wide_config app
|
69
|
-
config = EasyAppHelper::Common.override_config config, load_system_wide_config(app, script_filename)
|
70
|
-
EasyAppHelper::Common.override_config config, load_user_config(app, script_filename)
|
71
|
-
end
|
72
|
-
|
73
|
-
def self.post_config_action(app)
|
74
|
-
return unless app.app_config[:'config-file']
|
75
|
-
begin
|
76
|
-
app.app_config = EasyAppHelper::Common.override_config app.app_config, load_config_file(app, app.app_config[:'config-file'])
|
77
|
-
rescue => e
|
78
|
-
app.logger.error "Problem with \"#{app.app_config[:'config-file']}\" config file!\n#{e.message}\nIgnoring..."
|
79
|
-
end
|
80
|
-
end
|
81
|
-
|
82
|
-
################################################################################
|
83
|
-
private
|
84
|
-
|
85
|
-
# Reads config from admin config file.
|
86
|
-
def self.load_admin_wide_config(app)
|
87
|
-
load_config_file app, find_file(app, ADMIN_CONFIG_POSSIBLE_PLACES, ADMIN_CONFIG_FILENAME)
|
88
|
-
end
|
89
|
-
|
90
|
-
# Reads config from system config file.
|
91
|
-
def self.load_system_wide_config(app, script_filename)
|
92
|
-
load_config_file app, find_file(app, SYSTEM_CONFIG_POSSIBLE_PLACES, script_filename)
|
93
|
-
end
|
94
|
-
|
95
|
-
# Reads config from user config file.
|
96
|
-
def self.load_user_config(app, script_filename)
|
97
|
-
load_config_file app, find_file(app, USER_CONFIG_POSSIBLE_PLACES, script_filename)
|
98
|
-
end
|
99
|
-
|
100
|
-
# Loads a config file.
|
101
|
-
def self.load_config_file(app, conf_filename)
|
102
|
-
conf = {}
|
103
|
-
return conf if conf_filename.nil?
|
104
|
-
# A file exists
|
105
|
-
begin
|
106
|
-
app.logger.debug "Loading config file \"#{conf_filename}\""
|
107
|
-
conf = Hash[YAML::load(open(conf_filename)).map { |k, v| [k.to_sym, v] }]
|
108
|
-
rescue => e
|
109
|
-
app.logger.error "Invalid config file \"#{conf_filename}\". Not respecting YAML syntax!\n#{e.message}"
|
110
|
-
end
|
111
|
-
conf
|
112
|
-
end
|
113
|
-
|
114
|
-
# Tries to find config files according to places (array) given and possible extensions
|
115
|
-
def self.find_file(app, places, filename)
|
116
|
-
places.each do |dir|
|
117
|
-
CONFIG_FILE_POSSIBLE_EXTENSIONS.each do |ext|
|
118
|
-
filename_with_path = dir + '/' + filename + '.' + ext
|
119
|
-
if File.exists? filename_with_path
|
120
|
-
return filename_with_path
|
121
|
-
else
|
122
|
-
app.logger.debug "Trying \"#{filename_with_path}\" as config file."
|
123
|
-
end
|
124
|
-
end
|
125
|
-
end
|
126
|
-
nil
|
127
|
-
end
|
128
|
-
|
129
|
-
end
|
@@ -1,104 +0,0 @@
|
|
1
|
-
################################################################################
|
2
|
-
# EasyAppHelper
|
3
|
-
#
|
4
|
-
# Copyright (c) 2013 L.Briais under MIT license
|
5
|
-
# http://opensource.org/licenses/MIT
|
6
|
-
################################################################################
|
7
|
-
|
8
|
-
require 'logger'
|
9
|
-
|
10
|
-
|
11
|
-
# This module provides access to logger(Logger) fully configured according to command line options
|
12
|
-
# or config files.
|
13
|
-
#
|
14
|
-
# It will replace the stupid EasyAppHelper::Common::DummyLogger if the
|
15
|
-
# module is included.
|
16
|
-
#
|
17
|
-
# It brings as well some command line options to manipulate debug.
|
18
|
-
# See --help
|
19
|
-
module EasyAppHelper::Logger
|
20
|
-
|
21
|
-
# This module has the highest priority in order to be processed the first by
|
22
|
-
# the framework and therefore give a chance to other modules to use it to log.
|
23
|
-
MODULE_PRIORITY = 1
|
24
|
-
|
25
|
-
include EasyAppHelper::Common
|
26
|
-
|
27
|
-
|
28
|
-
# Returns the current log_level.
|
29
|
-
def log_level
|
30
|
-
app_config[:"log-level"]
|
31
|
-
end
|
32
|
-
|
33
|
-
# Enables to hot-change the log level.
|
34
|
-
def log_level=(level)
|
35
|
-
app_config[:"log-level"] = level
|
36
|
-
logger.level = level
|
37
|
-
end
|
38
|
-
|
39
|
-
def logger=(logger)
|
40
|
-
@logger = logger
|
41
|
-
end
|
42
|
-
|
43
|
-
# Displays the message according to application verbosity and logs it as info.
|
44
|
-
def puts_and_logs(msg)
|
45
|
-
puts msg if app_config[:verbose]
|
46
|
-
logger.info(msg)
|
47
|
-
end
|
48
|
-
|
49
|
-
|
50
|
-
end
|
51
|
-
|
52
|
-
|
53
|
-
module EasyAppHelper::Logger::Instanciator
|
54
|
-
extend EasyAppHelper::Common::Instanciator
|
55
|
-
|
56
|
-
# Default module priority
|
57
|
-
MODULE_PRIORITY = 1
|
58
|
-
|
59
|
-
# Adds some command line options for this module.
|
60
|
-
# - +--debug+
|
61
|
-
# - +--debug-on-err+ to have the debugging going to STDERR. Should be used on top of
|
62
|
-
# --debug.
|
63
|
-
# - +--log-file+ +filename+ To log to a specific file.
|
64
|
-
# - +--log-level+ +0-5+ Log level according to Logger::Severity
|
65
|
-
def self.add_cmd_line_options(app, slop_definition)
|
66
|
-
slop_definition.separator "\n-- Debug and logging options ---------------------------------"
|
67
|
-
slop_definition.on :debug, 'Run in debug mode.', :argument => false
|
68
|
-
slop_definition.on 'debug-on-err', 'Run in debug mode with output to stderr.', :argument => false
|
69
|
-
slop_definition.on 'log-level', "Log level from 0 to 5, default #{EasyAppHelper::Common::DEFAULT_LOG_LEVEL}.", :argument => true, :as => Integer
|
70
|
-
slop_definition.on 'log-file', 'File to log to.', :argument => true
|
71
|
-
end
|
72
|
-
|
73
|
-
# Creates the application logger
|
74
|
-
def self.post_config_action(app)
|
75
|
-
# Build logger for the application. Depending on config may end-up up to nowhere
|
76
|
-
# (by default), STDOUT, STDERR or a file. See --help or EasyAppHelper::Config#help
|
77
|
-
# for all options.
|
78
|
-
@logger = EasyAppHelper::Common::DummyLogger.instance
|
79
|
-
issue_report = nil
|
80
|
-
if app.app_config[:debug]
|
81
|
-
unless app.app_config[:"log-file"].nil?
|
82
|
-
begin
|
83
|
-
if File.exists? app.app_config[:"log-file"]
|
84
|
-
logger_type = File.open(app.app_config[:"log-file"], File::WRONLY | File::APPEND)
|
85
|
-
else
|
86
|
-
logger_type = File.open(app.app_config[:"log-file"], File::WRONLY | File::CREAT)
|
87
|
-
end
|
88
|
-
rescue Exception => e
|
89
|
-
logger_type = STDOUT
|
90
|
-
issue_report = e.message
|
91
|
-
end
|
92
|
-
else
|
93
|
-
logger_type = STDOUT
|
94
|
-
end
|
95
|
-
logger_type = STDERR if app.app_config[:"debug-on-err"]
|
96
|
-
app.logger = Logger.new(logger_type)
|
97
|
-
end
|
98
|
-
app.app_config[:'log-level'] = EasyAppHelper::Common::DEFAULT_LOG_LEVEL if app.app_config[:'log-level'].nil?
|
99
|
-
app.logger.level = app.app_config[:"log-level"]
|
100
|
-
app.logger.error issue_report if issue_report
|
101
|
-
app.logger.debug "Logger is created."
|
102
|
-
end
|
103
|
-
|
104
|
-
end
|
@@ -1,42 +0,0 @@
|
|
1
|
-
|
2
|
-
module EasyAppHelper
|
3
|
-
module Config
|
4
|
-
module UnixPlaces
|
5
|
-
# Where could be stored admin configuration that rules all EasyAppHelper
|
6
|
-
# based applications.
|
7
|
-
ADMIN_CONFIG_POSSIBLE_PLACES = ["/etc"]
|
8
|
-
|
9
|
-
# Where could be stored system wide configuration
|
10
|
-
SYSTEM_CONFIG_POSSIBLE_PLACES = ["/etc",
|
11
|
-
"/usr/local/etc"]
|
12
|
-
|
13
|
-
# Where could be stored user configuration
|
14
|
-
USER_CONFIG_POSSIBLE_PLACES = ["#{ENV['HOME']}/.config"]
|
15
|
-
end
|
16
|
-
|
17
|
-
module WindowsPlaces
|
18
|
-
# Where could be stored admin configuration that rules all EasyAppHelper
|
19
|
-
# based applications.
|
20
|
-
ADMIN_CONFIG_POSSIBLE_PLACES = ["#{ENV['systemRoot']}/Config"]
|
21
|
-
|
22
|
-
# Where could be stored system wide configuration
|
23
|
-
SYSTEM_CONFIG_POSSIBLE_PLACES = ['C:/Windows/Config', "#{ENV['ALLUSERSPROFILE']}/Application Data"]
|
24
|
-
|
25
|
-
# Where could be stored user configuration
|
26
|
-
USER_CONFIG_POSSIBLE_PLACES = [ENV['APPDATA']]
|
27
|
-
end
|
28
|
-
|
29
|
-
module Places
|
30
|
-
CONF ={
|
31
|
-
mingw32: EasyAppHelper::Config::WindowsPlaces
|
32
|
-
}
|
33
|
-
DEFAULT = EasyAppHelper::Config::UnixPlaces
|
34
|
-
|
35
|
-
def self.get_OS_module
|
36
|
-
conf = CONF[RbConfig::CONFIG['target_os'].to_sym]
|
37
|
-
conf.nil? ? DEFAULT : conf
|
38
|
-
end
|
39
|
-
end
|
40
|
-
end
|
41
|
-
end
|
42
|
-
|