data_attributes 1.0.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.
- checksums.yaml +7 -0
- data/.gitignore +7 -0
- data/.rspec +2 -0
- data/Gemfile +3 -0
- data/MIT-LICENSE +20 -0
- data/README.mdown +75 -0
- data/Rakefile +10 -0
- data/VERSION +1 -0
- data/data_attributes.gemspec +24 -0
- data/lib/data_attributes/model.rb +45 -0
- data/lib/data_attributes/view.rb +55 -0
- data/lib/data_attributes.rb +8 -0
- data/lib/spec_helper.rb +27 -0
- data/spec/data_attributes/model_spec.rb +125 -0
- data/spec/data_attributes/view_spec.rb +178 -0
- data/spec/spec_helper.rb +26 -0
- data/spec/support/mocks/article.rb +15 -0
- data/spec/support/mocks/category.rb +7 -0
- data/spec/support/mocks/content.rb +7 -0
- data/spec/support/mocks/view.rb +5 -0
- metadata +149 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 13d87816eec1c6d0c9d3f23f54b26d9029104de8
|
4
|
+
data.tar.gz: ba5bf26281792856d44f9abc2e259ee21fa9fd62
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 37de7c74094ec28ec7d84c56a2e6a4376d0dbf965e0d9df960e96df0c74698c378439b710028d28082dae48fd65cc1f8714b0d5239f37c6cf043dec1450a0c81
|
7
|
+
data.tar.gz: b12317c608492d08a89adc4fd7024ec7c17fad9c55f74eb688af66181bb5a8e76f49f37bebbdcb39bf84fd6309c4c478af30ba4e389b3d4d81152a54ad1cdde3
|
data/.gitignore
ADDED
data/.rspec
ADDED
data/Gemfile
ADDED
data/MIT-LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2017 Alexis Toulotte
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.mdown
ADDED
@@ -0,0 +1,75 @@
|
|
1
|
+
# DataAttributes
|
2
|
+
|
3
|
+
Convenience helpers to provide [HTML data attributes](https://developer.mozilla.org/en-US/docs/Learn/HTML/Howto/Use_data_attributes)
|
4
|
+
from model to view.
|
5
|
+
|
6
|
+
## Setup
|
7
|
+
|
8
|
+
Just add this into your `Gemfile`:
|
9
|
+
|
10
|
+
```ruby
|
11
|
+
gem 'data_attributes'
|
12
|
+
```
|
13
|
+
|
14
|
+
If you want to take benefits of `content_tag_for` and `div_for` methods, add
|
15
|
+
also [record_tag_helper](https://rubygems.org/gems/record_tag_helper) into
|
16
|
+
your `Gemfile`:
|
17
|
+
|
18
|
+
```ruby
|
19
|
+
gem 'record_tag_helper'
|
20
|
+
```
|
21
|
+
|
22
|
+
Then, just run a `bundle install`.
|
23
|
+
|
24
|
+
## Usage
|
25
|
+
|
26
|
+
In your model just add `DataAttributes::Model` mixin:
|
27
|
+
|
28
|
+
```ruby
|
29
|
+
class Article
|
30
|
+
|
31
|
+
include DataAttributes::Model
|
32
|
+
|
33
|
+
end
|
34
|
+
```
|
35
|
+
|
36
|
+
Then, you can define you model's data attributes that are included into view:
|
37
|
+
|
38
|
+
```ruby
|
39
|
+
class Article
|
40
|
+
|
41
|
+
include DataAttributes::Model
|
42
|
+
|
43
|
+
data_attribute :id, :title
|
44
|
+
|
45
|
+
end
|
46
|
+
```
|
47
|
+
|
48
|
+
Then you must add `DataAttribute::View` into Rails `ApplicationHelper`:
|
49
|
+
|
50
|
+
```ruby
|
51
|
+
module ApplicationHelper
|
52
|
+
|
53
|
+
include DataAttribute::View
|
54
|
+
|
55
|
+
end
|
56
|
+
```
|
57
|
+
|
58
|
+
Then `content_tag_for` and `div_for` methods from [record_tag_helper](https://rubygems.org/gems/record_tag_helper)
|
59
|
+
gem will add model's data attributes into view:
|
60
|
+
|
61
|
+
```erb
|
62
|
+
<%= div_for @article do %>
|
63
|
+
<!-- <div class="article" data-id="42" data-title="Hello!"> -->
|
64
|
+
```
|
65
|
+
|
66
|
+
You can also pass data attributes directly to `content_tag` method:
|
67
|
+
|
68
|
+
```erb
|
69
|
+
<%= content_tag :div, id: 'articles', data: { count: 28 } do %>
|
70
|
+
```
|
71
|
+
|
72
|
+
## Executing test suite
|
73
|
+
|
74
|
+
This project is fully tested with [Rspec 3](http://github.com/rspec/rspec).
|
75
|
+
Just run `bundle exec rake` (after a `bundle install`).
|
data/Rakefile
ADDED
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
1.0.0
|
@@ -0,0 +1,24 @@
|
|
1
|
+
Gem::Specification.new do |s|
|
2
|
+
s.name = 'data_attributes'
|
3
|
+
s.version = File.read("#{File.dirname(__FILE__)}/VERSION").strip
|
4
|
+
s.platform = Gem::Platform::RUBY
|
5
|
+
s.author = 'Alexis Toulotte'
|
6
|
+
s.email = 'al@alweb.org'
|
7
|
+
s.homepage = 'https://github.com/alexistoulotte/data_attributes'
|
8
|
+
s.summary = 'Helpers for HTML data attributes'
|
9
|
+
s.description = 'Convenience helpers to provide HTML data attributes from model to view'
|
10
|
+
s.license = 'MIT'
|
11
|
+
|
12
|
+
s.files = `git ls-files`.split("\n")
|
13
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
14
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
15
|
+
s.require_paths = ['lib']
|
16
|
+
|
17
|
+
s.required_ruby_version = '>= 2.0.0'
|
18
|
+
|
19
|
+
s.add_dependency 'activesupport', '>= 4.1.0', '< 6.0.0'
|
20
|
+
|
21
|
+
s.add_development_dependency 'byebug', '>= 9.0.0', '< 10.0.0'
|
22
|
+
s.add_development_dependency 'rake', '>= 12.0.0', '< 13.0.0'
|
23
|
+
s.add_development_dependency 'rspec', '>= 3.5.0', '< 3.6.0'
|
24
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
module DataAttributes
|
2
|
+
|
3
|
+
module Model
|
4
|
+
|
5
|
+
extend ActiveSupport::Concern
|
6
|
+
|
7
|
+
class_methods do
|
8
|
+
|
9
|
+
def data_attribute(*attributes)
|
10
|
+
attributes = (__data_attributes + attributes).flatten.map(&:to_sym).uniq
|
11
|
+
class_eval(%Q{
|
12
|
+
class << self
|
13
|
+
private
|
14
|
+
|
15
|
+
def __data_attributes
|
16
|
+
#{attributes.inspect}
|
17
|
+
end
|
18
|
+
end
|
19
|
+
})
|
20
|
+
end
|
21
|
+
|
22
|
+
def data_attributes
|
23
|
+
super_attributes = superclass && superclass.respond_to?(:__data_attributes, true) ? superclass.send(:__data_attributes) : []
|
24
|
+
(super_attributes + __data_attributes).uniq.sort
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
def __data_attributes
|
30
|
+
[]
|
31
|
+
end
|
32
|
+
|
33
|
+
end
|
34
|
+
|
35
|
+
def data_attributes
|
36
|
+
{}.tap do |attributes|
|
37
|
+
self.class.data_attributes.each do |attribute|
|
38
|
+
attributes[attribute] = send(attribute) if respond_to?(attribute, true)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
module DataAttributes
|
2
|
+
|
3
|
+
module View
|
4
|
+
|
5
|
+
def content_tag_for_single_record(tag_name, record, prefix, options, &block)
|
6
|
+
options, prefix = prefix, nil if prefix.is_a?(Hash)
|
7
|
+
options ||= {}
|
8
|
+
options[:data] ||= {}
|
9
|
+
options[:data].reverse_merge!(record.data_attributes) if record.is_a?(DataAttributes::Model)
|
10
|
+
options.reverse_merge!(class: record.class.model_name.singular.dasherize)
|
11
|
+
if block.arity == 0
|
12
|
+
content_tag(tag_name, capture(&block), options)
|
13
|
+
else
|
14
|
+
content_tag(tag_name, capture(record, &block), options)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
def data_attribute_value(value, options = {})
|
19
|
+
if value.is_a?(String) || value.is_a?(Symbol)
|
20
|
+
options[:prefix_strings] ? "string:#{value}" : value.to_s
|
21
|
+
elsif value.is_a?(Numeric)
|
22
|
+
value
|
23
|
+
elsif value.nil?
|
24
|
+
nil
|
25
|
+
elsif value.is_a?(Time)
|
26
|
+
value.to_i
|
27
|
+
elsif value.is_a?(Date)
|
28
|
+
value.strftime('%Y/%m/%d')
|
29
|
+
elsif value.is_a?(TrueClass) || value.is_a?(FalseClass)
|
30
|
+
options[:raw] ? value : value.to_s
|
31
|
+
elsif value.is_a?(Array)
|
32
|
+
value = value.map { |v| data_attribute_value(v, options.merge(raw: true)) }
|
33
|
+
options[:raw] ? value : value.to_json
|
34
|
+
elsif value.is_a?(Hash)
|
35
|
+
value = value.each_with_object({}) { |(k, v), hash| hash[k.to_s.gsub(/^_+/, '').gsub(/\?$/, '').camelize(:lower)] = data_attribute_value(v, options.merge(raw: true)) }
|
36
|
+
options[:raw] ? value : value.to_json
|
37
|
+
elsif value.is_a?(DataAttributes::Model)
|
38
|
+
data_attribute_value(value.data_attributes, options)
|
39
|
+
else
|
40
|
+
raise "Can't convert object of class #{value.class} in data attributes"
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
def tag_options(options, escape = true)
|
45
|
+
(options.delete(:data) || options.delete('data') || {}).each do |key, value|
|
46
|
+
value = data_attribute_value(value)
|
47
|
+
value = html_escape(value) if escape
|
48
|
+
options["data-#{key.to_s.gsub(/^_+/, '').gsub(/\?$/, '').dasherize}"] = value
|
49
|
+
end
|
50
|
+
super
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
54
|
+
|
55
|
+
end
|
data/lib/spec_helper.rb
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
require File.expand_path("#{__dir__}/../lib/data_attributes")
|
2
|
+
require 'byebug'
|
3
|
+
|
4
|
+
# Support
|
5
|
+
require "#{__dir__}/support/mocks/content"
|
6
|
+
require "#{__dir__}/support/mocks/category"
|
7
|
+
require "#{__dir__}/support/mocks/article"
|
8
|
+
require "#{__dir__}/support/mocks/view"
|
9
|
+
|
10
|
+
RSpec.configure do |config|
|
11
|
+
config.raise_errors_for_deprecations!
|
12
|
+
|
13
|
+
config.before(:each) do
|
14
|
+
[Article, Category, Content].each do |mock_class|
|
15
|
+
next unless mock_class.respond_to?(:__data_attributes, true)
|
16
|
+
mock_class.class_eval(%Q{
|
17
|
+
class << self
|
18
|
+
private
|
19
|
+
|
20
|
+
def __data_attributes
|
21
|
+
[]
|
22
|
+
end
|
23
|
+
end
|
24
|
+
})
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,125 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe DataAttributes::Model do
|
4
|
+
|
5
|
+
describe '.data_attribute' do
|
6
|
+
|
7
|
+
it 'adds given attributes to data attributes' do
|
8
|
+
expect {
|
9
|
+
Article.data_attribute(:id)
|
10
|
+
}.to change { Article.data_attributes }.from([]).to([:id])
|
11
|
+
end
|
12
|
+
|
13
|
+
it 'removes doubloons' do
|
14
|
+
Article.data_attribute(:id)
|
15
|
+
expect {
|
16
|
+
Article.data_attribute(:id)
|
17
|
+
}.not_to change { Article.data_attributes }
|
18
|
+
expect(Article.send(:__data_attributes)).to eq([:id])
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'removes doubloons (if given as string)' do
|
22
|
+
Article.data_attribute(:id)
|
23
|
+
expect {
|
24
|
+
Article.data_attribute('id')
|
25
|
+
}.not_to change { Article.data_attributes }
|
26
|
+
expect(Article.send(:__data_attributes)).to eq([:id])
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'converts attributes to symbols' do
|
30
|
+
Article.data_attribute('id')
|
31
|
+
expect(Article.data_attributes).to eq([:id])
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'accepts arrays' do
|
35
|
+
Article.data_attribute(['id', ['category']], :body)
|
36
|
+
expect(Article.data_attributes).to eq([:body, :category, :id])
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
describe '.__data_attributes' do
|
42
|
+
|
43
|
+
it 'is a private method' do
|
44
|
+
expect(Article.respond_to?(:__data_attributes)).to be(false)
|
45
|
+
expect(Article.respond_to?(:__data_attributes, true)).to be(true)
|
46
|
+
end
|
47
|
+
|
48
|
+
it 'is a private method even after a call to .data_attribute' do
|
49
|
+
Article.data_attribute(:id)
|
50
|
+
expect(Article.respond_to?(:__data_attributes)).to be(false)
|
51
|
+
expect(Article.respond_to?(:__data_attributes, true)).to be(true)
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
|
56
|
+
describe '.data_attributes' do
|
57
|
+
|
58
|
+
it 'is an empty array by default' do
|
59
|
+
expect(Article.data_attributes).to eq([])
|
60
|
+
end
|
61
|
+
|
62
|
+
it "can't be changed" do
|
63
|
+
Article.data_attribute(:id)
|
64
|
+
expect {
|
65
|
+
Article.data_attributes.clear
|
66
|
+
}.not_to change { Article.data_attribute }
|
67
|
+
end
|
68
|
+
|
69
|
+
it 'is correct with subclasses' do
|
70
|
+
Content.data_attribute(:body, :id)
|
71
|
+
expect(Content.data_attributes).to eq([:body, :id])
|
72
|
+
expect(Article.data_attributes).to eq([:body, :id])
|
73
|
+
|
74
|
+
Article.data_attribute(:title)
|
75
|
+
expect(Content.data_attributes).to eq([:body, :id])
|
76
|
+
expect(Article.data_attributes).to eq([:body, :id, :title])
|
77
|
+
end
|
78
|
+
|
79
|
+
it 'removes doubloons with subclasses' do
|
80
|
+
Content.data_attribute(:body, :id)
|
81
|
+
expect(Article.data_attributes).to eq([:body, :id])
|
82
|
+
Article.data_attribute(:title, :id, :body)
|
83
|
+
expect(Article.data_attributes).to eq([:body, :id, :title])
|
84
|
+
end
|
85
|
+
|
86
|
+
it 'is sorted' do
|
87
|
+
Article.data_attribute(:id, :body)
|
88
|
+
expect(Article.data_attributes).to eq([:body, :id])
|
89
|
+
end
|
90
|
+
|
91
|
+
it 'is sorted with subclasses' do
|
92
|
+
Content.data_attribute(:bar, :foo)
|
93
|
+
Article.data_attribute(:body)
|
94
|
+
expect(Article.data_attributes).to eq([:bar, :body, :foo])
|
95
|
+
end
|
96
|
+
|
97
|
+
end
|
98
|
+
|
99
|
+
describe '#data_attributes' do
|
100
|
+
|
101
|
+
it 'returns an hash of instance data attributes' do
|
102
|
+
Article.data_attribute(:id, :body)
|
103
|
+
article = Article.new
|
104
|
+
article.body = 'This is the body'
|
105
|
+
article.id = 42
|
106
|
+
expect(article.data_attributes).to eq({ body: 'This is the body', id: 42 })
|
107
|
+
end
|
108
|
+
|
109
|
+
it 'does not fail if method does not exist' do
|
110
|
+
Article.data_attribute(:id, :foo)
|
111
|
+
article = Article.new
|
112
|
+
article.id = 42
|
113
|
+
expect(article.data_attributes).to eq({ id: 42 })
|
114
|
+
end
|
115
|
+
|
116
|
+
it 'does not fail if method is private' do
|
117
|
+
Article.data_attribute(:published)
|
118
|
+
article = Article.new
|
119
|
+
article.published = true
|
120
|
+
expect(article.data_attributes).to eq({ published: true })
|
121
|
+
end
|
122
|
+
|
123
|
+
end
|
124
|
+
|
125
|
+
end
|
@@ -0,0 +1,178 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe DataAttributes::View do
|
4
|
+
|
5
|
+
let(:view) { View.new }
|
6
|
+
|
7
|
+
describe '#data_attribute_value' do
|
8
|
+
|
9
|
+
it 'raise an error if given object is not supported' do
|
10
|
+
expect {
|
11
|
+
view.data_attribute_value(Object.new)
|
12
|
+
}.to raise_error("Can't convert object of class Object in data attributes")
|
13
|
+
end
|
14
|
+
|
15
|
+
context 'with string' do
|
16
|
+
|
17
|
+
it 'returns given value' do
|
18
|
+
expect(view.data_attribute_value('hello world')).to eq('hello world')
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'accepts :prefix_strings option' do
|
22
|
+
expect(view.data_attribute_value('hello world', prefix_strings: true)).to eq('string:hello world')
|
23
|
+
expect(view.data_attribute_value('hello world', prefix_strings: false)).to eq('hello world')
|
24
|
+
end
|
25
|
+
|
26
|
+
end
|
27
|
+
|
28
|
+
context 'with symbol' do
|
29
|
+
|
30
|
+
it 'returns given value' do
|
31
|
+
expect(view.data_attribute_value(:hello)).to eq('hello')
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'accepts :prefix_strings option' do
|
35
|
+
expect(view.data_attribute_value(:hello, prefix_strings: true)).to eq('string:hello')
|
36
|
+
expect(view.data_attribute_value(:hello, prefix_strings: false)).to eq('hello')
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
context 'with integer' do
|
42
|
+
|
43
|
+
it 'returns given value' do
|
44
|
+
expect(view.data_attribute_value(42)).to eq(42)
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
48
|
+
|
49
|
+
context 'with float' do
|
50
|
+
|
51
|
+
it 'returns given value' do
|
52
|
+
expect(view.data_attribute_value(42.28)).to eq(42.28)
|
53
|
+
end
|
54
|
+
|
55
|
+
end
|
56
|
+
|
57
|
+
context 'with nil' do
|
58
|
+
|
59
|
+
it 'returns nil' do
|
60
|
+
expect(view.data_attribute_value(nil)).to be(nil)
|
61
|
+
end
|
62
|
+
|
63
|
+
end
|
64
|
+
|
65
|
+
context 'with Time' do
|
66
|
+
|
67
|
+
it 'returns time as integer' do
|
68
|
+
expect(view.data_attribute_value(Time.new(2017, 2, 10, 4, 1, 2))).to eq(1486659662)
|
69
|
+
end
|
70
|
+
|
71
|
+
end
|
72
|
+
|
73
|
+
context 'with true' do
|
74
|
+
|
75
|
+
it 'returns "true"' do
|
76
|
+
expect(view.data_attribute_value(true)).to eq('true')
|
77
|
+
end
|
78
|
+
|
79
|
+
it 'accepts :raw option' do
|
80
|
+
expect(view.data_attribute_value(true, raw: true)).to eq(true)
|
81
|
+
end
|
82
|
+
|
83
|
+
end
|
84
|
+
|
85
|
+
context 'with false' do
|
86
|
+
|
87
|
+
it 'returns "false"' do
|
88
|
+
expect(view.data_attribute_value(false)).to eq('false')
|
89
|
+
end
|
90
|
+
|
91
|
+
it 'accepts :raw option' do
|
92
|
+
expect(view.data_attribute_value(false, raw: true)).to eq(false)
|
93
|
+
end
|
94
|
+
|
95
|
+
end
|
96
|
+
|
97
|
+
context 'with array' do
|
98
|
+
|
99
|
+
it 'returns array as JSON' do
|
100
|
+
expect(view.data_attribute_value([42, :bam, true, Time.new(2017, 2, 10, 4, 1, 2)])).to eq('[42,"bam",true,1486659662]')
|
101
|
+
end
|
102
|
+
|
103
|
+
it 'accepts :prefix_strings option' do
|
104
|
+
expect(view.data_attribute_value([42, :bam, true, Time.new(2017, 2, 10, 4, 1, 2)], prefix_strings: true)).to eq('[42,"string:bam",true,1486659662]')
|
105
|
+
end
|
106
|
+
|
107
|
+
it 'is correct with arrays of arrays' do
|
108
|
+
expect(view.data_attribute_value([42, [:bam, true]])).to eq('[42,["bam",true]]')
|
109
|
+
end
|
110
|
+
|
111
|
+
it 'is correct with arrays of hashes' do
|
112
|
+
expect(view.data_attribute_value([44, { '_category_id?' => 28 }])).to eq('[44,{"categoryId":28}]')
|
113
|
+
end
|
114
|
+
|
115
|
+
end
|
116
|
+
|
117
|
+
context 'with hash' do
|
118
|
+
|
119
|
+
it 'returns hash as JSON' do
|
120
|
+
expect(view.data_attribute_value({ id: 42, 'message' => :bam, date: Time.new(2017, 2, 10, 4, 1, 2), valid: true })).to eq('{"id":42,"message":"bam","date":1486659662,"valid":true}')
|
121
|
+
end
|
122
|
+
|
123
|
+
it 'accepts :prefix_strings option' do
|
124
|
+
expect(view.data_attribute_value({ id: 42, 'message' => :bam, date: Time.new(2017, 2, 10, 4, 1, 2), valid: true }, prefix_strings: true)).to eq('{"id":42,"message":"string:bam","date":1486659662,"valid":true}')
|
125
|
+
end
|
126
|
+
|
127
|
+
it 'converts keys correctly' do
|
128
|
+
expect(view.data_attribute_value({ '_category_id?' => 28 })).to eq('{"categoryId":28}')
|
129
|
+
end
|
130
|
+
|
131
|
+
end
|
132
|
+
|
133
|
+
context 'with a date' do
|
134
|
+
|
135
|
+
it 'returns date formatted' do
|
136
|
+
expect(view.data_attribute_value(Date.new(2017, 4, 27))).to eq('2017/04/27')
|
137
|
+
end
|
138
|
+
|
139
|
+
end
|
140
|
+
|
141
|
+
context 'with a data attributes model' do
|
142
|
+
|
143
|
+
it 'returns hash of attributes as JSON' do
|
144
|
+
Article.data_attribute(:id, :body)
|
145
|
+
article = Article.new
|
146
|
+
article.body = 'This is the body'
|
147
|
+
article.id = 28
|
148
|
+
expect(view.data_attribute_value(article)).to eq('{"body":"This is the body","id":28}')
|
149
|
+
end
|
150
|
+
|
151
|
+
it 'accepts :prefix_strings option' do
|
152
|
+
Article.data_attribute(:id, :body)
|
153
|
+
article = Article.new
|
154
|
+
article.body = 'This is the body'
|
155
|
+
article.id = 28
|
156
|
+
expect(view.data_attribute_value(article, prefix_strings: true)).to eq('{"body":"string:This is the body","id":28}')
|
157
|
+
end
|
158
|
+
|
159
|
+
it 'is correct with a nested data attributes object' do
|
160
|
+
Article.data_attribute(:id, :body, :category)
|
161
|
+
Category.data_attribute(:id, :title)
|
162
|
+
|
163
|
+
category = Category.new
|
164
|
+
category.id = 20
|
165
|
+
category.title = 'Books'
|
166
|
+
|
167
|
+
article = Article.new
|
168
|
+
article.body = 'This is the body'
|
169
|
+
article.category = category
|
170
|
+
|
171
|
+
expect(view.data_attribute_value(article)).to eq('{"body":"This is the body","category":{"id":20,"title":"Books"},"id":null}')
|
172
|
+
end
|
173
|
+
|
174
|
+
end
|
175
|
+
|
176
|
+
end
|
177
|
+
|
178
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
require File.expand_path("#{__dir__}/../lib/data_attributes")
|
2
|
+
require 'byebug'
|
3
|
+
|
4
|
+
# Support
|
5
|
+
require "#{__dir__}/support/mocks/content"
|
6
|
+
require "#{__dir__}/support/mocks/article"
|
7
|
+
require "#{__dir__}/support/mocks/category"
|
8
|
+
require "#{__dir__}/support/mocks/view"
|
9
|
+
|
10
|
+
RSpec.configure do |config|
|
11
|
+
config.raise_errors_for_deprecations!
|
12
|
+
|
13
|
+
config.before(:each) do
|
14
|
+
[Article, Category, Content].each do |mock_class|
|
15
|
+
mock_class.class_eval(%Q{
|
16
|
+
class << self
|
17
|
+
private
|
18
|
+
|
19
|
+
def __data_attributes
|
20
|
+
[]
|
21
|
+
end
|
22
|
+
end
|
23
|
+
})
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
metadata
ADDED
@@ -0,0 +1,149 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: data_attributes
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 1.0.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Alexis Toulotte
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2017-03-06 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: activesupport
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ">="
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: 4.1.0
|
20
|
+
- - "<"
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: 6.0.0
|
23
|
+
type: :runtime
|
24
|
+
prerelease: false
|
25
|
+
version_requirements: !ruby/object:Gem::Requirement
|
26
|
+
requirements:
|
27
|
+
- - ">="
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: 4.1.0
|
30
|
+
- - "<"
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: 6.0.0
|
33
|
+
- !ruby/object:Gem::Dependency
|
34
|
+
name: byebug
|
35
|
+
requirement: !ruby/object:Gem::Requirement
|
36
|
+
requirements:
|
37
|
+
- - ">="
|
38
|
+
- !ruby/object:Gem::Version
|
39
|
+
version: 9.0.0
|
40
|
+
- - "<"
|
41
|
+
- !ruby/object:Gem::Version
|
42
|
+
version: 10.0.0
|
43
|
+
type: :development
|
44
|
+
prerelease: false
|
45
|
+
version_requirements: !ruby/object:Gem::Requirement
|
46
|
+
requirements:
|
47
|
+
- - ">="
|
48
|
+
- !ruby/object:Gem::Version
|
49
|
+
version: 9.0.0
|
50
|
+
- - "<"
|
51
|
+
- !ruby/object:Gem::Version
|
52
|
+
version: 10.0.0
|
53
|
+
- !ruby/object:Gem::Dependency
|
54
|
+
name: rake
|
55
|
+
requirement: !ruby/object:Gem::Requirement
|
56
|
+
requirements:
|
57
|
+
- - ">="
|
58
|
+
- !ruby/object:Gem::Version
|
59
|
+
version: 12.0.0
|
60
|
+
- - "<"
|
61
|
+
- !ruby/object:Gem::Version
|
62
|
+
version: 13.0.0
|
63
|
+
type: :development
|
64
|
+
prerelease: false
|
65
|
+
version_requirements: !ruby/object:Gem::Requirement
|
66
|
+
requirements:
|
67
|
+
- - ">="
|
68
|
+
- !ruby/object:Gem::Version
|
69
|
+
version: 12.0.0
|
70
|
+
- - "<"
|
71
|
+
- !ruby/object:Gem::Version
|
72
|
+
version: 13.0.0
|
73
|
+
- !ruby/object:Gem::Dependency
|
74
|
+
name: rspec
|
75
|
+
requirement: !ruby/object:Gem::Requirement
|
76
|
+
requirements:
|
77
|
+
- - ">="
|
78
|
+
- !ruby/object:Gem::Version
|
79
|
+
version: 3.5.0
|
80
|
+
- - "<"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: 3.6.0
|
83
|
+
type: :development
|
84
|
+
prerelease: false
|
85
|
+
version_requirements: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - ">="
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: 3.5.0
|
90
|
+
- - "<"
|
91
|
+
- !ruby/object:Gem::Version
|
92
|
+
version: 3.6.0
|
93
|
+
description: Convenience helpers to provide HTML data attributes from model to view
|
94
|
+
email: al@alweb.org
|
95
|
+
executables: []
|
96
|
+
extensions: []
|
97
|
+
extra_rdoc_files: []
|
98
|
+
files:
|
99
|
+
- ".gitignore"
|
100
|
+
- ".rspec"
|
101
|
+
- Gemfile
|
102
|
+
- MIT-LICENSE
|
103
|
+
- README.mdown
|
104
|
+
- Rakefile
|
105
|
+
- VERSION
|
106
|
+
- data_attributes.gemspec
|
107
|
+
- lib/data_attributes.rb
|
108
|
+
- lib/data_attributes/model.rb
|
109
|
+
- lib/data_attributes/view.rb
|
110
|
+
- lib/spec_helper.rb
|
111
|
+
- spec/data_attributes/model_spec.rb
|
112
|
+
- spec/data_attributes/view_spec.rb
|
113
|
+
- spec/spec_helper.rb
|
114
|
+
- spec/support/mocks/article.rb
|
115
|
+
- spec/support/mocks/category.rb
|
116
|
+
- spec/support/mocks/content.rb
|
117
|
+
- spec/support/mocks/view.rb
|
118
|
+
homepage: https://github.com/alexistoulotte/data_attributes
|
119
|
+
licenses:
|
120
|
+
- MIT
|
121
|
+
metadata: {}
|
122
|
+
post_install_message:
|
123
|
+
rdoc_options: []
|
124
|
+
require_paths:
|
125
|
+
- lib
|
126
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
127
|
+
requirements:
|
128
|
+
- - ">="
|
129
|
+
- !ruby/object:Gem::Version
|
130
|
+
version: 2.0.0
|
131
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
132
|
+
requirements:
|
133
|
+
- - ">="
|
134
|
+
- !ruby/object:Gem::Version
|
135
|
+
version: '0'
|
136
|
+
requirements: []
|
137
|
+
rubyforge_project:
|
138
|
+
rubygems_version: 2.5.2
|
139
|
+
signing_key:
|
140
|
+
specification_version: 4
|
141
|
+
summary: Helpers for HTML data attributes
|
142
|
+
test_files:
|
143
|
+
- spec/data_attributes/model_spec.rb
|
144
|
+
- spec/data_attributes/view_spec.rb
|
145
|
+
- spec/spec_helper.rb
|
146
|
+
- spec/support/mocks/article.rb
|
147
|
+
- spec/support/mocks/category.rb
|
148
|
+
- spec/support/mocks/content.rb
|
149
|
+
- spec/support/mocks/view.rb
|