gyoku 0.3.1 → 0.4.0
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/.gemtest +0 -0
- data/README.md +11 -0
- data/Rakefile +6 -5
- data/lib/gyoku.rb +16 -4
- data/lib/gyoku/array.rb +1 -4
- data/lib/gyoku/core_ext/string.rb +6 -5
- data/lib/gyoku/hash.rb +2 -4
- data/lib/gyoku/version.rb +1 -1
- data/lib/gyoku/xml_key.rb +47 -25
- data/lib/gyoku/xml_value.rb +17 -15
- data/spec/gyoku/core_ext/string_spec.rb +6 -0
- data/spec/gyoku/xml_key_spec.rb +40 -9
- data/spec/gyoku/xml_value_spec.rb +15 -12
- data/spec/gyoku_spec.rb +20 -0
- metadata +7 -6
data/.gemtest
ADDED
File without changes
|
data/README.md
CHANGED
@@ -37,6 +37,17 @@ Conventions
|
|
37
37
|
* These conventions are also applied to the return value of objects responding to :call
|
38
38
|
* All other objects are converted to Strings using :to_s
|
39
39
|
|
40
|
+
Symbols are converted to lowerCamelCase?
|
41
|
+
----------------------------------------
|
42
|
+
|
43
|
+
That's the default. But you can use one of the other conversion formulas:
|
44
|
+
|
45
|
+
Gyoku.convert_symbols_to :camelcase # or one of [:none, :lower_camelcase]
|
46
|
+
|
47
|
+
or even define you own one:
|
48
|
+
|
49
|
+
Gyoku.convert_symbols_to { |key| key.upcase }
|
50
|
+
|
40
51
|
Special characters
|
41
52
|
------------------
|
42
53
|
|
data/Rakefile
CHANGED
@@ -1,11 +1,9 @@
|
|
1
1
|
require "bundler"
|
2
2
|
Bundler::GemHelper.install_tasks
|
3
3
|
|
4
|
-
task :default => :spec
|
5
|
-
|
6
4
|
begin
|
7
5
|
require "yard"
|
8
|
-
|
6
|
+
|
9
7
|
YARD::Rake::YardocTask.new do |t|
|
10
8
|
t.files = ["README.md", "lib/**/*.rb"]
|
11
9
|
end
|
@@ -16,7 +14,7 @@ end
|
|
16
14
|
|
17
15
|
begin
|
18
16
|
require "metric_fu"
|
19
|
-
|
17
|
+
|
20
18
|
MetricFu::Configuration.run do |c|
|
21
19
|
c.metrics = [:churn, :flog, :flay, :reek, :roodi, :saikuro] # :rcov seems to be broken
|
22
20
|
c.graphs = [:flog, :flay, :reek, :roodi]
|
@@ -30,7 +28,7 @@ end
|
|
30
28
|
|
31
29
|
begin
|
32
30
|
require "rspec/core/rake_task"
|
33
|
-
|
31
|
+
|
34
32
|
RSpec::Core::RakeTask.new do |t|
|
35
33
|
t.pattern = "spec/**/*_spec.rb"
|
36
34
|
t.rspec_opts = %w(-fd -c)
|
@@ -40,3 +38,6 @@ rescue LoadError
|
|
40
38
|
abort "Run 'gem install rspec' to be able to run specs"
|
41
39
|
end
|
42
40
|
end
|
41
|
+
|
42
|
+
task :default => :spec
|
43
|
+
task :test => :spec
|
data/lib/gyoku.rb
CHANGED
@@ -2,10 +2,22 @@ require "gyoku/version"
|
|
2
2
|
require "gyoku/hash"
|
3
3
|
|
4
4
|
module Gyoku
|
5
|
+
class << self
|
5
6
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
7
|
+
# Translates a given +hash+ with +options+ to XML.
|
8
|
+
def xml(hash, options = {})
|
9
|
+
Hash.to_xml hash, options
|
10
|
+
end
|
11
|
+
|
12
|
+
# Yields this object for configuration.
|
13
|
+
def configure
|
14
|
+
yield self
|
15
|
+
end
|
10
16
|
|
17
|
+
# Sets the formula for converting Symbol keys.
|
18
|
+
def convert_symbols_to(formula = nil, &block)
|
19
|
+
XMLKey.symbol_converter = formula ? formula : block
|
20
|
+
end
|
21
|
+
|
22
|
+
end
|
11
23
|
end
|
data/lib/gyoku/array.rb
CHANGED
@@ -1,13 +1,10 @@
|
|
1
1
|
require "builder"
|
2
2
|
|
3
3
|
require "gyoku/hash"
|
4
|
-
require "gyoku/xml_key"
|
5
4
|
require "gyoku/xml_value"
|
6
5
|
|
7
6
|
module Gyoku
|
8
7
|
class Array
|
9
|
-
extend XMLKey
|
10
|
-
extend XMLValue
|
11
8
|
|
12
9
|
# Translates a given +array+ to XML. Accepts the XML +key+ to add the elements to,
|
13
10
|
# whether to +escape_xml+ and an optional Hash of +attributes+.
|
@@ -16,7 +13,7 @@ module Gyoku
|
|
16
13
|
case item
|
17
14
|
when ::Hash then xml.tag!(key, attrs) { xml << Hash.to_xml(item) }
|
18
15
|
when NilClass then xml.tag!(key, "xsi:nil" => "true")
|
19
|
-
else xml.tag!(key, attrs) { xml <<
|
16
|
+
else xml.tag!(key, attrs) { xml << XMLValue.create(item, escape_xml) }
|
20
17
|
end
|
21
18
|
end
|
22
19
|
end
|
@@ -4,11 +4,12 @@ module Gyoku
|
|
4
4
|
|
5
5
|
# Returns the String in lowerCamelCase.
|
6
6
|
def lower_camelcase
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
7
|
+
self[0].chr.downcase + self.camelcase[1..-1]
|
8
|
+
end
|
9
|
+
|
10
|
+
# Returns the String in CamelCase.
|
11
|
+
def camelcase
|
12
|
+
self.gsub(/\/(.?)/) { "::#{$1.upcase}" }.gsub(/(?:^|_)(.)/) { $1.upcase }
|
12
13
|
end
|
13
14
|
|
14
15
|
end
|
data/lib/gyoku/hash.rb
CHANGED
@@ -6,22 +6,20 @@ require "gyoku/xml_value"
|
|
6
6
|
|
7
7
|
module Gyoku
|
8
8
|
class Hash
|
9
|
-
extend XMLKey
|
10
|
-
extend XMLValue
|
11
9
|
|
12
10
|
# Translates a given +hash+ with +options+ to XML.
|
13
11
|
def self.to_xml(hash, options = {})
|
14
12
|
iterate_with_xml hash do |xml, key, value, attributes|
|
15
13
|
self_closing = key.to_s[-1, 1] == "/"
|
16
14
|
escape_xml = key.to_s[-1, 1] != "!"
|
17
|
-
xml_key =
|
15
|
+
xml_key = XMLKey.create key, options
|
18
16
|
|
19
17
|
case
|
20
18
|
when ::Array === value then xml << Array.to_xml(value, xml_key, escape_xml, attributes)
|
21
19
|
when ::Hash === value then xml.tag!(xml_key, attributes) { xml << Hash.to_xml(value, options) }
|
22
20
|
when self_closing then xml.tag!(xml_key, attributes)
|
23
21
|
when NilClass === value then xml.tag!(xml_key, "xsi:nil" => "true")
|
24
|
-
else xml.tag!(xml_key, attributes) { xml <<
|
22
|
+
else xml.tag!(xml_key, attributes) { xml << XMLValue.create(value, escape_xml) }
|
25
23
|
end
|
26
24
|
end
|
27
25
|
end
|
data/lib/gyoku/version.rb
CHANGED
data/lib/gyoku/xml_key.rb
CHANGED
@@ -2,39 +2,61 @@ require "gyoku/core_ext/string"
|
|
2
2
|
|
3
3
|
module Gyoku
|
4
4
|
module XMLKey
|
5
|
+
class << self
|
6
|
+
|
7
|
+
FORMULAS = {
|
8
|
+
:lower_camelcase => lambda { |key| key.lower_camelcase },
|
9
|
+
:camelcase => lambda { |key| key.camelcase },
|
10
|
+
:none => lambda { |key| key }
|
11
|
+
}
|
12
|
+
|
13
|
+
# Converts a given +object+ with +options+ to an XML key.
|
14
|
+
def create(key, options = {})
|
15
|
+
xml_key = chop_special_characters key.to_s
|
16
|
+
|
17
|
+
if unqualify?(xml_key)
|
18
|
+
xml_key = xml_key.split(":").last
|
19
|
+
elsif qualify?(options) && !xml_key.include?(":")
|
20
|
+
xml_key = "#{options[:namespace]}:#{xml_key}"
|
21
|
+
end
|
22
|
+
|
23
|
+
case key
|
24
|
+
when Symbol then symbol_converter.call(xml_key)
|
25
|
+
else xml_key
|
26
|
+
end
|
27
|
+
end
|
5
28
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
if unqualify?(xml_key)
|
11
|
-
xml_key = xml_key.split(":").last
|
12
|
-
elsif qualify?(options) && !xml_key.include?(":")
|
13
|
-
xml_key = "#{options[:namespace]}:#{xml_key}"
|
29
|
+
# Returns the formula for converting Symbol keys.
|
30
|
+
def symbol_converter
|
31
|
+
@symbol_converter ||= FORMULAS[:lower_camelcase]
|
14
32
|
end
|
15
33
|
|
16
|
-
|
17
|
-
|
18
|
-
|
34
|
+
# Sets the +formula+ for converting Symbol keys.
|
35
|
+
# Accepts one of +FORMULAS+ of an object responding to <tt>:call</tt>.
|
36
|
+
def symbol_converter=(formula)
|
37
|
+
formula = FORMULAS[formula] unless formula.respond_to? :call
|
38
|
+
raise ArgumentError, "Invalid symbol_converter formula" unless formula
|
39
|
+
|
40
|
+
@symbol_converter = formula
|
19
41
|
end
|
20
|
-
end
|
21
42
|
|
22
|
-
|
43
|
+
private
|
23
44
|
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
45
|
+
# Chops special characters from the end of a given +string+.
|
46
|
+
def chop_special_characters(string)
|
47
|
+
["!", "/"].include?(string[-1, 1]) ? string.chop : string
|
48
|
+
end
|
28
49
|
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
50
|
+
# Returns whether to remove the namespace from a given +key+.
|
51
|
+
def unqualify?(key)
|
52
|
+
key[0, 1] == ":"
|
53
|
+
end
|
33
54
|
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
55
|
+
# Returns whether to namespace all keys (elementFormDefault).
|
56
|
+
def qualify?(options)
|
57
|
+
options[:element_form_default] == :qualified && options[:namespace]
|
58
|
+
end
|
38
59
|
|
60
|
+
end
|
39
61
|
end
|
40
62
|
end
|
data/lib/gyoku/xml_value.rb
CHANGED
@@ -2,24 +2,26 @@ require "cgi"
|
|
2
2
|
|
3
3
|
module Gyoku
|
4
4
|
module XMLValue
|
5
|
+
class << self
|
5
6
|
|
6
|
-
|
7
|
-
|
7
|
+
# xs:dateTime format.
|
8
|
+
XS_DATETIME_FORMAT = "%Y-%m-%dT%H:%M:%S%Z"
|
8
9
|
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
10
|
+
# Converts a given +object+ to an XML value.
|
11
|
+
def create(object, escape_xml = true)
|
12
|
+
if DateTime === object
|
13
|
+
object.strftime XS_DATETIME_FORMAT
|
14
|
+
elsif String === object
|
15
|
+
escape_xml ? CGI.escapeHTML(object) : object
|
16
|
+
elsif object.respond_to?(:to_datetime)
|
17
|
+
create object.to_datetime
|
18
|
+
elsif object.respond_to?(:call)
|
19
|
+
create object.call
|
20
|
+
else
|
21
|
+
object.to_s
|
22
|
+
end
|
21
23
|
end
|
22
|
-
end
|
23
24
|
|
25
|
+
end
|
24
26
|
end
|
25
27
|
end
|
data/spec/gyoku/xml_key_spec.rb
CHANGED
@@ -1,37 +1,68 @@
|
|
1
1
|
require "spec_helper"
|
2
2
|
|
3
3
|
describe Gyoku::XMLKey do
|
4
|
-
include Gyoku::XMLKey
|
5
4
|
|
6
|
-
describe "
|
5
|
+
describe ".create" do
|
7
6
|
it "should remove exclamation marks from the end of a String" do
|
8
|
-
|
7
|
+
create("value!").should == "value"
|
9
8
|
end
|
10
9
|
|
11
10
|
it "should remove forward slashes from the end of a String" do
|
12
|
-
|
11
|
+
create("self-closing/").should == "self-closing"
|
13
12
|
end
|
14
13
|
|
15
14
|
it "should not convert snake_case Strings" do
|
16
|
-
|
15
|
+
create("lower_camel_case").should == "lower_camel_case"
|
17
16
|
end
|
18
17
|
|
19
18
|
it "should convert snake_case Symbols to lowerCamelCase Strings" do
|
20
|
-
|
21
|
-
|
19
|
+
create(:lower_camel_case).should == "lowerCamelCase"
|
20
|
+
create(:lower_camel_case!).should == "lowerCamelCase"
|
22
21
|
end
|
23
22
|
|
24
23
|
context "with :element_form_default set to :qualified and a :namespace" do
|
25
24
|
it "should add the given namespace" do
|
26
|
-
key =
|
25
|
+
key = create :qualify, :element_form_default => :qualified, :namespace => :v1
|
27
26
|
key.should == "v1:qualify"
|
28
27
|
end
|
29
28
|
|
30
29
|
it "should not add the given namespace if the key starts with a colon" do
|
31
|
-
key =
|
30
|
+
key = create ":qualify", :element_form_default => :qualified, :namespace => :v1
|
32
31
|
key.should == "qualify"
|
33
32
|
end
|
34
33
|
end
|
35
34
|
end
|
36
35
|
|
36
|
+
describe ".symbol_converter" do
|
37
|
+
after { Gyoku::XMLKey.symbol_converter = :lower_camelcase } #reset
|
38
|
+
|
39
|
+
it "should return the default lower_camelcase converter" do
|
40
|
+
Gyoku::XMLKey.symbol_converter.call("snake_case").should == "snakeCase"
|
41
|
+
end
|
42
|
+
|
43
|
+
it "should accept :lower_camelcase" do
|
44
|
+
Gyoku::XMLKey.symbol_converter = :lower_camelcase
|
45
|
+
Gyoku::XMLKey.create(:snake_case).should == "snakeCase"
|
46
|
+
end
|
47
|
+
|
48
|
+
it "should accept :camelcase" do
|
49
|
+
Gyoku::XMLKey.symbol_converter = :camelcase
|
50
|
+
Gyoku::XMLKey.create(:snake_case).should == "SnakeCase"
|
51
|
+
end
|
52
|
+
|
53
|
+
it "should accept :none" do
|
54
|
+
Gyoku::XMLKey.symbol_converter = :none
|
55
|
+
Gyoku::XMLKey.create(:snake_Case).should == "snake_Case"
|
56
|
+
end
|
57
|
+
|
58
|
+
it "should allow to set a custom converter" do
|
59
|
+
Gyoku::XMLKey.symbol_converter = Proc.new { |key| key.upcase }
|
60
|
+
Gyoku::XMLKey.create(:snake_case).should == "SNAKE_CASE"
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
def create(key, options = {})
|
65
|
+
Gyoku::XMLKey.create key, options
|
66
|
+
end
|
67
|
+
|
37
68
|
end
|
@@ -1,27 +1,26 @@
|
|
1
1
|
require "spec_helper"
|
2
2
|
|
3
3
|
describe Gyoku::XMLValue do
|
4
|
-
include Gyoku::XMLValue
|
5
4
|
|
6
5
|
let(:datetime) { DateTime.new 2012, 03, 22, 16, 22, 33 }
|
7
6
|
let(:datetime_string) { "2012-03-22T16:22:33+00:00" }
|
8
|
-
|
9
|
-
describe "
|
7
|
+
|
8
|
+
describe ".create" do
|
10
9
|
context "for DateTime objects" do
|
11
10
|
it "should return an xs:dateTime compliant String" do
|
12
|
-
|
11
|
+
create(datetime).should == datetime_string
|
13
12
|
end
|
14
13
|
end
|
15
14
|
|
16
15
|
it "should return the String value and escape special characters" do
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
16
|
+
create("string").should == "string"
|
17
|
+
create("<tag>").should == "<tag>"
|
18
|
+
create("at&t").should == "at&t"
|
19
|
+
create('"quotes"').should == ""quotes""
|
21
20
|
end
|
22
21
|
|
23
22
|
it "should just return the String value without escaping special characters" do
|
24
|
-
|
23
|
+
create("<tag>", false).should == "<tag>"
|
25
24
|
end
|
26
25
|
|
27
26
|
it "should return an xs:dateTime compliant String for Objects responding to #to_datetime" do
|
@@ -30,17 +29,21 @@ describe Gyoku::XMLValue do
|
|
30
29
|
DateTime.new 2012, 03, 22, 16, 22, 33
|
31
30
|
end
|
32
31
|
|
33
|
-
|
32
|
+
create(singleton).should == "2012-03-22T16:22:33+00:00"
|
34
33
|
end
|
35
34
|
|
36
35
|
it "should #call Proc objects and convert their return value" do
|
37
36
|
object = lambda { DateTime.new 2012, 03, 22, 16, 22, 33 }
|
38
|
-
|
37
|
+
create(object).should == "2012-03-22T16:22:33+00:00"
|
39
38
|
end
|
40
39
|
|
41
40
|
it "should call #to_s unless the Object responds to #to_datetime" do
|
42
|
-
|
41
|
+
create("value").should == "value"
|
43
42
|
end
|
44
43
|
end
|
45
44
|
|
45
|
+
def create(object, escape_xml = true)
|
46
|
+
Gyoku::XMLValue.create object, escape_xml
|
47
|
+
end
|
48
|
+
|
46
49
|
end
|
data/spec/gyoku_spec.rb
CHANGED
@@ -9,4 +9,24 @@ describe Gyoku do
|
|
9
9
|
end
|
10
10
|
end
|
11
11
|
|
12
|
+
describe ".configure" do
|
13
|
+
it "should yield the Gyoku module" do
|
14
|
+
Gyoku.configure { |config| config.should respond_to(:convert_symbols_to) }
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
describe ".convert_symbols_to" do
|
19
|
+
after { Gyoku.convert_symbols_to(:lower_camelcase) } # reset
|
20
|
+
|
21
|
+
it "should accept a predefined formula" do
|
22
|
+
Gyoku.convert_symbols_to(:camelcase)
|
23
|
+
Gyoku::XMLKey.create(:snake_case).should == "SnakeCase"
|
24
|
+
end
|
25
|
+
|
26
|
+
it "should accept a block" do
|
27
|
+
Gyoku.convert_symbols_to { |key| key.upcase }
|
28
|
+
Gyoku::XMLKey.create(:snake_case).should == "SNAKE_CASE"
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
12
32
|
end
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gyoku
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 15
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
-
-
|
9
|
-
-
|
10
|
-
version: 0.
|
8
|
+
- 4
|
9
|
+
- 0
|
10
|
+
version: 0.4.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Daniel Harrington
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-
|
18
|
+
date: 2011-04-05 00:00:00 +02:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|
@@ -89,6 +89,7 @@ extensions: []
|
|
89
89
|
extra_rdoc_files: []
|
90
90
|
|
91
91
|
files:
|
92
|
+
- .gemtest
|
92
93
|
- .gitignore
|
93
94
|
- .rspec
|
94
95
|
- Gemfile
|
@@ -140,7 +141,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
140
141
|
requirements: []
|
141
142
|
|
142
143
|
rubyforge_project: gyoku
|
143
|
-
rubygems_version: 1.4.
|
144
|
+
rubygems_version: 1.4.2
|
144
145
|
signing_key:
|
145
146
|
specification_version: 3
|
146
147
|
summary: Converts Ruby Hashes to XML
|