morph 0.3.4 → 0.3.5
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG +2 -0
- data/Manifest +0 -5
- data/README +23 -9
- data/lib/morph.rb +15 -6
- data/morph.gemspec +5 -5
- metadata +5 -10
- data/examples/forger.rb +0 -31
- data/examples/hubbit.rb +0 -32
- data/spec/lib/morph_spec.rb +0 -642
- data/spec/morph_spec_helper.rb +0 -147
- data/spec/spec_helper.rb +0 -3
data/CHANGELOG
CHANGED
data/Manifest
CHANGED
data/README
CHANGED
@@ -1,44 +1,50 @@
|
|
1
|
-
Morph mixin allows you to emerge class definitions via calling assignment methods
|
1
|
+
Morph mixin allows you to emerge Ruby class definitions from data via calling assignment methods.
|
2
2
|
|
3
3
|
|
4
|
+
== Installing Morph
|
5
|
+
|
6
|
+
gem install morph
|
7
|
+
|
8
|
+
To use Morph:
|
9
|
+
|
10
|
+
require 'morph'
|
11
|
+
|
4
12
|
== Morph creating classes +from_csv+
|
5
13
|
|
6
14
|
Here's example code showing Morph playing with CSV (comma-separated values):
|
7
15
|
|
8
|
-
require 'rubygems'; require 'morph'
|
9
|
-
|
10
16
|
csv = %Q[name,party\nTed Roe,red\nAli Davidson,blue\nSue Smith,green]
|
11
17
|
|
12
18
|
people = Morph.from_csv(csv, 'person')
|
19
|
+
|
13
20
|
# => [#<Morph::Person @name="Ted Roe", @party="red">,
|
14
21
|
#<Morph::Person @name="Ali Davidson", @party="blue">,
|
15
22
|
#<Morph::Person @name="Sue Smith", @party="green">]
|
16
23
|
|
17
24
|
people.last.party
|
25
|
+
|
18
26
|
# => "green"
|
19
27
|
|
20
28
|
== Morph creating classes +from_tsv+
|
21
29
|
|
22
30
|
Here's example code showing Morph playing with TSV (tab-separated values):
|
23
31
|
|
24
|
-
require 'rubygems'; require 'morph'
|
25
|
-
|
26
32
|
tsv = %Q[name\tparty\nTed Roe\tred\nAli Davidson\tblue\nSue Smith\tgreen]
|
27
33
|
|
28
34
|
people = Morph.from_tsv(tsv, 'person')
|
35
|
+
|
29
36
|
# => [#<Morph::Person @name="Ted Roe", @party="red">,
|
30
37
|
#<Morph::Person @name="Ali Davidson", @party="blue">,
|
31
38
|
#<Morph::Person @name="Sue Smith", @party="green">]
|
32
39
|
|
33
40
|
people.last.party
|
41
|
+
|
34
42
|
# => "green"
|
35
43
|
|
36
44
|
== Morph creating classes +from_xml+
|
37
45
|
|
38
46
|
Here's example code showing Morph playing with XML:
|
39
47
|
|
40
|
-
require 'rubygems'; require 'morph'
|
41
|
-
|
42
48
|
xml = %Q[<?xml version="1.0" encoding="UTF-8"?>
|
43
49
|
<councils type="array">
|
44
50
|
<council code='1'>
|
@@ -50,18 +56,20 @@ Here's example code showing Morph playing with XML:
|
|
50
56
|
</councils>]
|
51
57
|
|
52
58
|
councils = Morph.from_xml(xml)
|
59
|
+
|
53
60
|
# => [#<Morph::Council @code="1", @name="Aberdeen City Council">,
|
54
61
|
#<Morph::Council @code="2", @name="Allerdale Borough Council">]
|
55
62
|
|
56
63
|
councils.first.name
|
64
|
+
|
57
65
|
# => "Aberdeen City Council"
|
58
66
|
|
59
67
|
== Morph playing with +Nokogiri+
|
60
68
|
|
61
69
|
Here's example code showing Morph playing with Nokogiri in Ruby 1.9.2:
|
62
70
|
|
63
|
-
require '
|
64
|
-
|
71
|
+
require 'morph'; require 'nokogiri'; require 'open-uri'
|
72
|
+
|
65
73
|
|
66
74
|
class Hubbit
|
67
75
|
include Morph # allows class to morph
|
@@ -93,6 +101,7 @@ The model emerges from the data. Let's start by looking up 'why':
|
|
93
101
|
What new methods do we have?
|
94
102
|
|
95
103
|
Hubbit.morph_methods.map {|m| m.to_s}
|
104
|
+
|
96
105
|
#=> ["location", "location=", "member_since", "member_since=", "name", "name="]
|
97
106
|
|
98
107
|
Ah-ha, so we have a name attribute now:
|
@@ -112,6 +121,7 @@ Let's add some of why's projects:
|
|
112
121
|
That why's a productive fellow! Note new accessor methods have been added:
|
113
122
|
|
114
123
|
Hubbit.morph_methods.map {|m| m.to_s}
|
124
|
+
|
115
125
|
#=> ["location", "location=", "member_since", "member_since=", "name", "name=",
|
116
126
|
# "projects", "projects="]
|
117
127
|
|
@@ -123,6 +133,7 @@ Let's do some more morphing:
|
|
123
133
|
Do we have more methods now?
|
124
134
|
|
125
135
|
Hubbit.morph_methods.map {|m| m.to_s}
|
136
|
+
|
126
137
|
#=> ["company", "company=", "email", "email=", "location", "location=",
|
127
138
|
# "member_since", "member_since=", "name", "name=", "projects", "projects=",
|
128
139
|
# "website_blog", "website_blog="]
|
@@ -137,6 +148,7 @@ So, a new company method has appeared:
|
|
137
148
|
Time to generate an Active Record model? Get a sample script line like this:
|
138
149
|
|
139
150
|
Hubbit.script_generate
|
151
|
+
|
140
152
|
#=> "rails destroy model Hubbit;
|
141
153
|
# rails generate model Hubbit company:string email:string location:string
|
142
154
|
# member_since:string name:string projects:string website_blog:string"
|
@@ -144,6 +156,7 @@ Time to generate an Active Record model? Get a sample script line like this:
|
|
144
156
|
or specify the generator:
|
145
157
|
|
146
158
|
Hubbit.script_generate :generator => 'rspec_model'
|
159
|
+
|
147
160
|
#=> "rails destroy rspec_model Hubbit;
|
148
161
|
# rails generate rspec_model Hubbit company:string email:string
|
149
162
|
# location:string member_since:string name:string projects:string
|
@@ -187,6 +200,7 @@ Now an order:
|
|
187
200
|
Want to retrieve all that as a nested hash of values? No problem:
|
188
201
|
|
189
202
|
order.morph_attributes
|
203
|
+
|
190
204
|
# => {:items=>[{:name=>"spinach", :cost=>0.5}], :no=>123}
|
191
205
|
|
192
206
|
|
data/lib/morph.rb
CHANGED
@@ -18,7 +18,7 @@ rescue Exception => e
|
|
18
18
|
end
|
19
19
|
|
20
20
|
module Morph
|
21
|
-
VERSION = "0.3.
|
21
|
+
VERSION = "0.3.5" unless defined? Morph::VERSION
|
22
22
|
|
23
23
|
class << self
|
24
24
|
def generate_migrations object, options={}
|
@@ -183,20 +183,29 @@ module Morph
|
|
183
183
|
|
184
184
|
module ClassMethods
|
185
185
|
|
186
|
-
@@adding_morph_method = Hash.new {|hash,klass| hash[klass] = false }
|
187
|
-
@@morph_methods = Hash.new {|hash,klass| hash[klass] = {} }
|
188
|
-
@@morph_attributes = Hash.new {|hash,klass| hash[klass] = [] }
|
186
|
+
@@adding_morph_method = Hash.new {|hash,klass| hash[klass] = false } unless defined?(@@adding_morph_method)
|
187
|
+
@@morph_methods = Hash.new {|hash,klass| hash[klass] = {} } unless defined?(@@morph_methods)
|
188
|
+
@@morph_attributes = Hash.new {|hash,klass| hash[klass] = [] } unless defined?(@@morph_attributes)
|
189
189
|
|
190
190
|
def morph_attributes
|
191
|
-
|
191
|
+
if superclass.respond_to?(:morph_attributes)
|
192
|
+
@@morph_attributes[self] + superclass.morph_attributes
|
193
|
+
else
|
194
|
+
@@morph_attributes[self] + []
|
195
|
+
end
|
192
196
|
end
|
193
197
|
|
194
198
|
def morph_methods
|
195
|
-
if RUBY_VERSION >= "1.9"
|
199
|
+
methods = if RUBY_VERSION >= "1.9"
|
196
200
|
@@morph_methods[self].keys.sort.map(&:to_sym)
|
197
201
|
else
|
198
202
|
@@morph_methods[self].keys.sort
|
199
203
|
end
|
204
|
+
|
205
|
+
if superclass.respond_to?(:morph_attributes)
|
206
|
+
methods += superclass.morph_methods
|
207
|
+
end
|
208
|
+
methods
|
200
209
|
end
|
201
210
|
|
202
211
|
def adding_morph_method= true_or_false
|
data/morph.gemspec
CHANGED
@@ -2,21 +2,21 @@
|
|
2
2
|
|
3
3
|
Gem::Specification.new do |s|
|
4
4
|
s.name = "morph"
|
5
|
-
s.version = "0.3.
|
5
|
+
s.version = "0.3.5"
|
6
6
|
|
7
7
|
s.required_rubygems_version = Gem::Requirement.new(">= 1.2") if s.respond_to? :required_rubygems_version=
|
8
8
|
s.authors = ["Rob McKinnon"]
|
9
|
-
s.date = "2012-
|
10
|
-
s.description = "Morph mixin allows you to emerge class definitions via calling assignment methods
|
9
|
+
s.date = "2012-08-31"
|
10
|
+
s.description = "Morph mixin allows you to emerge Ruby class definitions from data via calling assignment methods.\n"
|
11
11
|
s.email = ["rob ~@nospam@~ rubyforge.org"]
|
12
12
|
s.extra_rdoc_files = ["CHANGELOG", "LICENSE", "README"]
|
13
|
-
s.files = ["CHANGELOG", "
|
13
|
+
s.files = ["CHANGELOG", "lib/morph.rb", "LICENSE", "README", "Manifest", "morph.gemspec", "Rakefile"]
|
14
14
|
s.homepage = "https://github.com/robmckinnon/morph"
|
15
15
|
s.post_install_message = "Read usage examples at: https://github.com/robmckinnon/morph#readme"
|
16
16
|
s.rdoc_options = ["--line-numbers", "--inline-source", "--title", "Morph", "--main", "README", "--inline-source"]
|
17
17
|
s.require_paths = ["lib"]
|
18
18
|
s.rubyforge_project = "morph"
|
19
|
-
s.rubygems_version = "1.8.
|
19
|
+
s.rubygems_version = "1.8.24"
|
20
20
|
s.summary = "Morph mixin allows you to emerge class definitions via calling assignment methods."
|
21
21
|
|
22
22
|
if s.respond_to? :specification_version then
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: morph
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.3.
|
4
|
+
version: 0.3.5
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-08-31 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: activesupport
|
@@ -59,8 +59,8 @@ dependencies:
|
|
59
59
|
- - ! '>='
|
60
60
|
- !ruby/object:Gem::Version
|
61
61
|
version: '0'
|
62
|
-
description: ! 'Morph mixin allows you to emerge class definitions
|
63
|
-
|
62
|
+
description: ! 'Morph mixin allows you to emerge Ruby class definitions from data
|
63
|
+
via calling assignment methods.
|
64
64
|
|
65
65
|
'
|
66
66
|
email:
|
@@ -73,14 +73,9 @@ extra_rdoc_files:
|
|
73
73
|
- README
|
74
74
|
files:
|
75
75
|
- CHANGELOG
|
76
|
-
- examples/forger.rb
|
77
|
-
- examples/hubbit.rb
|
78
76
|
- lib/morph.rb
|
79
77
|
- LICENSE
|
80
78
|
- README
|
81
|
-
- spec/lib/morph_spec.rb
|
82
|
-
- spec/morph_spec_helper.rb
|
83
|
-
- spec/spec_helper.rb
|
84
79
|
- Manifest
|
85
80
|
- morph.gemspec
|
86
81
|
- Rakefile
|
@@ -111,7 +106,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
111
106
|
version: '1.2'
|
112
107
|
requirements: []
|
113
108
|
rubyforge_project: morph
|
114
|
-
rubygems_version: 1.8.
|
109
|
+
rubygems_version: 1.8.24
|
115
110
|
signing_key:
|
116
111
|
specification_version: 3
|
117
112
|
summary: Morph mixin allows you to emerge class definitions via calling assignment
|
data/examples/forger.rb
DELETED
@@ -1,31 +0,0 @@
|
|
1
|
-
require 'rubygems'; require 'hpricot'; require 'open-uri'; require 'morph'
|
2
|
-
|
3
|
-
# An example of Morph playing with Hpricot
|
4
|
-
class Forger
|
5
|
-
|
6
|
-
include Morph
|
7
|
-
|
8
|
-
def initialize name
|
9
|
-
begin
|
10
|
-
doc = Hpricot open("http://rubyforge.org/users/#{name}")
|
11
|
-
|
12
|
-
table = doc.at('td[text() = "Personal Information"]').parent.parent
|
13
|
-
values = table/'tr/td/strong'
|
14
|
-
|
15
|
-
values.collect do |node|
|
16
|
-
value = node.inner_text.strip
|
17
|
-
label = node.at('../../td[1]').inner_text
|
18
|
-
morph(label, value)
|
19
|
-
end
|
20
|
-
rescue
|
21
|
-
raise "Couldn't find forger with name: #{name}"
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
def Forger name
|
27
|
-
Forger.new name
|
28
|
-
end
|
29
|
-
|
30
|
-
#> why = Forger 'why'
|
31
|
-
|
data/examples/hubbit.rb
DELETED
@@ -1,32 +0,0 @@
|
|
1
|
-
require 'morph'
|
2
|
-
|
3
|
-
require 'rubygems'; require 'nokogiri'; require 'open-uri'
|
4
|
-
|
5
|
-
# An example of Morph playing with Nokogiri
|
6
|
-
class Hubbit
|
7
|
-
include Morph # allows class to morph
|
8
|
-
|
9
|
-
def initialize name
|
10
|
-
doc = Nokogiri::HTML open("https://github.com/#{name}")
|
11
|
-
|
12
|
-
profile_fields = doc.search('.vcard dt')
|
13
|
-
|
14
|
-
profile_fields.each do |node|
|
15
|
-
label = node.inner_text
|
16
|
-
value = node.next_element.inner_text.strip
|
17
|
-
|
18
|
-
morph(label, value) # morph magic adds accessor methods!
|
19
|
-
end
|
20
|
-
end
|
21
|
-
|
22
|
-
def member_since_date
|
23
|
-
Date.parse member_since
|
24
|
-
end
|
25
|
-
end
|
26
|
-
|
27
|
-
def Hubbit name
|
28
|
-
Hubbit.new name
|
29
|
-
end
|
30
|
-
|
31
|
-
# why = Hubbit 'why'
|
32
|
-
# dhh = Hubbit 'dhh'
|
data/spec/lib/morph_spec.rb
DELETED
@@ -1,642 +0,0 @@
|
|
1
|
-
# encoding: utf-8
|
2
|
-
require File.dirname(__FILE__) + '/../morph_spec_helper'
|
3
|
-
|
4
|
-
describe Morph do
|
5
|
-
include MorphSpecHelperMethods
|
6
|
-
|
7
|
-
describe "when writer method that didn't exist before is called with non-nil value" do
|
8
|
-
before :all do initialize_morph; end
|
9
|
-
after :all do remove_morph_methods; end
|
10
|
-
|
11
|
-
before :each do
|
12
|
-
remove_morph_methods
|
13
|
-
@quack = 'quack'
|
14
|
-
@morph.noise= @quack
|
15
|
-
@attribute = 'noise'
|
16
|
-
@expected_morph_methods_count = 2
|
17
|
-
end
|
18
|
-
|
19
|
-
it_should_behave_like "class with generated accessor methods added"
|
20
|
-
|
21
|
-
it 'should return assigned value when reader method called' do
|
22
|
-
@morph.noise.should == @quack
|
23
|
-
end
|
24
|
-
|
25
|
-
it 'should return hash of attributes when morph_attributes called' do
|
26
|
-
@morph.morph_attributes.should == {@attribute.to_sym => @quack}
|
27
|
-
end
|
28
|
-
|
29
|
-
it 'should generate rails model generator script line, with given model name' do
|
30
|
-
@morphed_class.script_generate {|model_name| 'SomethingDifferent'}.should == "rails destroy model SomethingDifferent; rails generate model SomethingDifferent noise:string"
|
31
|
-
end
|
32
|
-
|
33
|
-
it 'should generate rails model generator script line' do
|
34
|
-
@morphed_class.script_generate.should == "rails destroy model ExampleMorph; rails generate model ExampleMorph noise:string"
|
35
|
-
end
|
36
|
-
|
37
|
-
it 'should generate rails model generator script line' do
|
38
|
-
@morphed_class.script_generate(:generator=>'model').should == "rails destroy model ExampleMorph; rails generate model ExampleMorph noise:string"
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
describe "when writer method that didn't exist before is called with nil value" do
|
43
|
-
before :each do
|
44
|
-
remove_morph_methods
|
45
|
-
@morph.noise= nil
|
46
|
-
@attribute = 'noise'
|
47
|
-
end
|
48
|
-
|
49
|
-
it_should_behave_like "class without generated accessor methods added"
|
50
|
-
end
|
51
|
-
|
52
|
-
describe "when different writer method called on two different morph classes" do
|
53
|
-
include MorphSpecHelperMethods
|
54
|
-
|
55
|
-
before :each do
|
56
|
-
initialize_morph
|
57
|
-
initialize_another_morph
|
58
|
-
end
|
59
|
-
|
60
|
-
it 'should have morph_method return appropriate methods for each class' do
|
61
|
-
@morph.every = 'where'
|
62
|
-
@another_morph.no = 'where'
|
63
|
-
|
64
|
-
@morphed_class.morph_methods.size.should == 2
|
65
|
-
@another_morphed_class.morph_methods.size.should == 2
|
66
|
-
|
67
|
-
if RUBY_VERSION >= "1.9"
|
68
|
-
@morphed_class.morph_methods.should == [:every,:every=]
|
69
|
-
@another_morphed_class.morph_methods.should == [:no,:no=]
|
70
|
-
else
|
71
|
-
@morphed_class.morph_methods.should == ['every','every=']
|
72
|
-
@another_morphed_class.morph_methods.should == ['no','no=']
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
it 'should call morph_attributes on both objects, when one object has a reference to another' do
|
77
|
-
@morph.every = 'which'
|
78
|
-
@another_morph.way = 'but'
|
79
|
-
@morph.loose = @another_morph
|
80
|
-
|
81
|
-
attributes = @morph.morph_attributes
|
82
|
-
attributes[:every].should == 'which'
|
83
|
-
attributes[:loose].should == {:way => 'but'}
|
84
|
-
end
|
85
|
-
|
86
|
-
it 'should call morph_attributes on both objects, when one object has a reference to array of others' do
|
87
|
-
@morph.every = 'which'
|
88
|
-
@another_morph.way = 'but'
|
89
|
-
@morph.loose = [@another_morph]
|
90
|
-
|
91
|
-
attributes = @morph.morph_attributes
|
92
|
-
attributes[:every].should == 'which'
|
93
|
-
attributes[:loose].should == [{:way => 'but'}]
|
94
|
-
end
|
95
|
-
|
96
|
-
it 'should call morph_attributes on both objects, when one object has a reference to hash of others' do
|
97
|
-
@morph.every = 'which'
|
98
|
-
@another_morph.way = 'but'
|
99
|
-
@morph.loose = { :honky_tonk => @another_morph}
|
100
|
-
|
101
|
-
attributes = @morph.morph_attributes
|
102
|
-
attributes[:every].should == 'which'
|
103
|
-
attributes[:loose].should == { :honky_tonk => {:way => 'but'} }
|
104
|
-
attributes.delete(:every)
|
105
|
-
attributes = @morph.morph_attributes
|
106
|
-
attributes[:every].should == 'which'
|
107
|
-
|
108
|
-
attributes = @morph.class.morph_attributes
|
109
|
-
attributes.should == [:every, :loose]
|
110
|
-
attributes.delete(:every)
|
111
|
-
attributes = @morph.class.morph_attributes
|
112
|
-
attributes.should == [:every, :loose]
|
113
|
-
end
|
114
|
-
|
115
|
-
after :each do
|
116
|
-
remove_morph_methods
|
117
|
-
remove_another_morph_methods
|
118
|
-
end
|
119
|
-
end
|
120
|
-
|
121
|
-
describe "when class definition contains methods and morph is included" do
|
122
|
-
include MorphSpecHelperMethods
|
123
|
-
|
124
|
-
after :all do
|
125
|
-
remove_morph_methods
|
126
|
-
@morphed_class.class_eval "remove_method :happy" if @morphed_class
|
127
|
-
end
|
128
|
-
|
129
|
-
it 'should not return methods defined in class in morph_methods list' do
|
130
|
-
initialize_morph "class ExampleMorph\n include Morph\n def happy\n 'happy, joy, joy'\n end\n end"
|
131
|
-
morph_methods.should be_empty
|
132
|
-
end
|
133
|
-
end
|
134
|
-
|
135
|
-
describe "when writer method that didn't exist before is called with blank space attribute value" do
|
136
|
-
before :each do
|
137
|
-
remove_morph_methods
|
138
|
-
@morph.noise= ' '
|
139
|
-
@attribute = 'noise'
|
140
|
-
end
|
141
|
-
|
142
|
-
it_should_behave_like "class without generated accessor methods added"
|
143
|
-
end
|
144
|
-
|
145
|
-
describe 'when morph method used to set attribute value' do
|
146
|
-
before :all do initialize_morph; end
|
147
|
-
after :all do remove_morph_methods; end
|
148
|
-
|
149
|
-
before :each do
|
150
|
-
remove_morph_methods
|
151
|
-
@value = '20 Mar 2008'
|
152
|
-
@morph.morph('Reading', @value)
|
153
|
-
@attribute = 'reading'
|
154
|
-
@expected_morph_methods_count = 2
|
155
|
-
end
|
156
|
-
|
157
|
-
it_should_behave_like "class with generated accessor methods added"
|
158
|
-
|
159
|
-
it 'should return assigned value when reader method called' do
|
160
|
-
@morph.reading.should == @value
|
161
|
-
end
|
162
|
-
end
|
163
|
-
|
164
|
-
describe 'when morph method used to set an attribute value hash' do
|
165
|
-
before :all do initialize_morph; end
|
166
|
-
after :all do remove_morph_methods; end
|
167
|
-
|
168
|
-
before :each do
|
169
|
-
remove_morph_methods
|
170
|
-
@attributes = [:drink,:sugars,:milk]
|
171
|
-
@morph.morph :drink => 'tea', :sugars => 2, :milk => 'yes please'
|
172
|
-
@expected_morph_methods_count = 6
|
173
|
-
end
|
174
|
-
|
175
|
-
it_should_behave_like "class with generated accessor methods added"
|
176
|
-
|
177
|
-
it 'should return assigned value when reader method called' do
|
178
|
-
@morph.drink.should == 'tea'
|
179
|
-
@morph.sugars.should == 2
|
180
|
-
@morph.milk.should == 'yes please'
|
181
|
-
end
|
182
|
-
|
183
|
-
it 'should generate rails model generator script line' do
|
184
|
-
@morphed_class.script_generate.should == "rails destroy model ExampleMorph; rails generate model ExampleMorph drink:string milk:string sugars:string"
|
185
|
-
end
|
186
|
-
|
187
|
-
it 'should generate rails model generator script line' do
|
188
|
-
@morphed_class.script_generate(:generator=>'model').should == "rails destroy model ExampleMorph; rails generate model ExampleMorph drink:string milk:string sugars:string"
|
189
|
-
end
|
190
|
-
end
|
191
|
-
|
192
|
-
=begin
|
193
|
-
describe "when morph method used to set unicode attribute name with a value" do
|
194
|
-
before :all do initialize_morph; end
|
195
|
-
after :all do remove_morph_methods; end
|
196
|
-
|
197
|
-
before :each do
|
198
|
-
$KCODE = "u" unless RUBY_VERSION >= "1.9"
|
199
|
-
remove_morph_methods
|
200
|
-
@age = 19
|
201
|
-
@attribute = "年龄"
|
202
|
-
@morph.morph(@attribute, @age)
|
203
|
-
@expected_morph_methods_count = 2
|
204
|
-
end
|
205
|
-
|
206
|
-
after :all do
|
207
|
-
$KCODE = "NONE" unless RUBY_VERSION >= "1.9"
|
208
|
-
end
|
209
|
-
|
210
|
-
it_should_behave_like "class with generated accessor methods added"
|
211
|
-
|
212
|
-
it 'should return assigned value when reader method called' do
|
213
|
-
@morph.send(@attribute.to_sym) == @age
|
214
|
-
end
|
215
|
-
end
|
216
|
-
describe "when morph method used to set japanese and latin unicode attribute name with a value" do
|
217
|
-
before :all do initialize_morph; end
|
218
|
-
after :all do remove_morph_methods; end
|
219
|
-
|
220
|
-
before :each do
|
221
|
-
$KCODE = "u" unless RUBY_VERSION >= "1.9"
|
222
|
-
remove_morph_methods
|
223
|
-
@age = 19
|
224
|
-
@attribute = "ページビュー_graph"
|
225
|
-
@morph.morph(@attribute, @age)
|
226
|
-
@expected_morph_methods_count = 2
|
227
|
-
end
|
228
|
-
|
229
|
-
after :all do
|
230
|
-
$KCODE = "NONE" unless RUBY_VERSION >= "1.9"
|
231
|
-
end
|
232
|
-
|
233
|
-
it_should_behave_like "class with generated accessor methods added"
|
234
|
-
|
235
|
-
it 'should return assigned value when reader method called' do
|
236
|
-
@morph.send(@attribute.to_sym) == @age
|
237
|
-
end
|
238
|
-
end
|
239
|
-
=end
|
240
|
-
describe 'when morph method used to set blank space attribute value' do
|
241
|
-
before :each do
|
242
|
-
remove_morph_methods
|
243
|
-
@morph.morph('Pizza', ' ')
|
244
|
-
@attribute = 'pizza'
|
245
|
-
end
|
246
|
-
|
247
|
-
it_should_behave_like "class without generated accessor methods added"
|
248
|
-
end
|
249
|
-
|
250
|
-
describe 'when morph method used to set nil attribute value' do
|
251
|
-
before :each do
|
252
|
-
remove_morph_methods
|
253
|
-
@morph.morph('Pizza', nil)
|
254
|
-
@attribute = 'pizza'
|
255
|
-
end
|
256
|
-
|
257
|
-
it_should_behave_like "class without generated accessor methods added"
|
258
|
-
end
|
259
|
-
|
260
|
-
|
261
|
-
describe "when reader method that didn't exist before is called" do
|
262
|
-
|
263
|
-
include MorphSpecHelperMethods
|
264
|
-
|
265
|
-
it 'should raise NoMethodError' do
|
266
|
-
initialize_morph
|
267
|
-
lambda { @morph.noise }.should raise_error(/undefined method `noise'/)
|
268
|
-
end
|
269
|
-
end
|
270
|
-
|
271
|
-
describe "when reader method called that didn't exist before is a class method" do
|
272
|
-
|
273
|
-
include MorphSpecHelperMethods
|
274
|
-
|
275
|
-
it 'should raise NoMethodError' do
|
276
|
-
initialize_morph
|
277
|
-
lambda { @morph.name }.should raise_error(/undefined method `name'/)
|
278
|
-
end
|
279
|
-
end
|
280
|
-
|
281
|
-
describe "when writer method called matches a class reader method" do
|
282
|
-
|
283
|
-
before :all do initialize_morph; end
|
284
|
-
after :all do remove_morph_methods; end
|
285
|
-
|
286
|
-
before :each do
|
287
|
-
remove_morph_methods
|
288
|
-
@value = 'Morph'
|
289
|
-
@morph.name = @value
|
290
|
-
@attribute = 'name'
|
291
|
-
@expected_morph_methods_count = 2
|
292
|
-
end
|
293
|
-
|
294
|
-
it_should_behave_like "class with generated accessor methods added"
|
295
|
-
|
296
|
-
it 'should return assigned value when reader method called' do
|
297
|
-
@morph.name.should == @value
|
298
|
-
end
|
299
|
-
end
|
300
|
-
|
301
|
-
|
302
|
-
describe "when class= is called" do
|
303
|
-
|
304
|
-
include MorphSpecHelperMethods
|
305
|
-
before :all do initialize_morph; end
|
306
|
-
after :all do remove_morph_methods; end
|
307
|
-
|
308
|
-
it 'should throw exception if non nil object is passed' do
|
309
|
-
lambda { @morph.class = 'Red' }.should raise_error(/cannot create accessor methods/)
|
310
|
-
end
|
311
|
-
|
312
|
-
it 'should throw exception if nil object is passed' do
|
313
|
-
lambda { @morph.class = nil }.should raise_error(/cannot create accessor methods/)
|
314
|
-
end
|
315
|
-
end
|
316
|
-
|
317
|
-
describe 'when passing block to morph_method_missing' do
|
318
|
-
|
319
|
-
include MorphSpecHelperMethods
|
320
|
-
before :all do initialize_morph; end
|
321
|
-
after :each do remove_morph_methods; end
|
322
|
-
|
323
|
-
it 'should class_eval the block' do
|
324
|
-
@morph.morph_method_missing(:chunky, 'bacon') do |base, attribute|
|
325
|
-
base.class_eval "def #{attribute}; 'spinach'; end"
|
326
|
-
end
|
327
|
-
@morph.respond_to?(:chunky).should == true
|
328
|
-
@morph.chunky.should == 'spinach'
|
329
|
-
@morphed_class.class_eval "remove_method :chunky"
|
330
|
-
lambda { @morph.chunky }.should raise_error
|
331
|
-
end
|
332
|
-
|
333
|
-
it 'should class_eval the block' do
|
334
|
-
@morph.morph_method_missing :chunky, 'bacon' do |base, attribute|
|
335
|
-
base.class_def(attribute) { 'spinach' }
|
336
|
-
end
|
337
|
-
@morph.respond_to?(:chunky).should == true
|
338
|
-
@morph.chunky.should == 'spinach'
|
339
|
-
@morphed_class.class_eval "remove_method :chunky"
|
340
|
-
lambda { @morph.chunky }.should raise_error
|
341
|
-
end
|
342
|
-
|
343
|
-
end
|
344
|
-
|
345
|
-
describe "when converting label text to morph method name" do
|
346
|
-
|
347
|
-
include MorphSpecHelperMethods
|
348
|
-
|
349
|
-
it 'should covert dash to underscore' do
|
350
|
-
check_convert_to_morph_method_name 'hi-time', 'hi_time'
|
351
|
-
end
|
352
|
-
it 'should upper case to lower case' do
|
353
|
-
check_convert_to_morph_method_name 'CaSe', 'case'
|
354
|
-
end
|
355
|
-
it 'should convert single space to underscorce' do
|
356
|
-
check_convert_to_morph_method_name 'First reading', 'first_reading'
|
357
|
-
end
|
358
|
-
it 'should convert multiple spaces to single underscorce' do
|
359
|
-
check_convert_to_morph_method_name "First reading", 'first_reading'
|
360
|
-
end
|
361
|
-
it 'should convert tabs to single underscorce' do
|
362
|
-
check_convert_to_morph_method_name "First\t\treading", 'first_reading'
|
363
|
-
end
|
364
|
-
it 'should convert new line chars to single underscorce' do
|
365
|
-
check_convert_to_morph_method_name "First\r\nreading", 'first_reading'
|
366
|
-
end
|
367
|
-
it 'should remove leading and trailing whitespace new line chars to single underscorce' do
|
368
|
-
check_convert_to_morph_method_name " \t\r\nFirst reading \t\r\n", 'first_reading'
|
369
|
-
end
|
370
|
-
it 'should remove trailing colon surrounded by whitespace' do
|
371
|
-
check_convert_to_morph_method_name "First reading : ", 'first_reading'
|
372
|
-
end
|
373
|
-
it 'should remove parenthesis' do
|
374
|
-
check_convert_to_morph_method_name 'Nav(GBX)', 'nav_gbx'
|
375
|
-
end
|
376
|
-
it 'should remove *' do
|
377
|
-
check_convert_to_morph_method_name 'Change**', 'change'
|
378
|
-
end
|
379
|
-
it 'should convert % character to the text "percentage"' do
|
380
|
-
check_convert_to_morph_method_name '% Change', 'percentage_change'
|
381
|
-
end
|
382
|
-
it 'should precede leading digit with an underscore character' do
|
383
|
-
check_convert_to_morph_method_name '52w_high', '_52w_high'
|
384
|
-
end
|
385
|
-
it 'should handle unicode name' do
|
386
|
-
check_convert_to_morph_method_name '年龄', '年龄'
|
387
|
-
end
|
388
|
-
end
|
389
|
-
|
390
|
-
describe 'creating from hash' do
|
391
|
-
it 'should create classes and object instances with array of hashes' do
|
392
|
-
h = {
|
393
|
-
"CompanyDetails"=> {
|
394
|
-
"SearchItems"=> [
|
395
|
-
{ "CompanyDate"=> '',
|
396
|
-
"CompanyIndexStatus"=> '',
|
397
|
-
"DataSet"=>"LIVE",
|
398
|
-
"CompanyName"=>"CANONGROVE LIMITED",
|
399
|
-
"CompanyNumber"=>"SC244777" },
|
400
|
-
{ "CompanyDate"=>"",
|
401
|
-
"CompanyIndexStatus"=>"",
|
402
|
-
"DataSet"=>"LIVE",
|
403
|
-
"CompanyName"=>"CANONHALL ACCOUNTANCY LTD",
|
404
|
-
"CompanyNumber"=>"05110715" }
|
405
|
-
]
|
406
|
-
}
|
407
|
-
}
|
408
|
-
company_details = Morph.from_hash(h)
|
409
|
-
company_details.search_items.first.class.name.should == 'Morph::SearchItem'
|
410
|
-
company_details.search_items.first.data_set.should == 'LIVE'
|
411
|
-
company_details.search_items.first.company_name.should == 'CANONGROVE LIMITED'
|
412
|
-
end
|
413
|
-
|
414
|
-
it 'should create classes and object instances' do
|
415
|
-
h = {
|
416
|
-
"CompanyDetails"=> {
|
417
|
-
:RegAddress=> {
|
418
|
-
"AddressLine"=>["ST DAVID'S HOUSE", "WEST WING", "WOOD STREET", "CARDIFF CF10 1ES"]},
|
419
|
-
"LastFullMemDate"=>"2002-03-25",
|
420
|
-
"xsi:schemaLocation"=>"xmlgwdev.companieshouse.gov.uk/v1-0/schema/CompanyDetails.xsd",
|
421
|
-
"HasBranchInfo"=>"0",
|
422
|
-
"Mortgages"=> {
|
423
|
-
"NumMortSatisfied"=>"0",
|
424
|
-
"MortgageInd"=>"LT300",
|
425
|
-
"NumMortOutstanding"=>"7",
|
426
|
-
"NumMortPartSatisfied"=>"0",
|
427
|
-
"NumMortCharges"=>"7"},
|
428
|
-
"CompanyCategory"=>"Public Limited Company",
|
429
|
-
"HasAppointments"=>"1",
|
430
|
-
"SICCodes"=> {
|
431
|
-
"SicText"=>"stadiums"},
|
432
|
-
"Returns"=> {
|
433
|
-
"Overdue"=>"NO",
|
434
|
-
"DocumentAvailable"=>"1",
|
435
|
-
"NextDueDate"=>"2003-04-22",
|
436
|
-
"LastMadeUpDate"=>"2002-03-25"
|
437
|
-
},
|
438
|
-
"CountryOfOrigin"=>"United Kingdom",
|
439
|
-
"CompanyStatus"=>"Active",
|
440
|
-
"CompanyName"=>"MILLENNIUM STADIUM PLC",
|
441
|
-
"InLiquidation"=>"0",
|
442
|
-
"xmlns:xsi"=>"http://www.w3.org/2001/XMLSchema-instance",
|
443
|
-
"Accounts"=>{
|
444
|
-
"Overdue"=>"NO",
|
445
|
-
"DocumentAvailable"=>"1",
|
446
|
-
"AccountCategory"=>"FULL",
|
447
|
-
"NextDueDate"=>"2002-11-30",
|
448
|
-
"LastMadeUpDate"=>"2001-04-30",
|
449
|
-
"AccountRefDate"=>"0000-30-04"},
|
450
|
-
"IncorporationDate"=>"1996-03-25",
|
451
|
-
"CompanyNumber"=>"03176906",
|
452
|
-
"xmlns"=>"http://xmlgw.companieshouse.gov.uk/v1-0"
|
453
|
-
}
|
454
|
-
}
|
455
|
-
Object.const_set 'Company', Module.new
|
456
|
-
Company.const_set 'House', Module.new
|
457
|
-
|
458
|
-
company_details = Morph.from_hash(h, Company::House)
|
459
|
-
company_details.class.name.should == 'Company::House::CompanyDetails'
|
460
|
-
morph_methods = company_details.class.morph_methods
|
461
|
-
if RUBY_VERSION >= "1.9"
|
462
|
-
morph_methods.include?(:last_full_mem_date).should be_true
|
463
|
-
morph_methods.include?(:accounts).should be_true
|
464
|
-
morph_methods.delete(:accounts)
|
465
|
-
morph_methods.include?(:accounts).should be_false
|
466
|
-
morph_methods = company_details.class.morph_methods
|
467
|
-
morph_methods.include?(:accounts).should be_true
|
468
|
-
else
|
469
|
-
morph_methods.include?('last_full_mem_date').should be_true
|
470
|
-
morph_methods.include?('accounts').should be_true
|
471
|
-
morph_methods.delete('accounts')
|
472
|
-
morph_methods.include?('accounts').should be_false
|
473
|
-
morph_methods = company_details.class.morph_methods
|
474
|
-
morph_methods.include?('accounts').should be_true
|
475
|
-
end
|
476
|
-
|
477
|
-
company_details.accounts.class.name.should == 'Company::House::Accounts'
|
478
|
-
company_details.accounts.overdue.should == 'NO'
|
479
|
-
company_details.last_full_mem_date.should == "2002-03-25"
|
480
|
-
company_details.sic_codes.sic_text.should == 'stadiums'
|
481
|
-
company_details.reg_address.address_lines.should == ["ST DAVID'S HOUSE", "WEST WING", "WOOD STREET", "CARDIFF CF10 1ES"]
|
482
|
-
|
483
|
-
list = Morph.generate_migrations company_details, :ignore=>['xmlns','xmlns_xsi','xsi_schema_location']
|
484
|
-
list.size.should == 7
|
485
|
-
list[0].should == "./script/generate model company_details company_category:string company_name:string company_number:string company_status:string country_of_origin:string has_appointments:string has_branch_info:string in_liquidation:string incorporation_date:date last_full_mem_date:date"
|
486
|
-
list[1].should == './script/generate model accounts company_details_id:integer account_category:string account_ref_date:date document_available:string last_made_up_date:date next_due_date:date overdue:string'
|
487
|
-
list[2].should == './script/generate model mortgages company_details_id:integer mortgage_ind:string num_mort_charges:string num_mort_outstanding:string num_mort_part_satisfied:string num_mort_satisfied:string'
|
488
|
-
list[3].should == './script/generate model reg_address company_details_id:integer'
|
489
|
-
list[4].should == './script/generate model address_lines reg_address_id:integer'
|
490
|
-
list[5].should == './script/generate model returns company_details_id:integer document_available:string last_made_up_date:date next_due_date:date overdue:string'
|
491
|
-
list[6].should == './script/generate model sic_codes company_details_id:integer sic_text:string'
|
492
|
-
|
493
|
-
yaml = %Q|--- !ruby/object:Company::House::CompanyDetails
|
494
|
-
accounts: !ruby/object:Company::House::Accounts
|
495
|
-
account_category: FULL
|
496
|
-
account_ref_date: "0000-30-04"
|
497
|
-
document_available: "1"
|
498
|
-
last_made_up_date: "2001-04-30"
|
499
|
-
next_due_date: "2002-11-30"
|
500
|
-
overdue: "NO"
|
501
|
-
company_category: Public Limited Company
|
502
|
-
company_name: MILLENNIUM STADIUM PLC
|
503
|
-
company_number: 03176906
|
504
|
-
company_status: Active
|
505
|
-
country_of_origin: United Kingdom
|
506
|
-
has_appointments: "1"
|
507
|
-
has_branch_info: "0"
|
508
|
-
in_liquidation: "0"
|
509
|
-
incorporation_date: "1996-03-25"
|
510
|
-
last_full_mem_date: "2002-03-25"
|
511
|
-
mortgages: !ruby/object:Company::House::Mortgages
|
512
|
-
mortgage_ind: LT300
|
513
|
-
num_mort_charges: "7"
|
514
|
-
num_mort_outstanding: "7"
|
515
|
-
num_mort_part_satisfied: "0"
|
516
|
-
num_mort_satisfied: "0"
|
517
|
-
reg_address: !ruby/object:Company::House::RegAddress
|
518
|
-
address_lines:
|
519
|
-
- ST DAVID'S HOUSE
|
520
|
-
- WEST WING
|
521
|
-
- WOOD STREET
|
522
|
-
- CARDIFF CF10 1ES
|
523
|
-
returns: !ruby/object:Company::House::Returns
|
524
|
-
document_available: "1"
|
525
|
-
last_made_up_date: "2002-03-25"
|
526
|
-
next_due_date: "2003-04-22"
|
527
|
-
overdue: "NO"
|
528
|
-
sic_codes: !ruby/object:Company::House::SICCodes
|
529
|
-
sic_text: stadiums
|
530
|
-
xmlns: http://xmlgw.companieshouse.gov.uk/v1-0
|
531
|
-
xmlns_xsi: http://www.w3.org/2001/XMLSchema-instance
|
532
|
-
xsi_schema_location: xmlgwdev.companieshouse.gov.uk/v1-0/schema/CompanyDetails.xsd|
|
533
|
-
end
|
534
|
-
end
|
535
|
-
|
536
|
-
describe 'creating from xml' do
|
537
|
-
|
538
|
-
def check_councils councils, class_name
|
539
|
-
councils.class.should == Array
|
540
|
-
councils.size.should == 2
|
541
|
-
councils.first.class.name.should == class_name
|
542
|
-
councils.first.name.should == 'Aberdeen City Council'
|
543
|
-
councils.last.name.should == 'Allerdale Borough Council'
|
544
|
-
end
|
545
|
-
|
546
|
-
it 'should create classes and object instances' do
|
547
|
-
councils = Morph.from_xml(xml)
|
548
|
-
check_councils councils, 'Morph::Council'
|
549
|
-
end
|
550
|
-
|
551
|
-
describe 'when module name is supplied' do
|
552
|
-
it 'should create classes and object instances' do
|
553
|
-
Object.const_set 'Ppc', Module.new
|
554
|
-
councils = Morph.from_xml(xml, Ppc)
|
555
|
-
check_councils councils, 'Ppc::Council'
|
556
|
-
end
|
557
|
-
end
|
558
|
-
|
559
|
-
def xml
|
560
|
-
%Q[<?xml version="1.0" encoding="UTF-8"?>
|
561
|
-
<councils type="array">
|
562
|
-
<council code='1'>
|
563
|
-
<name>Aberdeen City Council</name>
|
564
|
-
</council>
|
565
|
-
<council code='2'>
|
566
|
-
<name>Allerdale Borough Council</name>
|
567
|
-
</council>
|
568
|
-
</councils>]
|
569
|
-
end
|
570
|
-
end
|
571
|
-
|
572
|
-
describe 'creating from' do
|
573
|
-
|
574
|
-
def check_councillors councillors, class_name, nil_value=''
|
575
|
-
councillors.class.should == Array
|
576
|
-
councillors.size.should == 2
|
577
|
-
councillor = councillors.first
|
578
|
-
councillor.class.name.should == class_name
|
579
|
-
councillor.name.should == 'Ted Roe'
|
580
|
-
councillor.party.should == 'labour'
|
581
|
-
councillor.councillors.should == 'Councillor for Stretford Ward'
|
582
|
-
councillor.councils.should == 'Trafford Council'
|
583
|
-
councillor.respond_to?(:council_experience).should be_false
|
584
|
-
|
585
|
-
councillor = councillors.last
|
586
|
-
councillor.name.should == 'Ali Davidson'
|
587
|
-
councillor.party.should == 'labour'
|
588
|
-
councillor.councillors.should == nil_value
|
589
|
-
councillor.councils.should == 'Basildon District Council'
|
590
|
-
councillor.respond_to?(:council_experience).should be_false
|
591
|
-
end
|
592
|
-
|
593
|
-
describe 'tsv (tab separated value)' do
|
594
|
-
describe 'when class name is supplied' do
|
595
|
-
it 'should create classes and object instances' do
|
596
|
-
councillors = Morph.from_tsv(tsv, 'Councillor')
|
597
|
-
check_councillors councillors, 'Morph::Councillor'
|
598
|
-
end
|
599
|
-
end
|
600
|
-
|
601
|
-
describe 'when class name and module name is supplied' do
|
602
|
-
it 'should create classes and object instances' do
|
603
|
-
Object.const_set 'Ppc', Module.new unless defined? Ppc
|
604
|
-
councillors = Morph.from_tsv(tsv, 'Councillor', Ppc)
|
605
|
-
check_councillors councillors, 'Ppc::Councillor'
|
606
|
-
end
|
607
|
-
end
|
608
|
-
|
609
|
-
def tsv
|
610
|
-
%Q[name party councillors councils council_experience
|
611
|
-
Ted Roe labour Councillor for Stretford Ward Trafford Council
|
612
|
-
Ali Davidson labour Basildon District Council
|
613
|
-
]
|
614
|
-
end
|
615
|
-
end
|
616
|
-
|
617
|
-
describe 'csv (comma separated value)' do
|
618
|
-
describe 'when class name is supplied' do
|
619
|
-
it 'should create classes and object instances' do
|
620
|
-
councillors = Morph.from_csv(csv, 'Councillor')
|
621
|
-
check_councillors councillors, 'Morph::Councillor', nil
|
622
|
-
end
|
623
|
-
end
|
624
|
-
|
625
|
-
describe 'when class name and module name is supplied' do
|
626
|
-
it 'should create classes and object instances' do
|
627
|
-
Object.const_set 'Ppc', Module.new unless defined? Ppc
|
628
|
-
councillors = Morph.from_csv(csv, 'Councillor', Ppc)
|
629
|
-
check_councillors councillors, 'Ppc::Councillor', nil
|
630
|
-
end
|
631
|
-
end
|
632
|
-
|
633
|
-
def csv
|
634
|
-
%Q[name,party,councillors,councils,council_experience
|
635
|
-
Ted Roe,labour,Councillor for Stretford Ward,Trafford Council,
|
636
|
-
Ali Davidson,labour,,Basildon District Council,
|
637
|
-
]
|
638
|
-
end
|
639
|
-
end
|
640
|
-
end
|
641
|
-
|
642
|
-
end
|
data/spec/morph_spec_helper.rb
DELETED
@@ -1,147 +0,0 @@
|
|
1
|
-
# encoding: utf-8
|
2
|
-
require File.dirname(__FILE__) + '/../lib/morph'
|
3
|
-
|
4
|
-
module MorphSpecHelperMethods
|
5
|
-
|
6
|
-
def initialize_morph_class code=nil
|
7
|
-
code = 'class ExampleMorph; include Morph; end' unless code
|
8
|
-
eval code
|
9
|
-
@morphed_class = ExampleMorph
|
10
|
-
end
|
11
|
-
|
12
|
-
def initialize_second_morph_class code=nil
|
13
|
-
code = 'class AnotherMorph; include Morph; end' unless code
|
14
|
-
eval code
|
15
|
-
@another_morphed_class = AnotherMorph
|
16
|
-
end
|
17
|
-
|
18
|
-
def initialize_morph code=nil
|
19
|
-
initialize_morph_class code
|
20
|
-
@original_instance_methods = @morphed_class.instance_methods
|
21
|
-
@morph = @morphed_class.new
|
22
|
-
end
|
23
|
-
|
24
|
-
def initialize_another_morph
|
25
|
-
initialize_second_morph_class
|
26
|
-
@more_original_instance_methods = @another_morphed_class.instance_methods
|
27
|
-
@another_morph = @another_morphed_class.new
|
28
|
-
end
|
29
|
-
|
30
|
-
def remove_morph_methods
|
31
|
-
@morphed_class.instance_methods.each do |method|
|
32
|
-
begin
|
33
|
-
unless method.to_s[/received_message\?|should_not_receive|rspec_verify|unstub|rspec_reset|should_receive|as_null_object|stub_chain|stub\!|null_object?|stub/]
|
34
|
-
remove_cmd = "remove_method :#{method}"
|
35
|
-
@morphed_class.class_eval remove_cmd unless @original_instance_methods.include?(method)
|
36
|
-
end
|
37
|
-
rescue Exception => e
|
38
|
-
raise e.to_s + '------' + @original_instance_methods.sort.inspect
|
39
|
-
end
|
40
|
-
|
41
|
-
end if @morphed_class
|
42
|
-
end
|
43
|
-
|
44
|
-
def remove_another_morph_methods
|
45
|
-
@another_morphed_class.instance_methods.each do |method|
|
46
|
-
@another_morphed_class.class_eval "remove_method :#{method}" unless @more_original_instance_methods.include?(method)
|
47
|
-
end
|
48
|
-
end
|
49
|
-
|
50
|
-
def instance_methods
|
51
|
-
@morphed_class.instance_methods
|
52
|
-
end
|
53
|
-
|
54
|
-
def morph_methods
|
55
|
-
@morphed_class.morph_methods
|
56
|
-
end
|
57
|
-
|
58
|
-
def check_convert_to_morph_method_name label, method_name
|
59
|
-
code = 'class ExampleMorph; include Morph; def convert_to_morph_method_name label; super; end; end'
|
60
|
-
eval code
|
61
|
-
ExampleMorph.new.convert_to_morph_method_name(label).should == method_name
|
62
|
-
end
|
63
|
-
|
64
|
-
def each_attribute
|
65
|
-
if @attribute
|
66
|
-
yield @attribute
|
67
|
-
elsif @attributes
|
68
|
-
@attributes.each {|a| yield a }
|
69
|
-
end
|
70
|
-
end
|
71
|
-
end
|
72
|
-
|
73
|
-
shared_examples_for "class with generated accessor methods added" do
|
74
|
-
|
75
|
-
include MorphSpecHelperMethods
|
76
|
-
before :all do initialize_morph; end
|
77
|
-
after :all do remove_morph_methods; end
|
78
|
-
|
79
|
-
it 'should add reader method to class instance_methods list' do
|
80
|
-
if RUBY_VERSION >= "1.9"
|
81
|
-
each_attribute { |a| instance_methods.should include(a.to_s.to_sym) }
|
82
|
-
else
|
83
|
-
each_attribute { |a| instance_methods.should include(a.to_s) }
|
84
|
-
end
|
85
|
-
end
|
86
|
-
|
87
|
-
it 'should add writer method to class instance_methods list' do
|
88
|
-
if RUBY_VERSION >= "1.9"
|
89
|
-
each_attribute { |a| instance_methods.should include("#{a}=".to_sym) }
|
90
|
-
else
|
91
|
-
each_attribute { |a| instance_methods.should include("#{a}=") }
|
92
|
-
end
|
93
|
-
end
|
94
|
-
|
95
|
-
it 'should add reader method to class morph_methods list' do
|
96
|
-
if RUBY_VERSION >= "1.9"
|
97
|
-
each_attribute { |a| morph_methods.should include(a.to_s.to_sym) }
|
98
|
-
else
|
99
|
-
each_attribute { |a| morph_methods.should include(a.to_s) }
|
100
|
-
end
|
101
|
-
end
|
102
|
-
|
103
|
-
it 'should add writer method to class morph_methods list' do
|
104
|
-
if RUBY_VERSION >= "1.9"
|
105
|
-
each_attribute { |a| morph_methods.should include("#{a}=".to_sym) }
|
106
|
-
else
|
107
|
-
each_attribute { |a| morph_methods.should include("#{a}=") }
|
108
|
-
end
|
109
|
-
end
|
110
|
-
|
111
|
-
it 'should only have generated accessor methods in morph_methods list' do
|
112
|
-
morph_methods.size.should == @expected_morph_methods_count
|
113
|
-
end
|
114
|
-
|
115
|
-
end
|
116
|
-
|
117
|
-
shared_examples_for "class without generated accessor methods added" do
|
118
|
-
include MorphSpecHelperMethods
|
119
|
-
|
120
|
-
before :all do
|
121
|
-
initialize_morph
|
122
|
-
end
|
123
|
-
|
124
|
-
after :all do
|
125
|
-
remove_morph_methods
|
126
|
-
end
|
127
|
-
|
128
|
-
it 'should not add reader method to class instance_methods list' do
|
129
|
-
instance_methods.should_not include(@attribute)
|
130
|
-
end
|
131
|
-
|
132
|
-
it 'should not add writer method to class instance_methods list' do
|
133
|
-
instance_methods.should_not include("#{@attribute}=")
|
134
|
-
end
|
135
|
-
|
136
|
-
it 'should not add reader method to class morph_methods list' do
|
137
|
-
morph_methods.should_not include(@attribute)
|
138
|
-
end
|
139
|
-
|
140
|
-
it 'should not add writer method to class morph_methods list' do
|
141
|
-
morph_methods.should_not include("#{@attribute}=")
|
142
|
-
end
|
143
|
-
|
144
|
-
it 'should have empty morph_methods list' do
|
145
|
-
morph_methods.size.should == 0
|
146
|
-
end
|
147
|
-
end
|
data/spec/spec_helper.rb
DELETED