green_monkey 0.1
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/.gitignore +3 -0
- data/.rspec +1 -0
- data/.travis.yml +8 -0
- data/Gemfile +3 -0
- data/Gemfile.haml-edge +4 -0
- data/Gemfile.lock +131 -0
- data/Gemfile.rails-3.0.11 +4 -0
- data/Gemfile.rails-3.1.3 +4 -0
- data/README.md +152 -0
- data/Rakefile +15 -0
- data/green_monkey.gemspec +29 -0
- data/lib/green_monkey/ext/action_view.rb +22 -0
- data/lib/green_monkey/ext/active_model.rb +29 -0
- data/lib/green_monkey/ext/haml.rb +67 -0
- data/lib/green_monkey/ext/mida.rb +34 -0
- data/lib/green_monkey/ext/view_helper.rb +60 -0
- data/lib/green_monkey/railtie.rb +17 -0
- data/lib/green_monkey.rb +3 -0
- data/spec/haml_spec.rb +85 -0
- data/spec/mida_spec.rb +18 -0
- data/spec/model_spec.rb +19 -0
- data/spec/post.haml +9 -0
- data/spec/spec_helper.rb +54 -0
- data/tmp/rails/config/database.yml +9 -0
- data/tmp/rails/config/environments/development.rb +0 -0
- metadata +158 -0
data/.gitignore
ADDED
data/.rspec
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
# just let autotest know about rspec
|
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/Gemfile.haml-edge
ADDED
data/Gemfile.lock
ADDED
@@ -0,0 +1,131 @@
|
|
1
|
+
GIT
|
2
|
+
remote: git://github.com/Paxa/chronic_duration.git
|
3
|
+
revision: 8c0d0e101bdbaf2b2299f33e7bfa880b0885a017
|
4
|
+
ref: 8c0d0e101b
|
5
|
+
specs:
|
6
|
+
chronic_duration (0.9.6)
|
7
|
+
numerizer (~> 0.1.1)
|
8
|
+
|
9
|
+
PATH
|
10
|
+
remote: .
|
11
|
+
specs:
|
12
|
+
green_monkey (0.1)
|
13
|
+
chronic_duration
|
14
|
+
haml (>= 3.1.0)
|
15
|
+
mida (>= 0.3.3)
|
16
|
+
rails (>= 3.0.0)
|
17
|
+
|
18
|
+
GEM
|
19
|
+
remote: http://rubygems.org/
|
20
|
+
specs:
|
21
|
+
actionmailer (3.1.3)
|
22
|
+
actionpack (= 3.1.3)
|
23
|
+
mail (~> 2.3.0)
|
24
|
+
actionpack (3.1.3)
|
25
|
+
activemodel (= 3.1.3)
|
26
|
+
activesupport (= 3.1.3)
|
27
|
+
builder (~> 3.0.0)
|
28
|
+
erubis (~> 2.7.0)
|
29
|
+
i18n (~> 0.6)
|
30
|
+
rack (~> 1.3.5)
|
31
|
+
rack-cache (~> 1.1)
|
32
|
+
rack-mount (~> 0.8.2)
|
33
|
+
rack-test (~> 0.6.1)
|
34
|
+
sprockets (~> 2.0.3)
|
35
|
+
activemodel (3.1.3)
|
36
|
+
activesupport (= 3.1.3)
|
37
|
+
builder (~> 3.0.0)
|
38
|
+
i18n (~> 0.6)
|
39
|
+
activerecord (3.1.3)
|
40
|
+
activemodel (= 3.1.3)
|
41
|
+
activesupport (= 3.1.3)
|
42
|
+
arel (~> 2.2.1)
|
43
|
+
tzinfo (~> 0.3.29)
|
44
|
+
activeresource (3.1.3)
|
45
|
+
activemodel (= 3.1.3)
|
46
|
+
activesupport (= 3.1.3)
|
47
|
+
activesupport (3.1.3)
|
48
|
+
multi_json (~> 1.0)
|
49
|
+
arel (2.2.1)
|
50
|
+
blankslate (2.1.2.4)
|
51
|
+
builder (3.0.0)
|
52
|
+
diff-lcs (1.1.3)
|
53
|
+
erubis (2.7.0)
|
54
|
+
haml (3.1.3)
|
55
|
+
hike (1.2.1)
|
56
|
+
i18n (0.6.0)
|
57
|
+
json (1.6.1)
|
58
|
+
mail (2.3.0)
|
59
|
+
i18n (>= 0.4.0)
|
60
|
+
mime-types (~> 1.16)
|
61
|
+
treetop (~> 1.4.8)
|
62
|
+
mida (0.3.3)
|
63
|
+
blankslate
|
64
|
+
nokogiri (>= 1.5)
|
65
|
+
mime-types (1.17.2)
|
66
|
+
multi_json (1.0.3)
|
67
|
+
nokogiri (1.5.0)
|
68
|
+
numerizer (0.1.1)
|
69
|
+
polyglot (0.3.3)
|
70
|
+
rack (1.3.5)
|
71
|
+
rack-cache (1.1)
|
72
|
+
rack (>= 0.4)
|
73
|
+
rack-mount (0.8.3)
|
74
|
+
rack (>= 1.0.0)
|
75
|
+
rack-ssl (1.3.2)
|
76
|
+
rack
|
77
|
+
rack-test (0.6.1)
|
78
|
+
rack (>= 1.0)
|
79
|
+
rails (3.1.3)
|
80
|
+
actionmailer (= 3.1.3)
|
81
|
+
actionpack (= 3.1.3)
|
82
|
+
activerecord (= 3.1.3)
|
83
|
+
activeresource (= 3.1.3)
|
84
|
+
activesupport (= 3.1.3)
|
85
|
+
bundler (~> 1.0)
|
86
|
+
railties (= 3.1.3)
|
87
|
+
railties (3.1.3)
|
88
|
+
actionpack (= 3.1.3)
|
89
|
+
activesupport (= 3.1.3)
|
90
|
+
rack-ssl (~> 1.3.2)
|
91
|
+
rake (>= 0.8.7)
|
92
|
+
rdoc (~> 3.4)
|
93
|
+
thor (~> 0.14.6)
|
94
|
+
rake (0.9.2.2)
|
95
|
+
rdoc (3.11)
|
96
|
+
json (~> 1.4)
|
97
|
+
rspec (2.7.0)
|
98
|
+
rspec-core (~> 2.7.0)
|
99
|
+
rspec-expectations (~> 2.7.0)
|
100
|
+
rspec-mocks (~> 2.7.0)
|
101
|
+
rspec-core (2.7.1)
|
102
|
+
rspec-expectations (2.7.0)
|
103
|
+
diff-lcs (~> 1.1.2)
|
104
|
+
rspec-mocks (2.7.0)
|
105
|
+
rspec-rails (2.7.0)
|
106
|
+
actionpack (~> 3.0)
|
107
|
+
activesupport (~> 3.0)
|
108
|
+
railties (~> 3.0)
|
109
|
+
rspec (~> 2.7.0)
|
110
|
+
sprockets (2.0.3)
|
111
|
+
hike (~> 1.2)
|
112
|
+
rack (~> 1.0)
|
113
|
+
tilt (~> 1.1, != 1.3.0)
|
114
|
+
sqlite3 (1.3.4)
|
115
|
+
thor (0.14.6)
|
116
|
+
tilt (1.3.3)
|
117
|
+
treetop (1.4.10)
|
118
|
+
polyglot
|
119
|
+
polyglot (>= 0.3.1)
|
120
|
+
tzinfo (0.3.31)
|
121
|
+
|
122
|
+
PLATFORMS
|
123
|
+
ruby
|
124
|
+
|
125
|
+
DEPENDENCIES
|
126
|
+
bundler (>= 1.0.0)
|
127
|
+
chronic_duration!
|
128
|
+
green_monkey!
|
129
|
+
rspec (>= 2.7.0)
|
130
|
+
rspec-rails
|
131
|
+
sqlite3
|
data/Gemfile.rails-3.1.3
ADDED
data/README.md
ADDED
@@ -0,0 +1,152 @@
|
|
1
|
+
# Green Monkey
|
2
|
+
|
3
|
+
## About
|
4
|
+
|
5
|
+
This Gem allows you to make html-layout with microdata properties easier. It works with ruby 1.9, rails 3, haml 3.
|
6
|
+
|
7
|
+

