jewelbox 0.0.2 → 0.0.3
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.
- data/LICENSE +2 -2
- data/README.md +1 -4
- data/lib/jewelbox.rb +2 -1
- data/lib/jewelbox/command.rb +179 -0
- data/lib/jewelbox/ext/string.rb +32 -0
- data/lib/jewelbox/version.rb +1 -1
- data/test/bin/myapp +44 -0
- metadata +8 -4
data/LICENSE
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
Copyright (c) 2012
|
1
|
+
Copyright (c) 2012 Steve Jang
|
2
2
|
|
3
3
|
MIT License
|
4
4
|
|
@@ -19,4 +19,4 @@ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
19
19
|
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
20
|
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
21
|
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
-
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
CHANGED
@@ -4,6 +4,7 @@ Useful Ruby utility classes that handle:
|
|
4
4
|
|
5
5
|
- configuration
|
6
6
|
- time stamp
|
7
|
+
- object serialization
|
7
8
|
|
8
9
|
## Installation
|
9
10
|
|
@@ -73,10 +74,6 @@ you might store your configuration in a YAML file under conf/ directory.
|
|
73
74
|
Jewelbox.config.service.log_dir => "/opt/myrailsapp/current/log"
|
74
75
|
Jewelbox.config.service.bin_dir => "/opt/myrailsapp/current/bin"
|
75
76
|
|
76
|
-
3. And my unicorn configuration looks like this:
|
77
|
-
|
78
|
-
TBD
|
79
|
-
|
80
77
|
## Contributing
|
81
78
|
|
82
79
|
1. Fork it
|
data/lib/jewelbox.rb
CHANGED
@@ -0,0 +1,179 @@
|
|
1
|
+
require 'jewelbox/ext/object'
|
2
|
+
require 'jewelbox/ext/string'
|
3
|
+
require 'optparse'
|
4
|
+
module Jewelbox
|
5
|
+
|
6
|
+
# === Description
|
7
|
+
# Simple wrapper around Ruby OptionParser to factor out common code that
|
8
|
+
# you have to repeat every time you write a command line tool. This is a
|
9
|
+
# simple wrapper. There is minimum additional functionality.
|
10
|
+
#
|
11
|
+
# === Example Code
|
12
|
+
# Creating a new command line tool or service runner.
|
13
|
+
#
|
14
|
+
# class MyApp < Jewelbox::Command
|
15
|
+
#
|
16
|
+
# class MyCustomException < RuntimeError; end
|
17
|
+
# exit_code 1, RuntimeError, "Unexpected error"
|
18
|
+
# exit_code 2, MyCustomException, "Some good explanation"
|
19
|
+
#
|
20
|
+
# def initialize
|
21
|
+
# @address = "default address"
|
22
|
+
# @name = "default name"
|
23
|
+
# @arg1 = ""
|
24
|
+
# @arg2 = ""
|
25
|
+
# end
|
26
|
+
#
|
27
|
+
# def define_options(opt)
|
28
|
+
# opt.banner = "Usage: #{opt.program_name} [options] arg1 arg2"
|
29
|
+
# opt.on("-a addr", "--address addr", String, "Address to work with") {|s| @address = s}
|
30
|
+
# opt.on("-n name", "--name name", String, "Name to work with") {|s| @name = s}
|
31
|
+
# end
|
32
|
+
#
|
33
|
+
# # Main entry point of the application
|
34
|
+
# #
|
35
|
+
# def main(argv)
|
36
|
+
# @arg1 = argv[0]
|
37
|
+
# @arg2 = argv[1]
|
38
|
+
# # write application code here
|
39
|
+
# end
|
40
|
+
#
|
41
|
+
# end
|
42
|
+
#
|
43
|
+
# MyApp.new.run
|
44
|
+
#
|
45
|
+
# === Help Output Example
|
46
|
+
# With the above example, you will get the following help text:
|
47
|
+
#
|
48
|
+
# Usage: myapp [options] arg1 arg2
|
49
|
+
# -a, --address addr Address to work with
|
50
|
+
# -n, --name name Name to work with
|
51
|
+
# -h, --help Display help
|
52
|
+
# -v, --verbose Verbose output
|
53
|
+
#
|
54
|
+
# Exit codes:
|
55
|
+
# 1 [RuntimeError] Unexpected error
|
56
|
+
# 2 [MyApp::MyCustomException] Some good explanation
|
57
|
+
#
|
58
|
+
# === Notes
|
59
|
+
#
|
60
|
+
# 1. The following options are automatically added.
|
61
|
+
# opt.on("-h", "--help", "Display help") { @help = true }
|
62
|
+
# opt.on("-v", "--verbose", "Verbose output") { @verbose = true }
|
63
|
+
#
|
64
|
+
# 2. You can map exception type to exit code by using exit_code method
|
65
|
+
# When exception happens during "run", we exit with the matching exit code (default = 1)
|
66
|
+
# Also, exception message + "[ERROR]" will be displayed to STDERR.
|
67
|
+
#
|
68
|
+
# 3. Make sure to override "define_options" and "main" methods.
|
69
|
+
#
|
70
|
+
class Command
|
71
|
+
@@exit_code_map = {}
|
72
|
+
|
73
|
+
# === Description
|
74
|
+
# Maps exception class to the exit code.
|
75
|
+
#
|
76
|
+
# === Parameters
|
77
|
+
# number:: (Integer) exit code to return on given exception
|
78
|
+
# eClass:: (Class) exception class
|
79
|
+
# message:: (String) explanation of the exception
|
80
|
+
#
|
81
|
+
def self.exit_code(number, eClass, message = "")
|
82
|
+
@@exit_code_map[eClass] = [number.to_i, eClass, message]
|
83
|
+
end
|
84
|
+
|
85
|
+
private
|
86
|
+
|
87
|
+
def default_options(opt) # :nodoc:
|
88
|
+
opt.on("-h", "--help", "Display help") {@help = true}
|
89
|
+
opt.on("-v", "--verbose", "Verbose output") {@verbose = true}
|
90
|
+
end
|
91
|
+
|
92
|
+
def define_exit_codes(opt) # :nodoc:
|
93
|
+
opt.separator ""
|
94
|
+
arr = @@exit_code_map.values.sort {|a,b| a[0] <=> b[0]}
|
95
|
+
unless arr.empty?
|
96
|
+
opt.separator "Exit codes:"
|
97
|
+
arr.each do |code, eClass, msg|
|
98
|
+
opt.separator "%6d %-29s %s" % [code, "[#{eClass}]", msg]
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
public
|
104
|
+
|
105
|
+
# === Description
|
106
|
+
# Your application should override this method.
|
107
|
+
# Define application command line options.
|
108
|
+
#
|
109
|
+
# === Parameters
|
110
|
+
# opt:: (OptionParser) use this to define options
|
111
|
+
#
|
112
|
+
def define_options(opt)
|
113
|
+
# override this; no additional options by default
|
114
|
+
end
|
115
|
+
|
116
|
+
# === Description
|
117
|
+
# Your application should override this method.
|
118
|
+
# Implement the main entry point.
|
119
|
+
#
|
120
|
+
# === Parameters
|
121
|
+
# argv:: (Array) of positional arguments
|
122
|
+
# Basically left over after processing command line options
|
123
|
+
# starting with dash(s) as defined in get_options.
|
124
|
+
#
|
125
|
+
# === Returns
|
126
|
+
# (Integer) exit code
|
127
|
+
#
|
128
|
+
def main(argv)
|
129
|
+
# override this; no default action in main
|
130
|
+
end
|
131
|
+
|
132
|
+
# === Description
|
133
|
+
# Parse options, and run the main method
|
134
|
+
#
|
135
|
+
# === Returns
|
136
|
+
# (Integer) exit code
|
137
|
+
#
|
138
|
+
def run
|
139
|
+
code = 0
|
140
|
+
opt = OptionParser.new
|
141
|
+
define_options(opt)
|
142
|
+
default_options(opt)
|
143
|
+
define_exit_codes(opt)
|
144
|
+
argv = opt.parse!
|
145
|
+
|
146
|
+
if @help
|
147
|
+
puts_msg(opt.help)
|
148
|
+
|
149
|
+
else
|
150
|
+
begin
|
151
|
+
main(argv)
|
152
|
+
rescue Exception => e
|
153
|
+
arr = @@exit_code_map[e.class]
|
154
|
+
code = arr ? arr[0] : 1
|
155
|
+
puts_err e.to_s
|
156
|
+
puts_err "[ERROR]"
|
157
|
+
end
|
158
|
+
end
|
159
|
+
|
160
|
+
exit(code)
|
161
|
+
end
|
162
|
+
|
163
|
+
# === Description
|
164
|
+
# Print out msg to STDOUT
|
165
|
+
#
|
166
|
+
def puts_msg(msg)
|
167
|
+
STDOUT.puts(msg)
|
168
|
+
end
|
169
|
+
|
170
|
+
# === Description
|
171
|
+
# Print out msg to STDERR in red color
|
172
|
+
#
|
173
|
+
def puts_err(msg)
|
174
|
+
STDERR.puts(msg.to_s.red)
|
175
|
+
end
|
176
|
+
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
@@ -0,0 +1,32 @@
|
|
1
|
+
class String
|
2
|
+
|
3
|
+
def colorize(color_code)
|
4
|
+
"\e[#{color_code}m#{self}\e[0m"
|
5
|
+
end
|
6
|
+
|
7
|
+
def red
|
8
|
+
colorize(31)
|
9
|
+
end
|
10
|
+
|
11
|
+
def green
|
12
|
+
colorize(32)
|
13
|
+
end
|
14
|
+
|
15
|
+
def yellow
|
16
|
+
colorize(33)
|
17
|
+
end
|
18
|
+
|
19
|
+
def blue
|
20
|
+
colorize(34)
|
21
|
+
end
|
22
|
+
|
23
|
+
def magenta
|
24
|
+
colorize(35)
|
25
|
+
end
|
26
|
+
|
27
|
+
def cyan
|
28
|
+
colorize(36)
|
29
|
+
end
|
30
|
+
|
31
|
+
end
|
32
|
+
|
data/lib/jewelbox/version.rb
CHANGED
data/test/bin/myapp
ADDED
@@ -0,0 +1,44 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require 'jewelbox/command'
|
3
|
+
|
4
|
+
class MyApp < Jewelbox::Command
|
5
|
+
|
6
|
+
class MyCustomException < RuntimeError; end
|
7
|
+
exit_code 1, RuntimeError, "Unexpected error"
|
8
|
+
exit_code 2, MyCustomException, "Some good explanation"
|
9
|
+
|
10
|
+
def initialize
|
11
|
+
@address = "default address"
|
12
|
+
@name = "default name"
|
13
|
+
end
|
14
|
+
|
15
|
+
def define_options(opt)
|
16
|
+
opt.banner = "Usage: #{opt.program_name} [options] file1 file2"
|
17
|
+
opt.on("-a addr", "--address addr", String, "Address to work with") {|s| @address = s}
|
18
|
+
opt.on("-n name", "--name name", String, "Name to work with") {|s| @name = s}
|
19
|
+
end
|
20
|
+
|
21
|
+
def do_something_with_address
|
22
|
+
puts "@address is #{@address}"
|
23
|
+
end
|
24
|
+
|
25
|
+
def do_something_with_name
|
26
|
+
puts "@name is #{@name}"
|
27
|
+
end
|
28
|
+
|
29
|
+
# Entry point of the application
|
30
|
+
#
|
31
|
+
def main(argv)
|
32
|
+
do_something_with_address
|
33
|
+
do_something_with_name
|
34
|
+
puts_msg "regular message"
|
35
|
+
puts_err "error message"
|
36
|
+
if argv[0] == "err"
|
37
|
+
raise MyCustomException.new("Some bad thing happened")
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
end
|
42
|
+
|
43
|
+
MyApp.new.run
|
44
|
+
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: jewelbox
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.3
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-08-28 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: ruby-debug19
|
16
|
-
requirement: &
|
16
|
+
requirement: &13114440 !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>='
|
@@ -21,7 +21,7 @@ dependencies:
|
|
21
21
|
version: '0'
|
22
22
|
type: :development
|
23
23
|
prerelease: false
|
24
|
-
version_requirements: *
|
24
|
+
version_requirements: *13114440
|
25
25
|
description: A set of useful Ruby functions to be used when creating a new service
|
26
26
|
or rails application
|
27
27
|
email:
|
@@ -37,10 +37,13 @@ files:
|
|
37
37
|
- Rakefile
|
38
38
|
- jewelbox.gemspec
|
39
39
|
- lib/jewelbox.rb
|
40
|
+
- lib/jewelbox/command.rb
|
40
41
|
- lib/jewelbox/config.rb
|
41
42
|
- lib/jewelbox/ext/object.rb
|
43
|
+
- lib/jewelbox/ext/string.rb
|
42
44
|
- lib/jewelbox/ext/time.rb
|
43
45
|
- lib/jewelbox/version.rb
|
46
|
+
- test/bin/myapp
|
44
47
|
- test/unit/conf/additional.yml
|
45
48
|
- test/unit/conf/service.yml
|
46
49
|
- test/unit/config_test.rb
|
@@ -72,6 +75,7 @@ specification_version: 3
|
|
72
75
|
summary: Contains functions that support service configuration, useful ruby methods
|
73
76
|
(such as eigenclass), and other functionality commonly used by Ruby services
|
74
77
|
test_files:
|
78
|
+
- test/bin/myapp
|
75
79
|
- test/unit/conf/additional.yml
|
76
80
|
- test/unit/conf/service.yml
|
77
81
|
- test/unit/config_test.rb
|