raph 0.0.2 → 0.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +16 -16
- data/.travis.yml +9 -9
- data/.yardopts +2 -2
- data/CHANGELOG.md +7 -0
- data/Gemfile +4 -4
- data/LICENSE +202 -202
- data/LICENSE.txt +22 -22
- data/README.md +102 -103
- data/Rakefile +6 -6
- data/example/sample.rb +7 -6
- data/lib/raph.rb +110 -61
- data/lib/raph/parser/assignment_parser.rb +38 -38
- data/lib/raph/parser/base_parser.rb +50 -50
- data/lib/raph/parser/file_parser.rb +24 -24
- data/lib/raph/parser/flag_parser.rb +31 -31
- data/lib/raph/parser/grouped_arg_parser.rb +42 -0
- data/lib/raph/version.rb +3 -3
- data/raph.gemspec +29 -29
- data/spec/raph/parser/assinment_parser_spec.rb +45 -45
- data/spec/raph/parser/base_parser_spec.rb +47 -47
- data/spec/raph/parser/file_parser_spec.rb +25 -25
- data/spec/raph/parser/flag_parser_spec.rb +48 -48
- data/spec/raph/parser/grouped_args_parser_spec.rb +60 -0
- data/spec/raph_spec.rb +78 -56
- data/spec/spec_helper.rb +1 -1
- metadata +19 -14
@@ -1,38 +1,38 @@
|
|
1
|
-
require 'raph/parser/assignment_parser'
|
2
|
-
|
3
|
-
module Raph
|
4
|
-
module Parser
|
5
|
-
# Considers option as assignment if and only if
|
6
|
-
# it has an assignment character (=) between
|
7
|
-
# option key and option value.
|
8
|
-
#
|
9
|
-
# Assumes that each option doesn't have spaces.
|
10
|
-
#
|
11
|
-
# Example of assignments:
|
12
|
-
# 'h=one' '-assg=two' '--config=my-file'
|
13
|
-
#
|
14
|
-
# Example of non-assignments:
|
15
|
-
# '-h' '-h=' 'h=' '=' '--config='
|
16
|
-
#
|
17
|
-
class AssignmentParser < BaseParser
|
18
|
-
def parse(args)
|
19
|
-
assgs = {}
|
20
|
-
args.each do |a|
|
21
|
-
if assignment? a
|
22
|
-
kv = a.split('=')
|
23
|
-
k = to_underscored_sym(kv.first)
|
24
|
-
v = kv.last
|
25
|
-
assgs[k] = v
|
26
|
-
end
|
27
|
-
end
|
28
|
-
assgs
|
29
|
-
end
|
30
|
-
|
31
|
-
def assignment?(option)
|
32
|
-
option.count('=') == 1 &&
|
33
|
-
!option.start_with?('=') &&
|
34
|
-
!option.end_with?('=')
|
35
|
-
end
|
36
|
-
end
|
37
|
-
end
|
38
|
-
end
|
1
|
+
require 'raph/parser/assignment_parser'
|
2
|
+
|
3
|
+
module Raph
|
4
|
+
module Parser
|
5
|
+
# Considers option as assignment if and only if
|
6
|
+
# it has an assignment character (=) between
|
7
|
+
# option key and option value.
|
8
|
+
#
|
9
|
+
# Assumes that each option doesn't have spaces.
|
10
|
+
#
|
11
|
+
# Example of assignments:
|
12
|
+
# 'h=one' '-assg=two' '--config=my-file'
|
13
|
+
#
|
14
|
+
# Example of non-assignments:
|
15
|
+
# '-h' '-h=' 'h=' '=' '--config='
|
16
|
+
#
|
17
|
+
class AssignmentParser < BaseParser
|
18
|
+
def parse(args)
|
19
|
+
assgs = {}
|
20
|
+
args.each do |a|
|
21
|
+
if assignment? a
|
22
|
+
kv = a.split('=')
|
23
|
+
k = to_underscored_sym(kv.first)
|
24
|
+
v = kv.last
|
25
|
+
assgs[k] = v
|
26
|
+
end
|
27
|
+
end
|
28
|
+
assgs
|
29
|
+
end
|
30
|
+
|
31
|
+
def assignment?(option)
|
32
|
+
option.count('=') == 1 &&
|
33
|
+
!option.start_with?('=') &&
|
34
|
+
!option.end_with?('=')
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -1,50 +1,50 @@
|
|
1
|
-
module Raph
|
2
|
-
# This module consists of argument parsers for Humans
|
3
|
-
module Parser
|
4
|
-
# Base class for all argument parsers.
|
5
|
-
#
|
6
|
-
# You can create a custom parser by subclassing
|
7
|
-
# `Raph::Parser::BaseParser` and overriding some methods,
|
8
|
-
# or by implementing all the methods by duck typing.
|
9
|
-
class BaseParser
|
10
|
-
# Parser unique id.
|
11
|
-
# If parser class name follows a convention NameParser
|
12
|
-
# then it's id will be automatically determined as it's
|
13
|
-
# name in snake case plus suffix 's'
|
14
|
-
#
|
15
|
-
# Example:
|
16
|
-
# FlagParser.new.id # => :flags
|
17
|
-
# FileParser.new.id # => :files
|
18
|
-
# BaseArgumentParser.new.id # => :base_arguments
|
19
|
-
def id
|
20
|
-
name = class_name.gsub(/parser$/i, '')
|
21
|
-
name << 's' # make it plural
|
22
|
-
to_underscored_sym(name)
|
23
|
-
end
|
24
|
-
|
25
|
-
# Parses arguments and returns results of parsing.
|
26
|
-
def parse(args)
|
27
|
-
end
|
28
|
-
|
29
|
-
protected
|
30
|
-
|
31
|
-
# Returns underscored symbol of string
|
32
|
-
# (snake case format).
|
33
|
-
def to_underscored_sym(str)
|
34
|
-
str.gsub(/^[-]+/, '').
|
35
|
-
gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
|
36
|
-
gsub(/([a-z\d])([A-Z])/,'\1_\2').
|
37
|
-
tr("-", "_").
|
38
|
-
downcase.
|
39
|
-
to_sym
|
40
|
-
end
|
41
|
-
|
42
|
-
private
|
43
|
-
|
44
|
-
# Returns name of current class.
|
45
|
-
def class_name
|
46
|
-
self.class.name.split('::').last || ''
|
47
|
-
end
|
48
|
-
end
|
49
|
-
end
|
50
|
-
end
|
1
|
+
module Raph
|
2
|
+
# This module consists of argument parsers for Humans
|
3
|
+
module Parser
|
4
|
+
# Base class for all argument parsers.
|
5
|
+
#
|
6
|
+
# You can create a custom parser by subclassing
|
7
|
+
# `Raph::Parser::BaseParser` and overriding some methods,
|
8
|
+
# or by implementing all the methods by duck typing.
|
9
|
+
class BaseParser
|
10
|
+
# Parser unique id.
|
11
|
+
# If parser class name follows a convention NameParser
|
12
|
+
# then it's id will be automatically determined as it's
|
13
|
+
# name in snake case plus suffix 's'
|
14
|
+
#
|
15
|
+
# Example:
|
16
|
+
# FlagParser.new.id # => :flags
|
17
|
+
# FileParser.new.id # => :files
|
18
|
+
# BaseArgumentParser.new.id # => :base_arguments
|
19
|
+
def id
|
20
|
+
name = class_name.gsub(/parser$/i, '')
|
21
|
+
name << 's' # make it plural
|
22
|
+
to_underscored_sym(name)
|
23
|
+
end
|
24
|
+
|
25
|
+
# Parses arguments and returns results of parsing.
|
26
|
+
def parse(args)
|
27
|
+
end
|
28
|
+
|
29
|
+
protected
|
30
|
+
|
31
|
+
# Returns underscored symbol of string
|
32
|
+
# (snake case format).
|
33
|
+
def to_underscored_sym(str)
|
34
|
+
str.gsub(/^[-]+/, '').
|
35
|
+
gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
|
36
|
+
gsub(/([a-z\d])([A-Z])/,'\1_\2').
|
37
|
+
tr("-", "_").
|
38
|
+
downcase.
|
39
|
+
to_sym
|
40
|
+
end
|
41
|
+
|
42
|
+
private
|
43
|
+
|
44
|
+
# Returns name of current class.
|
45
|
+
def class_name
|
46
|
+
self.class.name.split('::').last || ''
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -1,24 +1,24 @@
|
|
1
|
-
require 'raph/parser/base_parser'
|
2
|
-
|
3
|
-
module Raph
|
4
|
-
module Parser
|
5
|
-
# Argument is considered as file argument if and only if
|
6
|
-
# corresponding file exist on file system and match
|
7
|
-
# current argument.
|
8
|
-
#
|
9
|
-
# Example:
|
10
|
-
# 'test.rb' - file in current directory with name 'test.rb'
|
11
|
-
# '*.rb' - all files in current directory with extension 'rb'
|
12
|
-
# '**/*.xml' - all files in current directory and directories
|
13
|
-
# that are in this directory with extension 'xml'
|
14
|
-
class FileParser < BaseParser
|
15
|
-
def parse(args)
|
16
|
-
files = []
|
17
|
-
args.each do |a|
|
18
|
-
files.concat Dir[a]
|
19
|
-
end
|
20
|
-
files.uniq
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
1
|
+
require 'raph/parser/base_parser'
|
2
|
+
|
3
|
+
module Raph
|
4
|
+
module Parser
|
5
|
+
# Argument is considered as file argument if and only if
|
6
|
+
# corresponding file exist on file system and match
|
7
|
+
# current argument.
|
8
|
+
#
|
9
|
+
# Example:
|
10
|
+
# 'test.rb' - file in current directory with name 'test.rb'
|
11
|
+
# '*.rb' - all files in current directory with extension 'rb'
|
12
|
+
# '**/*.xml' - all files in current directory and directories
|
13
|
+
# that are in this directory with extension 'xml'
|
14
|
+
class FileParser < BaseParser
|
15
|
+
def parse(args)
|
16
|
+
files = []
|
17
|
+
args.each do |a|
|
18
|
+
files.concat Dir[a]
|
19
|
+
end
|
20
|
+
files.uniq
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -1,31 +1,31 @@
|
|
1
|
-
require 'raph/parser/base_parser'
|
2
|
-
|
3
|
-
module Raph
|
4
|
-
module Parser
|
5
|
-
# Considers option as flag if and only if
|
6
|
-
# it's name starts with one dash and follows by
|
7
|
-
# one word character or starts with two dashes
|
8
|
-
# and follows by 2 or more word chacters or dashes.
|
9
|
-
#
|
10
|
-
# Assumes that each option doesn't have spaces.
|
11
|
-
#
|
12
|
-
# Example of flags:
|
13
|
-
# '-h' '-T' '--config'
|
14
|
-
#
|
15
|
-
# Example of non-flags:
|
16
|
-
# 'option' '---option2' '--h'
|
17
|
-
class FlagParser < BaseParser
|
18
|
-
def parse(args)
|
19
|
-
flags = []
|
20
|
-
args.each do |a|
|
21
|
-
flags << to_underscored_sym(a) if flag? a
|
22
|
-
end
|
23
|
-
flags
|
24
|
-
end
|
25
|
-
|
26
|
-
def flag?(option)
|
27
|
-
option =~ /^-[\w]$/ || option =~ /^--[\w][\w-]+$/
|
28
|
-
end
|
29
|
-
end
|
30
|
-
end
|
31
|
-
end
|
1
|
+
require 'raph/parser/base_parser'
|
2
|
+
|
3
|
+
module Raph
|
4
|
+
module Parser
|
5
|
+
# Considers option as flag if and only if
|
6
|
+
# it's name starts with one dash and follows by
|
7
|
+
# one word character or starts with two dashes
|
8
|
+
# and follows by 2 or more word chacters or dashes.
|
9
|
+
#
|
10
|
+
# Assumes that each option doesn't have spaces.
|
11
|
+
#
|
12
|
+
# Example of flags:
|
13
|
+
# '-h' '-T' '--config'
|
14
|
+
#
|
15
|
+
# Example of non-flags:
|
16
|
+
# 'option' '---option2' '--h'
|
17
|
+
class FlagParser < BaseParser
|
18
|
+
def parse(args)
|
19
|
+
flags = []
|
20
|
+
args.each do |a|
|
21
|
+
flags << to_underscored_sym(a) if flag? a
|
22
|
+
end
|
23
|
+
flags
|
24
|
+
end
|
25
|
+
|
26
|
+
def flag?(option)
|
27
|
+
!!(option =~ /^-[\w]$/ || option =~ /^--[\w][\w-]+$/)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require 'raph/parser/base_parser'
|
2
|
+
require 'raph/parser/flag_parser'
|
3
|
+
require 'raph/parser/assignment_parser'
|
4
|
+
|
5
|
+
module Raph
|
6
|
+
module Parser
|
7
|
+
# Grouped arguments are arguments that follows
|
8
|
+
# a group - a specific argument. In other words
|
9
|
+
# flags and assignments represents groups and
|
10
|
+
# arguments followed them are grouped arguments.
|
11
|
+
#
|
12
|
+
# Next example:
|
13
|
+
# '--group1', '1', '2', '--group2', 'three'
|
14
|
+
# has two groups (`:group1` and `:group2`) with
|
15
|
+
# corresponding grouped arguments (['1', '2'], ['three'])
|
16
|
+
class GroupedArgParser < BaseParser
|
17
|
+
def initialize
|
18
|
+
@flag_parser = FlagParser.new
|
19
|
+
@assignment_parser = AssignmentParser.new
|
20
|
+
end
|
21
|
+
|
22
|
+
def parse(args)
|
23
|
+
groups = {}
|
24
|
+
current_group = nil
|
25
|
+
|
26
|
+
args.each do |arg|
|
27
|
+
if group? arg
|
28
|
+
current_group = to_underscored_sym arg
|
29
|
+
groups[current_group] = []
|
30
|
+
else
|
31
|
+
groups[current_group].push(arg) if current_group
|
32
|
+
end
|
33
|
+
end
|
34
|
+
groups
|
35
|
+
end
|
36
|
+
|
37
|
+
def group?(arg)
|
38
|
+
@flag_parser.flag?(arg) || @assignment_parser.assignment?(arg)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
data/lib/raph/version.rb
CHANGED
@@ -1,3 +1,3 @@
|
|
1
|
-
module Raph
|
2
|
-
VERSION = '0.0.
|
3
|
-
end
|
1
|
+
module Raph
|
2
|
+
VERSION = '0.0.3'
|
3
|
+
end
|
data/raph.gemspec
CHANGED
@@ -1,29 +1,29 @@
|
|
1
|
-
# coding: utf-8
|
2
|
-
lib = File.expand_path('../lib', __FILE__)
|
3
|
-
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
-
require 'raph/version'
|
5
|
-
|
6
|
-
Gem::Specification.new do |spec|
|
7
|
-
spec.name = 'raph'
|
8
|
-
spec.version = Raph::VERSION
|
9
|
-
spec.authors = ['Vitalii Elenhaupt']
|
10
|
-
spec.email = ['velenhaupt@gmail.com']
|
11
|
-
spec.summary = 'Ruby Argument Parsing for Humans.'
|
12
|
-
spec.description = <<-DESC
|
13
|
-
Lightweight argument parsing with flexible structure.
|
14
|
-
Add your parser in few minutes.
|
15
|
-
DESC
|
16
|
-
spec.homepage = 'https://github.com/veelenga/raph'
|
17
|
-
spec.license = 'MIT'
|
18
|
-
|
19
|
-
spec.files = `git ls-files`.split($RS)
|
20
|
-
spec.executables = spec.files.grep(/^bin\//) { |f| File.basename(f) }
|
21
|
-
spec.test_files = spec.files.grep(/^spec\//)
|
22
|
-
spec.require_paths = ['lib']
|
23
|
-
|
24
|
-
spec.required_ruby_version = '>= 1.9.3'
|
25
|
-
|
26
|
-
spec.add_development_dependency 'bundler', '~> 1.7'
|
27
|
-
spec.add_development_dependency 'rake', '~> 10.0'
|
28
|
-
spec.add_development_dependency 'rspec', '~> 3.0'
|
29
|
-
end
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'raph/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = 'raph'
|
8
|
+
spec.version = Raph::VERSION
|
9
|
+
spec.authors = ['Vitalii Elenhaupt']
|
10
|
+
spec.email = ['velenhaupt@gmail.com']
|
11
|
+
spec.summary = 'Ruby Argument Parsing for Humans.'
|
12
|
+
spec.description = <<-DESC
|
13
|
+
Lightweight argument parsing with flexible structure.
|
14
|
+
Add your parser in few minutes.
|
15
|
+
DESC
|
16
|
+
spec.homepage = 'https://github.com/veelenga/raph'
|
17
|
+
spec.license = 'MIT'
|
18
|
+
|
19
|
+
spec.files = `git ls-files`.split($RS)
|
20
|
+
spec.executables = spec.files.grep(/^bin\//) { |f| File.basename(f) }
|
21
|
+
spec.test_files = spec.files.grep(/^spec\//)
|
22
|
+
spec.require_paths = ['lib']
|
23
|
+
|
24
|
+
spec.required_ruby_version = '>= 1.9.3'
|
25
|
+
|
26
|
+
spec.add_development_dependency 'bundler', '~> 1.7'
|
27
|
+
spec.add_development_dependency 'rake', '~> 10.0'
|
28
|
+
spec.add_development_dependency 'rspec', '~> 3.0'
|
29
|
+
end
|
@@ -1,45 +1,45 @@
|
|
1
|
-
require 'spec_helper'
|
2
|
-
|
3
|
-
module Raph
|
4
|
-
module Parser
|
5
|
-
describe AssignmentParser do
|
6
|
-
describe '#id' do
|
7
|
-
it 'has correct form' do
|
8
|
-
expect(subject.id).to eq :assignments
|
9
|
-
end
|
10
|
-
end
|
11
|
-
|
12
|
-
describe '#parse' do
|
13
|
-
it 'returns assignments only' do
|
14
|
-
parsed = subject.parse(['-h', '-on=20', '--two=my-file'])
|
15
|
-
expect(parsed).to include(:on => '20', :two => 'my-file')
|
16
|
-
end
|
17
|
-
|
18
|
-
it 'has no to return assignments here' do
|
19
|
-
expect(subject.parse(['-h', 'file', '=', '123'])).to be_empty
|
20
|
-
expect(subject.parse([])).to be_empty
|
21
|
-
end
|
22
|
-
end
|
23
|
-
|
24
|
-
describe '#assignment?' do
|
25
|
-
def ass?(option)
|
26
|
-
subject.assignment? option
|
27
|
-
end
|
28
|
-
|
29
|
-
it 'is an assignment' do
|
30
|
-
expect(ass? 'h=one').to be true
|
31
|
-
expect(ass? '-ass=two').to be true
|
32
|
-
expect(ass? '--ass=two').to be true
|
33
|
-
end
|
34
|
-
|
35
|
-
it 'is not as assignment' do
|
36
|
-
expect(ass? '-h').to be false
|
37
|
-
expect(ass? '-h=').to be false
|
38
|
-
expect(ass? 'h=').to be false
|
39
|
-
expect(ass? '=').to be false
|
40
|
-
expect(ass? '-h=one=two').to be false
|
41
|
-
end
|
42
|
-
end
|
43
|
-
end
|
44
|
-
end
|
45
|
-
end
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Raph
|
4
|
+
module Parser
|
5
|
+
describe AssignmentParser do
|
6
|
+
describe '#id' do
|
7
|
+
it 'has correct form' do
|
8
|
+
expect(subject.id).to eq :assignments
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
describe '#parse' do
|
13
|
+
it 'returns assignments only' do
|
14
|
+
parsed = subject.parse(['-h', '-on=20', '--two=my-file'])
|
15
|
+
expect(parsed).to include(:on => '20', :two => 'my-file')
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'has no to return assignments here' do
|
19
|
+
expect(subject.parse(['-h', 'file', '=', '123'])).to be_empty
|
20
|
+
expect(subject.parse([])).to be_empty
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
describe '#assignment?' do
|
25
|
+
def ass?(option)
|
26
|
+
subject.assignment? option
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'is an assignment' do
|
30
|
+
expect(ass? 'h=one').to be true
|
31
|
+
expect(ass? '-ass=two').to be true
|
32
|
+
expect(ass? '--ass=two').to be true
|
33
|
+
end
|
34
|
+
|
35
|
+
it 'is not as assignment' do
|
36
|
+
expect(ass? '-h').to be false
|
37
|
+
expect(ass? '-h=').to be false
|
38
|
+
expect(ass? 'h=').to be false
|
39
|
+
expect(ass? '=').to be false
|
40
|
+
expect(ass? '-h=one=two').to be false
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|