|
8
|
+
|
9
|
+
## Install
|
10
|
+
|
11
|
+
Add to Gemfile
|
12
|
+
|
13
|
+
```ruby
|
14
|
+
gem "green_monkey"
|
15
|
+
```
|
16
|
+
|
17
|
+
## Examples
|
18
|
+
|
19
|
+
### helper `time_tag`
|
20
|
+
|
21
|
+
It almost as rails' time_tag but make `datetime` attribute in iso8601 format, according to Microdata specifications
|
22
|
+
Also it accepts Numeric values as duration
|
23
|
+
|
24
|
+
Haml & HTML:
|
25
|
+
|
26
|
+
```haml
|
27
|
+
= time_tag post.created_at
|
28
|
+
= time_tag post.created_at, itemprop: "datePublished"
|
29
|
+
= time_tag 3.hours + 30.minutes
|
30
|
+
```
|
31
|
+
|
32
|
+
```html
|
33
|
+
<time datetime="2011-11-23T00:00:00.0Z">23 Nov 2011</time>
|
34
|
+
<time datetime="2011-11-23T00:00:00.0Z" itemprop="datePublished">23 Nov 2011</time>
|
35
|
+
<time datetime="PT3H30M" title="3 hours 30 minutes">about 4 hours</time>
|
36
|
+
```
|
37
|
+
|
38
|
+
### helper `time_tag_interval`
|
39
|
+
|
40
|
+
The same with `time_tag` but made for time intervals
|
41
|
+
|
42
|
+
```haml
|
43
|
+
= time_tag_interval Time.parse("14 March 1879"), Time.parse("18 April 1955"), :format => '%d %h %Y'
|
44
|
+
= time_tag_interval Time.parse("14 March 1989"), 150.hours, :format => :short
|
45
|
+
```
|
46
|
+
|
47
|
+
```html
|
48
|
+
<time datetime="1879-03-14T00:00:00+07:30/1955-04-18T00:00:00+07:30">14 Mar 1879 - 14 Mar 1879</time>
|
49
|
+
<time datetime="1989-05-06T00:00:00+08:00/P6DT6H">06 May 00:00 in 6d 6h</time>
|
50
|
+
```
|
51
|
+
|
52
|
+
### ActiveRecord::Base#html\_schema\_type
|
53
|
+
|
54
|
+
```ruby
|
55
|
+
class User < ActiveRecord::Base
|
56
|
+
html_schema_type :Person
|
57
|
+
end
|
58
|
+
|
59
|
+
User.html_schema_type #=> Mida::SchemaOrg::Person
|
60
|
+
User.find(1).html_schema_type => Mida::SchemaOrg::Person
|
61
|
+
```
|
62
|
+
|
63
|
+
### Haml magic
|
64
|
+
|
65
|
+
Attribute `itemprop`
|
66
|
+
|
67
|
+
```haml
|
68
|
+
%span[:name]= item.name
|
69
|
+
<span itemprop='name'>Item name</span>
|
70
|
+
```
|
71
|
+
|
72
|
+
`itemscope` and `iteptype` attributes
|
73
|
+
|
74
|
+
```haml
|
75
|
+
%article[Mida(:Event)] # =>
|
76
|
+
<article itemscope itemtype='http://schema.org/Event'></article>
|
77
|
+
|
78
|
+
%article[Mida(:Event, :DrinkUp)] # =>
|
79
|
+
<article itemscope itemtype='http://schema.org/Event/DrinkUp'></article>
|
80
|
+
|
81
|
+
%article[@user] # =>
|
82
|
+
<article class='user' id='1' itemid='1' itemscope iteptype='http://schema.org/Person'></article>
|
83
|
+
```
|
84
|
+
|
85
|
+
### Real examples
|
86
|
+
Haml:
|
87
|
+
|
88
|
+
```haml
|
89
|
+
%article[post]
|
90
|
+
= link_to "/posts/#{post.id}", :itemprop => "url" do
|
91
|
+
%h3[:name]>= post.title
|
92
|
+
.post_body[:articleBody]= post.body.html_safe
|
93
|
+
= time_tag(post.created_at, :itemprop => "datePublished")
|
94
|
+
```
|
95
|
+
|
96
|
+
Output:
|
97
|
+
|
98
|
+
```html
|
99
|
+
<article class='post' id='post_1' itemid='1' itemscope itemtype='http://schema.org/BlogPosting'>
|
100
|
+
<a href="/posts/1" itemprop="url">
|
101
|
+
<h3 itemprop='name'>Hello world!</h3>
|
102
|
+
</a>
|
103
|
+
<div class='post_body' itemprop='articleBody'>Some text</div>
|
104
|
+
<time datetime="2011-11-22T09:16:57.0Z" itemprop="datePublished">November 22, 2011 09:16</time>
|
105
|
+
</article>
|
106
|
+
```
|
107
|
+
|
108
|
+
Haml:
|
109
|
+
|
110
|
+
```haml
|
111
|
+
%article[project]
|
112
|
+
%header
|
113
|
+
= link_to project.url, itemprop: 'url', target: "_blank" do
|
114
|
+
%h3[:name]<>= project.title
|
115
|
+
= " "
|
116
|
+
- if project.source_code.present?
|
117
|
+
= link_to "(source code)", project.source_code, class: "source_link", target: "_blank"
|
118
|
+
%section[:description]
|
119
|
+
= simple_format project.description
|
120
|
+
|
121
|
+
%ul
|
122
|
+
- for item_type in project.item_types.split(" ")
|
123
|
+
%li[Mida(:WebPageElement, :ItemType), :mentions]
|
124
|
+
%span[:name]= item_type
|
125
|
+
```
|
126
|
+
|
127
|
+
Output:
|
128
|
+
|
129
|
+
```html
|
130
|
+
<article class='project' id='project_2' itemid='2' itemscope itemtype='http://schema.org/WebPage'>
|
131
|
+
<header>
|
132
|
+
<a href="http://lawrencewoodman.github.com/mida/" itemprop="url" target="_blank">
|
133
|
+
<h3 itemprop='name'>Mida - A Microdata extractor/parser library for Ruby</h3>
|
134
|
+
</a>
|
135
|
+
<a href="http://github.com/LawrenceWoodman/mida" class="source_link" target="_blank">(source code)</a>
|
136
|
+
</header>
|
137
|
+
|
138
|
+
<section itemprop='description'>
|
139
|
+
<p>A Ruby Microdata parser/extractor</p>
|
140
|
+
</section>
|
141
|
+
|
142
|
+
<ul>
|
143
|
+
<li itemprop='mentions' itemscope itemtype='http://schema.org/WebPageElement/ItemType'>
|
144
|
+
<span itemprop='name'>http://schema.org/Blog</span>
|
145
|
+
</li>
|
146
|
+
</ul>
|
147
|
+
</article>
|
148
|
+
```
|
149
|
+
|
150
|
+
--------
|
151
|
+
|
152
|
+
I use it in [Microdata tools](http://github.com/paxa/semantic_data/ "my own project")
|
data/Rakefile
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
|
3
|
+
task :default => :spec
|
4
|
+
|
5
|
+
desc "Run Specs"
|
6
|
+
require 'rspec/core/rake_task'
|
7
|
+
RSpec::Core::RakeTask.new(:spec)
|
8
|
+
|
9
|
+
html5 microdata tags easy with green_monkey
|
10
|
+
|
11
|
+
I just launched <a href="http://">plugin saving time and let you make nice haml templates</a>
|
12
|
+
|
13
|
+
904a3032
|
14
|
+
Unlock Code = 39329878
|
15
|
+
Flash Code= 62867076
|
@@ -0,0 +1,29 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
Gem::Specification.new do |s|
|
4
|
+
s.name = "green_monkey"
|
5
|
+
s.version = '0.1'
|
6
|
+
s.platform = Gem::Platform::RUBY
|
7
|
+
s.authors = ["Pavel Evstigneev"]
|
8
|
+
s.email = ["pavel.evst@gmail.com"]
|
9
|
+
s.homepage = "https://github.com/paxa/green_monkey"
|
10
|
+
s.summary = "Rails and Haml microdata layout helpers"
|
11
|
+
s.description = "It hacks Rails and Haml"
|
12
|
+
|
13
|
+
s.required_rubygems_version = ">= 1.2.0"
|
14
|
+
|
15
|
+
s.add_runtime_dependency 'rails', '>= 3.0.0'
|
16
|
+
s.add_runtime_dependency 'haml', '>= 3.1.0'
|
17
|
+
s.add_runtime_dependency 'mida', '>= 0.3.3'
|
18
|
+
s.add_runtime_dependency 'chronic_duration'
|
19
|
+
|
20
|
+
s.add_development_dependency "bundler", ">= 1.0.0"
|
21
|
+
s.add_development_dependency "rspec", ">= 2.7.0"
|
22
|
+
s.add_development_dependency "rspec-rails"
|
23
|
+
s.add_development_dependency 'sqlite3'
|
24
|
+
|
25
|
+
s.files = `git ls-files`.split("\n")
|
26
|
+
s.executables = []
|
27
|
+
s.require_paths = ["lib"]
|
28
|
+
end
|
29
|
+
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module ActionView::Helpers::TagHelper
|
2
|
+
BOOLEAN_ATTRIBUTES.merge(['itemscope', :itemscope])
|
3
|
+
|
4
|
+
private
|
5
|
+
def tag_options(options, escape = true)
|
6
|
+
#p [options, escape, BOOLEAN_ATTRIBUTES]
|
7
|
+
unless options.blank?
|
8
|
+
attrs = []
|
9
|
+
options.each_pair do |key, value|
|
10
|
+
if BOOLEAN_ATTRIBUTES.include?(key)
|
11
|
+
attrs << key.to_s if value
|
12
|
+
elsif !value.nil?
|
13
|
+
final_value = value.is_a?(Array) ? value.join(" ") : value
|
14
|
+
final_value = html_escape(final_value) if escape
|
15
|
+
attrs << %(#{key}="#{final_value}")
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
" #{attrs.sort * ' '}".html_safe unless attrs.empty?
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
module GreenMonkey
|
4
|
+
module ModelHelpers
|
5
|
+
extend ActiveSupport::Concern
|
6
|
+
|
7
|
+
|
8
|
+
module ClassMethods
|
9
|
+
def html_schema_type(value = nil)
|
10
|
+
return @html_schema_type unless value
|
11
|
+
|
12
|
+
value = /#{value}/ if value.is_a?(Symbol)
|
13
|
+
if value.is_a?(Regexp)
|
14
|
+
value = Mida::Vocabulary.vocabularies.find do |vocabulary|
|
15
|
+
vocabulary.itemtype.to_s =~ value && vocabulary.itemtype.to_s
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
@html_schema_type = value
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
module InstanceMethods
|
24
|
+
def html_schema_type
|
25
|
+
self.class.html_schema_type
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,67 @@
|
|
1
|
+
require "haml"
|
2
|
+
|
3
|
+
# this hack looks at active-record object's :html_schema_type field and adds itemscope, itemid and itemtype to element
|
4
|
+
# example:
|
5
|
+
#
|
6
|
+
# %article[post]
|
7
|
+
# => <article class="post" itemscope itemtype="http://schema.org/BlogPosting" itemid="1">
|
8
|
+
#
|
9
|
+
# %section[Mida(:Blog)]
|
10
|
+
# => <section itemscope itemtype="http://schema.org/Blog">
|
11
|
+
#
|
12
|
+
# %section[Mida(:Blog), :sexjokes]
|
13
|
+
# => <section itemscope itemtype="http://schema.org/Blog/SexJokes">
|
14
|
+
# according to "Extension Mechanism" at http://schema.org/docs/extension.html
|
15
|
+
#
|
16
|
+
# %span[:title] Hello
|
17
|
+
# => <span itemprop="title">Hello</span>
|
18
|
+
|
19
|
+
class Haml::Buffer
|
20
|
+
|
21
|
+
# this methods calls then you pass
|
22
|
+
# %tag[object1, object2]
|
23
|
+
# ref argument is array
|
24
|
+
def parse_object_ref(ref)
|
25
|
+
options = {}
|
26
|
+
ref.each do |obj|
|
27
|
+
next if obj == "local-variable"
|
28
|
+
self.class.merge_attrs(options, process_object_ref(obj))
|
29
|
+
end
|
30
|
+
|
31
|
+
options
|
32
|
+
end
|
33
|
+
|
34
|
+
def process_object_ref(obj)
|
35
|
+
return {} if !obj
|
36
|
+
|
37
|
+
if obj.is_a?(Symbol)
|
38
|
+
# symbol => "itemprop" attribute
|
39
|
+
return {'itemprop' => obj.to_s}
|
40
|
+
elsif obj.kind_of?(Mida::Vocabulary)
|
41
|
+
# Mida::Vocabulary => itemprop and itemtype
|
42
|
+
return {itemscope: true, itemtype: obj.itemtype.source}
|
43
|
+
elsif obj.is_a?(String)
|
44
|
+
return {class: obj}
|
45
|
+
else
|
46
|
+
options = {}
|
47
|
+
options[:class] = obj.respond_to?(:haml_object_ref) ? obj.haml_object_ref : underscore(obj.class)
|
48
|
+
options[:id] = "#{options[:class]}_#{obj.id || 'new'}" if obj.respond_to?(:id)
|
49
|
+
|
50
|
+
# my hack for microdata attributes
|
51
|
+
if obj.respond_to?(:html_schema_type)
|
52
|
+
options[:itemscope] = true
|
53
|
+
options[:itemid] = obj.id
|
54
|
+
|
55
|
+
if obj.html_schema_type.kind_of?(Mida::Vocabulary)
|
56
|
+
options[:itemtype] = obj.html_schema_type.itemtype.source
|
57
|
+
else
|
58
|
+
raise "No vocabulary found (#{obj.html_schema_type})" unless Mida::Vocabulary.find(obj.html_schema_type)
|
59
|
+
options[:itemtype] = obj.html_schema_type
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
return options
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
require "mida"
|
2
|
+
|
3
|
+
class Mida::Vocabulary::Custom < Mida::Vocabulary
|
4
|
+
attr_reader :itemtype
|
5
|
+
def initialize(itemtype)
|
6
|
+
@itemtype = %r{#{itemtype}}
|
7
|
+
end
|
8
|
+
end
|
9
|
+
|
10
|
+
def Mida(itemtype, addition = nil)
|
11
|
+
if itemtype.is_a?(Symbol)
|
12
|
+
itemtype = "http://schema.org/#{itemtype}"
|
13
|
+
end
|
14
|
+
|
15
|
+
found_voc = Mida::Vocabulary.find(itemtype)
|
16
|
+
|
17
|
+
if found_voc == Mida::GenericVocabulary
|
18
|
+
found_voc = Mida::Vocabulary::Custom.new(itemtype)
|
19
|
+
end
|
20
|
+
|
21
|
+
if addition
|
22
|
+
Mida::Vocabulary::Custom.new(found_voc.itemtype.source + "/#{addition}")
|
23
|
+
else
|
24
|
+
found_voc
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
require "uri"
|
29
|
+
|
30
|
+
module URI
|
31
|
+
def to_json
|
32
|
+
to_s.to_json
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
require "chronic_duration"
|
4
|
+
module GreenMonkey
|
5
|
+
module ViewHelper
|
6
|
+
|
7
|
+
# it shortcut for this
|
8
|
+
#%time{:datetime => post.published_at.iso8601(10) }= post.published_at.strftime("%d %h %Y")
|
9
|
+
|
10
|
+
# = time_tag post.created_at
|
11
|
+
# = time_tag post.created_at, format: "%d %h %Y %R%p"
|
12
|
+
# = time_tag post.created_at, itemprop: "datePublished"
|
13
|
+
def time_tag(time, *args)
|
14
|
+
options = args.extract_options!
|
15
|
+
format = options.delete(:format) || :long
|
16
|
+
datetime = time_to_iso8601(time)
|
17
|
+
|
18
|
+
|
19
|
+
if time.acts_like?(:time)
|
20
|
+
title = nil
|
21
|
+
content = args.first || I18n.l(time, format: format)
|
22
|
+
elsif time.kind_of?(Numeric)
|
23
|
+
title = ChronicDuration.output(time, :format => format)
|
24
|
+
content = args.first || distance_of_time_in_words(time)
|
25
|
+
end
|
26
|
+
|
27
|
+
content_tag(:time, content, options.reverse_merge(datetime: datetime, title: title))
|
28
|
+
end
|
29
|
+
|
30
|
+
def time_tag_interval(from, to, *args)
|
31
|
+
options = args.extract_options!
|
32
|
+
format = options.delete(:format) || :long
|
33
|
+
|
34
|
+
datetime = [from, to].map(&method(:time_to_iso8601)).join("/")
|
35
|
+
content = args.first || [from, to].map do |time|
|
36
|
+
if time.acts_like?(:time)
|
37
|
+
I18n.l(from, format: format)
|
38
|
+
else
|
39
|
+
ChronicDuration.output(time, :format => format)
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
if to.acts_like?(:time)
|
44
|
+
content = content.join(" - ")
|
45
|
+
else
|
46
|
+
content = content.join(" in ")
|
47
|
+
end
|
48
|
+
|
49
|
+
content_tag(:time, content, options.reverse_merge(datetime: datetime))
|
50
|
+
end
|
51
|
+
|
52
|
+
def time_to_iso8601(time)
|
53
|
+
if time.acts_like?(:time)
|
54
|
+
time.iso8601
|
55
|
+
elsif time.kind_of?(Numeric)
|
56
|
+
ChronicDuration.output(time, :format => :iso8601)
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
module GreenMonkey
|
4
|
+
class Railtie < Rails::Railtie
|
5
|
+
initializer "load extentions and patches" do
|
6
|
+
require "green_monkey/ext/active_model"
|
7
|
+
ActiveModel::Dirty.send :include, GreenMonkey::ModelHelpers
|
8
|
+
|
9
|
+
require 'green_monkey/ext/view_helper'
|
10
|
+
ActionView::Base.send :include, GreenMonkey::ViewHelper
|
11
|
+
|
12
|
+
require "green_monkey/ext/action_view"
|
13
|
+
require "green_monkey/ext/haml"
|
14
|
+
require "green_monkey/ext/mida"
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
data/lib/green_monkey.rb
ADDED
data/spec/haml_spec.rb
ADDED
@@ -0,0 +1,85 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require "pathname"
|
3
|
+
|
4
|
+
$t = 0
|
5
|
+
|
6
|
+
describe "Haml generation" do
|
7
|
+
def render_file(file, options = {})
|
8
|
+
ActionController::Base.new.render_to_string(file: file, locals: options)
|
9
|
+
end
|
10
|
+
|
11
|
+
def render_haml(template, options = {})
|
12
|
+
$t += 1
|
13
|
+
file = File.expand_path(File.dirname(__FILE__) + "/../tmp/#{$t}.haml")
|
14
|
+
File.delete(file) if File.exist?(file)
|
15
|
+
File.open(file, 'w+') {|f| f.write template }
|
16
|
+
render_file(file, options)
|
17
|
+
end
|
18
|
+
|
19
|
+
it "should render itemscope as a boolean attribute" do
|
20
|
+
render_haml("%b{:itemscope => true}").should =~ /<b\s+itemscope\s*>/
|
21
|
+
end
|
22
|
+
|
23
|
+
it "should get AR object" do
|
24
|
+
user = User.create
|
25
|
+
tpl = "%article[user]"
|
26
|
+
str = render_haml(tpl, user: user)
|
27
|
+
|
28
|
+
str.should =~ /itemtype=('|")#{Regexp.escape 'http://example.com/User'}('|")/
|
29
|
+
str.should =~ /itemid=.?#{user.id}/
|
30
|
+
str.should =~ /itemscope/
|
31
|
+
end
|
32
|
+
|
33
|
+
it "should render itemprop attribute" do
|
34
|
+
render_haml("%b[:title] Dada").should =~ /itemprop=.?title/
|
35
|
+
end
|
36
|
+
|
37
|
+
it "should generate valid microdata layout" do
|
38
|
+
post = Post.create(title: "Post 1", body: "Some text")
|
39
|
+
tpl = Pathname.new(__FILE__).dirname.join("post.haml")
|
40
|
+
str = render_file(tpl, post: post)
|
41
|
+
|
42
|
+
doc = Mida::Document.new(str, "http://example.com/")
|
43
|
+
|
44
|
+
props = doc.items[0].properties
|
45
|
+
props['url'][0].to_s.should == "http://example.com/posts/#{post.id}"
|
46
|
+
props['name'][0].should == post.title
|
47
|
+
props['articleBody'][0].should == post.body
|
48
|
+
props['datePublished'][0].to_i.should == post.created_at.to_i
|
49
|
+
|
50
|
+
doc.items[0].id.should == post.id.to_s
|
51
|
+
doc.items[0].type.should == post.html_schema_type.itemtype.source
|
52
|
+
end
|
53
|
+
|
54
|
+
describe 'time_tag' do
|
55
|
+
it "should produce itemprop if specified" do
|
56
|
+
str = render_haml("= time_tag(Time.now, itemprop: 'time')")
|
57
|
+
str.should =~ /itemprop="time"/
|
58
|
+
end
|
59
|
+
|
60
|
+
it "should run with time" do
|
61
|
+
time = Time.now
|
62
|
+
str = render_haml("= time_tag(time)", time: time)
|
63
|
+
|
64
|
+
str.should =~ /<time.+datetime=.?#{Regexp.escape time.iso8601}/
|
65
|
+
end
|
66
|
+
|
67
|
+
it "should run with duration" do
|
68
|
+
str = render_haml("= time_tag(time)", time: 3.hours + 30.minutes)
|
69
|
+
str.should =~ /datetime=.PT3H30M/
|
70
|
+
end
|
71
|
+
|
72
|
+
it "should run with time interval of 2 dates" do
|
73
|
+
time = [Time.parse("14 March 1879"), Time.parse("18 April 1955")]
|
74
|
+
|
75
|
+
str = render_haml("= time_tag_interval(*time, :format => '%d %h %Y')", time: time)
|
76
|
+
str.should =~ /<time.+datetime=.?#{Regexp.escape time[0].iso8601}\/#{Regexp.escape time[1].iso8601}/
|
77
|
+
end
|
78
|
+
|
79
|
+
it "should run with date and duration" do
|
80
|
+
time = [Time.parse("6 May 1989"), 150.hours]
|
81
|
+
str = render_haml("= time_tag_interval(*time, :format => :short)", time: time)
|
82
|
+
str.should =~ /<time.+datetime=.?#{Regexp.escape time[0].iso8601}\/P6DT6H/
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
data/spec/mida_spec.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "Mida helper" do
|
4
|
+
it "should find vocabulary class" do
|
5
|
+
Mida(:BlogPosting).should == Mida::SchemaOrg::BlogPosting
|
6
|
+
Mida("http://schema.org/BlogPosting").should == Mida::SchemaOrg::BlogPosting
|
7
|
+
|
8
|
+
custom = Mida("http://t.co/BlogPosting")
|
9
|
+
custom.itemtype.source == "http://t.co/BlogPosting"
|
10
|
+
custom.class.should == Mida::Vocabulary::Custom
|
11
|
+
end
|
12
|
+
|
13
|
+
it "should make Mida::Vocabulary::Custom for extended vocabularies" do
|
14
|
+
extended = Mida(:Blog, :SexJokes)
|
15
|
+
extended.class.should == Mida::Vocabulary::Custom
|
16
|
+
extended.itemtype.source == "http://schema.org/Blog/SexJokes"
|
17
|
+
end
|
18
|
+
end
|
data/spec/model_spec.rb
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe ActiveModel do
|
4
|
+
it "should check ActiveModel extention" do
|
5
|
+
ActiveRecord::Base.should respond_to(:html_schema_type)
|
6
|
+
end
|
7
|
+
|
8
|
+
it "should return schema-type on #html_schema_type" do
|
9
|
+
Post.html_schema_type.should == Post.new.html_schema_type
|
10
|
+
end
|
11
|
+
|
12
|
+
it "should return instance of kind Mida::Vocabulary" do
|
13
|
+
Post.new.html_schema_type.should == Mida::SchemaOrg::BlogPosting
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should return string on unknown itemtype" do
|
17
|
+
User.html_schema_type.should == "http://example.com/User"
|
18
|
+
end
|
19
|
+
end
|
data/spec/post.haml
ADDED
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,54 @@
|
|
1
|
+
ENV['BUNDLE_GEMFILE'] ||= File.expand_path('../../Gemfile', __FILE__)
|
2
|
+
ENV['RAILS_ENV'] ||= 'development'
|
3
|
+
|
4
|
+
require 'bundler/setup'
|
5
|
+
|
6
|
+
require 'rails/all'
|
7
|
+
require 'rails/generators'
|
8
|
+
require 'rails/generators/test_case'
|
9
|
+
|
10
|
+
require "green_monkey"
|
11
|
+
|
12
|
+
class TestApp < Rails::Application
|
13
|
+
config.root = File.dirname(__FILE__)
|
14
|
+
config.active_support.deprecation :log
|
15
|
+
#config.logger = Logger.new(STDOUT)
|
16
|
+
config.log_level = :error
|
17
|
+
end
|
18
|
+
|
19
|
+
Rails.application = TestApp
|
20
|
+
|
21
|
+
module Rails
|
22
|
+
def self.root
|
23
|
+
@root ||= File.expand_path("../../tmp/rails", __FILE__)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
Rails.application.config.root = Rails.root
|
28
|
+
TestApp.initialize!
|
29
|
+
|
30
|
+
ActiveRecord::Schema.define(:version => 20111023054000) do
|
31
|
+
create_table "posts" do |t|
|
32
|
+
t.string "title"
|
33
|
+
t.text "body"
|
34
|
+
t.string "link"
|
35
|
+
t.datetime "published_at"
|
36
|
+
t.datetime "created_at"
|
37
|
+
t.datetime "updated_at"
|
38
|
+
end
|
39
|
+
|
40
|
+
create_table "users" do |t|
|
41
|
+
t.string "name"
|
42
|
+
t.string "location"
|
43
|
+
t.string "github"
|
44
|
+
t.string "password"
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
class Post < ActiveRecord::Base
|
49
|
+
html_schema_type :BlogPosting
|
50
|
+
end
|
51
|
+
|
52
|
+
class User < ActiveRecord::Base
|
53
|
+
html_schema_type "http://example.com/User"
|
54
|
+
end
|
File without changes
|
metadata
ADDED
@@ -0,0 +1,158 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: green_monkey
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: '0.1'
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Pavel Evstigneev
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2011-12-30 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: rails
|
16
|
+
requirement: &2152695500 !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: 3.0.0
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: *2152695500
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: haml
|
27
|
+
requirement: &2152679260 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: 3.1.0
|
33
|
+
type: :runtime
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *2152679260
|
36
|
+
- !ruby/object:Gem::Dependency
|
37
|
+
name: mida
|
38
|
+
requirement: &2152675760 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ! '>='
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: 0.3.3
|
44
|
+
type: :runtime
|
45
|
+
prerelease: false
|
46
|
+
version_requirements: *2152675760
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: chronic_duration
|
49
|
+
requirement: &2152674300 !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ! '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
type: :runtime
|
56
|
+
prerelease: false
|
57
|
+
version_requirements: *2152674300
|
58
|
+
- !ruby/object:Gem::Dependency
|
59
|
+
name: bundler
|
60
|
+
requirement: &2152664740 !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
62
|
+
requirements:
|
63
|
+
- - ! '>='
|
64
|
+
- !ruby/object:Gem::Version
|
65
|
+
version: 1.0.0
|
66
|
+
type: :development
|
67
|
+
prerelease: false
|
68
|
+
version_requirements: *2152664740
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: rspec
|
71
|
+
requirement: &2152648240 !ruby/object:Gem::Requirement
|
72
|
+
none: false
|
73
|
+
requirements:
|
74
|
+
- - ! '>='
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: 2.7.0
|
77
|
+
type: :development
|
78
|
+
prerelease: false
|
79
|
+
version_requirements: *2152648240
|
80
|
+
- !ruby/object:Gem::Dependency
|
81
|
+
name: rspec-rails
|
82
|
+
requirement: &2152639820 !ruby/object:Gem::Requirement
|
83
|
+
none: false
|
84
|
+
requirements:
|
85
|
+
- - ! '>='
|
86
|
+
- !ruby/object:Gem::Version
|
87
|
+
version: '0'
|
88
|
+
type: :development
|
89
|
+
prerelease: false
|
90
|
+
version_requirements: *2152639820
|
91
|
+
- !ruby/object:Gem::Dependency
|
92
|
+
name: sqlite3
|
93
|
+
requirement: &2152633580 !ruby/object:Gem::Requirement
|
94
|
+
none: false
|
95
|
+
requirements:
|
96
|
+
- - ! '>='
|
97
|
+
- !ruby/object:Gem::Version
|
98
|
+
version: '0'
|
99
|
+
type: :development
|
100
|
+
prerelease: false
|
101
|
+
version_requirements: *2152633580
|
102
|
+
description: It hacks Rails and Haml
|
103
|
+
email:
|
104
|
+
- pavel.evst@gmail.com
|
105
|
+
executables: []
|
106
|
+
extensions: []
|
107
|
+
extra_rdoc_files: []
|
108
|
+
files:
|
109
|
+
- .gitignore
|
110
|
+
- .rspec
|
111
|
+
- .travis.yml
|
112
|
+
- Gemfile
|
113
|
+
- Gemfile.haml-edge
|
114
|
+
- Gemfile.lock
|
115
|
+
- Gemfile.rails-3.0.11
|
116
|
+
- Gemfile.rails-3.1.3
|
117
|
+
- README.md
|
118
|
+
- Rakefile
|
119
|
+
- green_monkey.gemspec
|
120
|
+
- lib/green_monkey.rb
|
121
|
+
- lib/green_monkey/ext/action_view.rb
|
122
|
+
- lib/green_monkey/ext/active_model.rb
|
123
|
+
- lib/green_monkey/ext/haml.rb
|
124
|
+
- lib/green_monkey/ext/mida.rb
|
125
|
+
- lib/green_monkey/ext/view_helper.rb
|
126
|
+
- lib/green_monkey/railtie.rb
|
127
|
+
- spec/haml_spec.rb
|
128
|
+
- spec/mida_spec.rb
|
129
|
+
- spec/model_spec.rb
|
130
|
+
- spec/post.haml
|
131
|
+
- spec/spec_helper.rb
|
132
|
+
- tmp/rails/config/database.yml
|
133
|
+
- tmp/rails/config/environments/development.rb
|
134
|
+
homepage: https://github.com/paxa/green_monkey
|
135
|
+
licenses: []
|
136
|
+
post_install_message:
|
137
|
+
rdoc_options: []
|
138
|
+
require_paths:
|
139
|
+
- lib
|
140
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
141
|
+
none: false
|
142
|
+
requirements:
|
143
|
+
- - ! '>='
|
144
|
+
- !ruby/object:Gem::Version
|
145
|
+
version: '0'
|
146
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
147
|
+
none: false
|
148
|
+
requirements:
|
149
|
+
- - ! '>='
|
150
|
+
- !ruby/object:Gem::Version
|
151
|
+
version: 1.2.0
|
152
|
+
requirements: []
|
153
|
+
rubyforge_project:
|
154
|
+
rubygems_version: 1.8.10
|
155
|
+
signing_key:
|
156
|
+
specification_version: 3
|
157
|
+
summary: Rails and Haml microdata layout helpers
|
158
|
+
test_files: []
|