semantic-mapper 0.0.1 → 0.0.2
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.
- checksums.yaml +4 -4
- data/lib/semantic/mapper/markup.rb +34 -4
- data/lib/semantic/mapper/version.rb +1 -1
- data/spec/fixtures/reservation.html +8 -8
- data/spec/lib/semantic/mapper/markup_spec.rb +42 -10
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d7d2ffcffd11d706a95f945f1e40e8271487059f
|
4
|
+
data.tar.gz: 71c2c16b8544022aa75ecaeb2a093db6230c1b90
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 44f7c907d3b1e7e7a70d3c981750b4d68cac224b9baa88e73d5789af628712f2407c6998b8cec0f6bfca27f449d102c3b16feccbb7751df5e088955f4d3b0691
|
7
|
+
data.tar.gz: a4ae4599a427ae1bf726933b2f2f02963069586b38455345116c2f6073bebb26e29d1a333916a107c0a2521099ffd1d63f581864b23e93853e747de34951aec3
|
@@ -2,19 +2,49 @@ module Semantic
|
|
2
2
|
module Mapper
|
3
3
|
class Markup
|
4
4
|
SELECTOR = '[data-mapping]'
|
5
|
+
attr_reader :mapped_hash
|
5
6
|
|
6
7
|
def initialize(html)
|
7
8
|
@html = html
|
9
|
+
@mapped_hash = HashWithIndifferentAccess.new
|
8
10
|
end
|
9
11
|
|
10
12
|
def map
|
11
|
-
document.css(SELECTOR).
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
document.css(SELECTOR).each do |element|
|
14
|
+
fields(element).each do |key|
|
15
|
+
final_attribute_value = attribute_value(element, 'name')
|
16
|
+
keys = build_keys(key)
|
17
|
+
map_hash(final_attribute_value, keys)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
@mapped_hash
|
15
21
|
end
|
16
22
|
|
17
23
|
private
|
24
|
+
|
25
|
+
def map_hash(value, keys)
|
26
|
+
merge_or_set(keys[0], value) and return if keys.length == 1
|
27
|
+
current_key = keys.pop
|
28
|
+
value = HashWithIndifferentAccess.new(current_key => value)
|
29
|
+
map_hash(value, keys)
|
30
|
+
end
|
31
|
+
|
32
|
+
def build_keys(key)
|
33
|
+
key.scan(/([\w-]+)|\[([\w-]+?)\]/).flatten.compact
|
34
|
+
end
|
35
|
+
|
36
|
+
def merge_or_set(key, value)
|
37
|
+
if @mapped_hash.has_key?(key)
|
38
|
+
@mapped_hash[key].deep_merge!(value)
|
39
|
+
else
|
40
|
+
@mapped_hash[key] = value
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
def fields(element)
|
45
|
+
attribute_value(element, 'data-mapping').split(" ")
|
46
|
+
end
|
47
|
+
|
18
48
|
def document
|
19
49
|
@document ||= Nokogiri::HTML(@html)
|
20
50
|
end
|
@@ -1,27 +1,27 @@
|
|
1
1
|
<div class="p-author h-card">
|
2
2
|
<div class="form-field">
|
3
3
|
<label for="p-first-name" class="required">First Name</label>
|
4
|
-
<input type="text" id="p-first-name" class="p-first-name" name="p-first-name" data-mapping="first_name" required>
|
4
|
+
<input type="text" id="p-first-name" class="p-first-name" name="p-first-name" data-mapping="customer[first_name]" required>
|
5
5
|
</div>
|
6
6
|
|
7
7
|
<div class="form-field">
|
8
8
|
<label for="p-last-name" class="required">Last Name</label>
|
9
|
-
<input type="text" id="p-last-name" class="p-last-name" name="p-last-name" data-mapping="last_name" required>
|
9
|
+
<input type="text" id="p-last-name" class="p-last-name" name="p-last-name" data-mapping="customer[last_name]" required>
|
10
10
|
</div>
|
11
11
|
|
12
12
|
<div class="form-field">
|
13
13
|
<label for="p-address1" class="required">Address</label>
|
14
|
-
<input type="text" id="p-address1" class="p-address1" name="p-address1" data-mapping="address1" required>
|
14
|
+
<input type="text" id="p-address1" class="p-address1" name="p-address1" data-mapping="customer[address1] customer[billing_address]" required>
|
15
15
|
</div>
|
16
16
|
|
17
17
|
<div class="form-field">
|
18
18
|
<label for="p-city" class="required">City</label>
|
19
|
-
<input type="text" id="p-city" class="p-city" name="p-city" data-mapping="city" required>
|
19
|
+
<input type="text" id="p-city" class="p-city" name="p-city" data-mapping="customer[street_address][city]" required>
|
20
20
|
</div>
|
21
21
|
|
22
22
|
<div class="form-field">
|
23
23
|
<label for="p-state" class="required">State</label>
|
24
|
-
<input type="text" id="p-state" class="p-state" name="p-state" data-mapping="region" required>
|
24
|
+
<input type="text" id="p-state" class="p-state" name="p-state" data-mapping="customer[street_address][region]" required>
|
25
25
|
</div>
|
26
26
|
|
27
27
|
<div class="form-field">
|
@@ -31,12 +31,12 @@
|
|
31
31
|
|
32
32
|
<div class="form-field">
|
33
33
|
<label for="p-tel">Phone Number</label>
|
34
|
-
<input type="tel" id="p-tel" class="p-tel" name="p-tel" data-mapping="phone">
|
34
|
+
<input type="tel" id="p-tel" class="p-tel" name="p-tel" data-mapping="customer[phone]">
|
35
35
|
</div>
|
36
36
|
|
37
37
|
<div class="form-field">
|
38
38
|
<label for="u-email" class="required">Email</label>
|
39
|
-
<input type="email" id="u-email" class="u-email" name="u-email" data-mapping="email" required>
|
39
|
+
<input type="email" id="u-email" class="u-email" name="u-email" data-mapping="customer[email]" required>
|
40
40
|
</div>
|
41
41
|
|
42
42
|
<div class="form-field">
|
@@ -62,7 +62,7 @@
|
|
62
62
|
|
63
63
|
<div class="form-field">
|
64
64
|
<label for="p-card-exp-month" class="required">Expiration Date:</label>
|
65
|
-
<select id="p-card-exp-month" class="p-card-exp-month" name="p-card-exp-month" data-mapping="credit_card_exp_month" required>
|
65
|
+
<select id="p-card-exp-month" class="p-card-exp-month" name="p-card-exp-month" data-mapping="credit_card[credit_card_exp_month]" required>
|
66
66
|
<option value="1">1 - January</option>
|
67
67
|
<option value="2">2 - February</option>
|
68
68
|
<option value="3">3 - March</option>
|
@@ -5,16 +5,48 @@ describe Semantic::Mapper::Markup do
|
|
5
5
|
let(:html) { fixture('reservation.html') }
|
6
6
|
|
7
7
|
describe :map do
|
8
|
-
|
8
|
+
context 'nested mapping' do
|
9
|
+
subject { markup.map[:customer] }
|
10
|
+
its([:first_name]) { is_expected.to eq('p-first-name') }
|
11
|
+
its([:last_name]) { is_expected.to eq('p-last-name') }
|
12
|
+
its([:address1]) { is_expected.to eq('p-address1') }
|
13
|
+
its([:billing_address]) { is_expected.to eq('p-address1') }
|
9
14
|
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
15
|
+
it 'maps 3 levels deeps' do
|
16
|
+
expect(subject[:street_address][:city]).to eq('p-city')
|
17
|
+
expect(subject[:street_address][:region]).to eq('p-state')
|
18
|
+
end
|
19
|
+
end
|
20
|
+
context 'top level attributes' do
|
21
|
+
subject { markup.map }
|
22
|
+
its([:message]) { is_expected.to eq('e-content') }
|
23
|
+
its([:storage_unit_external_id]) { is_expected.to eq('p-storage-unit-external-id') }
|
24
|
+
its([:rental_rate]) { is_expected.to eq('p-rental-rate') }
|
25
|
+
its([:reservation_date]) { is_expected.to eq('p-reservation-date') }
|
26
|
+
its([:time_zone]) { is_expected.to eq('p-time-zone') }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
describe :map_hash do
|
31
|
+
[{value: 3, keys: %w(whatever foo), expected: {"whatever" => {"foo" => 3}}},
|
32
|
+
{value: 'semantic', keys: %w(customer address street1), expected: {"customer" => {"address" => {"street1" => "semantic"}}}},
|
33
|
+
{value: 'mapper', keys: ['jimmy'], expected: {"jimmy" => "mapper"}}
|
34
|
+
].each do |test_hash|
|
35
|
+
it "should map hash with value #{test_hash[:value]} and keys #{test_hash[:keys]} to #{test_hash[:expected]}" do
|
36
|
+
markup.send(:map_hash, test_hash[:value], test_hash[:keys])
|
37
|
+
expect(markup.mapped_hash).to eq(test_hash[:expected])
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
describe :build_keys do
|
43
|
+
[{data_mapping: 'jimmy[walker]', expected: %w(jimmy walker)},
|
44
|
+
{data_mapping: 'jimmy[walker][foo]', expected: %w(jimmy walker foo)},
|
45
|
+
{data_mapping: 'jimmy', expected: %w(jimmy)}
|
46
|
+
].each do |test_hash|
|
47
|
+
it "should build #{test_hash[:expected]} from #{test_hash[:data_mapping]}" do
|
48
|
+
expect(markup.send(:build_keys, test_hash[:data_mapping])).to eq(test_hash[:expected])
|
49
|
+
end
|
50
|
+
end
|
19
51
|
end
|
20
52
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: semantic-mapper
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Perry Hertler
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-12-
|
11
|
+
date: 2014-12-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|