kathy_lee 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/README CHANGED
@@ -1,150 +1 @@
1
- =Kathy Lee
2
-
3
- An easy to use factory framework for generating test data for ActiveRecord models.
4
-
5
- ==Setup Examples
6
-
7
- KathyLee::User.define do
8
- username(fake(:user_name))
9
- email(fake(:email))
10
- home_page_url(fake(:url))
11
- fullname(fake(:full_name))
12
- login_count(0)
13
-
14
- has_many :posts, :size => 2
15
- has_many :comments, :size => 1
16
- end
17
-
18
- KathyLee::User::Marge.define do
19
- fullname('Marge Simpson')
20
- login_count(1000)
21
- end
22
-
23
- KathyLee::User::Marge::Other.define do
24
- home_page_url('http://www.simpsons.com')
25
-
26
- has_many :posts, :size => 5
27
- has_many :comments, :size => 1
28
- end
29
-
30
- KathyLee::Post.define do
31
- title(fake(:title))
32
- body(fake(:body))
33
-
34
- belongs_to :user
35
- has_many :comments, :size => 1
36
- end
37
-
38
- KathyLee::Comment.define do
39
- body(fake(:body))
40
-
41
- belongs_to :user
42
- belongs_to :post
43
- end
44
-
45
- KathyLee::Movie.define(:title => 'Rocky II', :director => 'Sly Stallone')
46
-
47
-
48
- # Build a new unsaved model:
49
- user = KathyLee::User.new
50
- user.username.should == 'bill.smith'
51
- user.email.should == 'bill.smith@example.org'
52
- user.home_page_url.should == 'http://www.example.com'
53
- user.fullname.should == 'Bill Smith'
54
- user.login_count.should == 0
55
- user.new_record?.should be_true
56
-
57
- # Build a new unsaved model with a few overrides:
58
- user = KathyLee::User.new(:username => 'mark.bates', :login_count => 5)
59
- user.username.should == 'mark.bates'
60
- user.email.should == 'bill.smith@example.org'
61
- user.home_page_url.should == 'http://www.example.com'
62
- user.fullname.should == 'Bill Smith'
63
- user.login_count.should == 5
64
- user.new_record?.should be_true
65
-
66
- # Build and save a new model:
67
- user = KathyLee::User.create
68
- user.username.should == 'bill.smith'
69
- user.email.should == 'bill.smith@example.org'
70
- user.home_page_url.should == 'http://www.example.com'
71
- user.fullname.should == 'Bill Smith'
72
- user.login_count.should == 0
73
- user.new_record?.should be_false
74
-
75
- # Build and save a new model with a few overrides:
76
- user = KathyLee::User.create(:username => 'mark.bates')
77
- user.username.should == 'mark.bates'
78
- user.email.should == 'bill.smith@example.org'
79
- user.home_page_url.should == 'http://www.example.com'
80
- user.fullname.should == 'Bill Smith'
81
- user.login_count.should == 0
82
- user.new_record?.should be_false
83
-
84
- # Build many unsaved models (can be used with/without block):
85
- users = KathyLee::User.sweatshop(10) do |user, index|
86
- user.login_count = index
87
- end
88
- users.size.should == 10
89
- users.each_with_index do |user, index|
90
- user.login_count.should == index
91
- user.new_record?.should be_true
92
- end
93
-
94
- # Build and save many models (can be used with/without block):
95
- users = KathyLee::User.sweatshop!(10) do |user, index|
96
- user.login_count = index
97
- end
98
- users.size.should == 10
99
- users.each_with_index do |user, index|
100
- user.login_count.should == index
101
- user.new_record?.should be_false
102
- end
103
-
104
- # Build belongs_to associations (change KathyLee::Post.new to KathyLee::Post.create to save the whole thing):
105
- post = KathyLee::Post.new
106
- post.title.should_not be_nil
107
- post.user.should_not be_nil
108
- post.user.should be_kind_of(User)
109
- post.user.email.should == 'bill.smith@example.org'
110
-
111
- # Build has_many associations (change KathyLee::User.new to KathyLee::User.create to save the whole thing):
112
- user = KathyLee::User.new
113
- user.should_not be_nil
114
- user.posts.should_not be_nil
115
- user.posts.size.should == 2
116
- user.posts.each do |post|
117
- post.should be_kind_of(Post)
118
- post.title.should_not be_nil
119
- end
120
- user.comments.should_not be_nil
121
- user.comments.size.should == 1
122
- user.comments.each do |comment|
123
- comment.should be_kind_of(Comment)
124
- end
125
-
126
- # Build a variant of a model using subclasses:
127
- user = KathyLee::User::Marge.new
128
- user.username.should == 'bill.smith'
129
- user.email.should == 'bill.smith@example.org'
130
- user.home_page_url.should == 'http://www.example.com'
131
- user.fullname.should == 'Marge Simpson'
132
- user.login_count.should == 1000
133
- user.new_record?.should be_true
134
- user.posts.size.should == 2
135
-
136
- # Subclass your subclass for further customization:
137
- user = KathyLee::User::Marge::Other.new
138
- user.username.should == 'bill.smith'
139
- user.email.should == 'bill.smith@example.org'
140
- user.home_page_url.should == 'http://www.simpsons.com'
141
- user.fullname.should == 'Marge Simpson'
142
- user.login_count.should == 1000
143
- user.new_record?.should be_true
144
- user.posts.size.should == 5
145
-
146
- ==Contact
147
-
148
- Please mail bugs, suggestions and patches to "development@metabates.com":mailto:development@metabates.com
149
-
150
- On the web at: "http://www.metabates.com":http://www.metabates.
1
+ =KathyLee - An easy to use factory framework for generating test data for objects.
@@ -0,0 +1,14 @@
1
+ require 'generators/kathy_lee'
2
+
3
+ class KathyLee
4
+ module Generators
5
+ class ModelGenerator < Base
6
+ argument :attributes, :type => :array, :default => [], :banner => "field:type field:type"
7
+ class_option :dir, :type => :string, :default => "spec/factories", :desc => "The directory where the factories should go"
8
+
9
+ def create_fixture_file
10
+ template 'fixtures.rb', File.join(options[:dir], "#{singular_name}_factories.rb")
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,11 @@
1
+ # Define attributes for <%= class_name %>:
2
+ KathyLee.attributes(:<%= singular_name %>) do
3
+ <% for attribute in attributes -%>
4
+ <%= attribute.name %> <%= attribute.default.inspect %>
5
+ <% end -%>
6
+ end
7
+
8
+ KathyLee.define(:<%= singular_name %>) do
9
+ <%= singular_name %> = <%= class_name %>.new(options)
10
+ <%= singular_name %>
11
+ end
@@ -0,0 +1,11 @@
1
+ require 'rails/generators/named_base'
2
+
3
+ class KathyLee
4
+ module Generators
5
+ class Base < Rails::Generators::NamedBase #:nodoc:
6
+ def self.source_root
7
+ @_kathy_lee_source_root ||= File.expand_path(File.join(File.dirname(__FILE__), 'kathy_lee', 'model', 'templates'))
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,31 @@
1
+ class KathyLee::Attributes::Binding
2
+
3
+ attr_accessor :results
4
+ attr_accessor :attributes
5
+ attr_accessor :code_block
6
+
7
+ def initialize(attributes = {}, &block)
8
+ self.results = {}
9
+ self.attributes = attributes
10
+ self.code_block = block
11
+ end
12
+
13
+ def process!
14
+ if self.code_block
15
+ instance_eval(&self.code_block)
16
+ end
17
+ self.results.merge!(self.attributes)
18
+ end
19
+
20
+ def fake(name)
21
+ KathyLee::Fakes.execute(name)
22
+ end
23
+
24
+ def method_missing(sym, args = nil, &block)
25
+ self.results[sym] = args unless args.nil?
26
+ if block_given?
27
+ self.results[sym] = block.call
28
+ end
29
+ end
30
+
31
+ end
@@ -0,0 +1,18 @@
1
+ class KathyLee::Attributes
2
+
3
+ attr_accessor :attributes
4
+ attr_accessor :code_block
5
+
6
+ def initialize(attributes = {}, &block)
7
+ self.attributes = attributes
8
+ self.code_block = block
9
+ end
10
+
11
+ def process(attribs = {})
12
+ b = KathyLee::Attributes::Binding.new(self.attributes.merge(attribs), &self.code_block)
13
+ b.process!
14
+ return b.results
15
+ end
16
+
17
+
18
+ end
@@ -0,0 +1,72 @@
1
+ # Used to evaluate a KathyLee::Definition in it's own 'space' (binding)
2
+ class KathyLee::Definition::Binding
3
+
4
+ attr_accessor :factory_name
5
+ attr_accessor :options
6
+ attr_accessor :code_block
7
+ attr_accessor :result
8
+ attr_accessor :has_ones
9
+ attr_accessor :has_manys
10
+ attr_accessor :parent
11
+
12
+ def initialize(factory_name, attributes = {}, &block)
13
+ self.factory_name = factory_name
14
+ attrib_name = attributes.delete(:attributes_for) || factory_name.to_sym
15
+ self.options = (KathyLee.attributes(attrib_name) || {}).merge(attributes)
16
+ self.code_block = block
17
+ self.has_ones = {}
18
+ self.has_manys = {}
19
+ end
20
+
21
+ def has_one(factory, options = {}, &block)
22
+ self.has_ones[factory.to_sym] = {:options => options, :code_block => block,
23
+ :klass => self.options.delete(factory.to_sym)}
24
+ end
25
+
26
+ def has_many(factory, options = {}, &block)
27
+ options = {:size => 2}.merge(options)
28
+ self.has_manys[factory.to_sym] = KathyLee::Definition::HasMany.new(factory.to_sym, {:options => options, :code_block => block, :klass => self.options.delete(factory.to_sym)})
29
+ end
30
+
31
+ def process!
32
+ self.result = instance_eval(&self.code_block)
33
+ handle_has_ones
34
+ handle_has_manys
35
+ end
36
+
37
+ protected
38
+ def handle_has_ones
39
+ self.has_ones.each do |factory, h|
40
+ if h[:klass]
41
+ self.result.send("#{factory}=", h[:klass])
42
+ else
43
+ if h[:code_block]
44
+ b = KathyLee::Definition::Binding.new(factory, h[:options], &h[:code_block])
45
+ # b.send(:eval, %{
46
+ # def #{self.factory_name}=(x)
47
+ # @__#{self.factory_name} = x
48
+ # end
49
+ # def #{self.factory_name}
50
+ # @__#{self.factory_name}
51
+ # end
52
+ # })
53
+ # b.send("#{self.factory_name}=", self.result)
54
+ b.parent = self.result
55
+ b.process!
56
+ self.result.send("#{factory}=", b.result)
57
+ else
58
+ self.result.send("#{factory}=", KathyLee.build(factory, h[:options]))
59
+ end
60
+ end
61
+ end
62
+ end
63
+
64
+ def handle_has_manys
65
+ self.has_manys.each do |factory, h|
66
+ h.build.each do |obj|
67
+ self.result.send("#{factory}") << obj
68
+ end
69
+ end
70
+ end
71
+
72
+ end
@@ -0,0 +1,27 @@
1
+ class KathyLee::Definition::HasMany < KathyLee::Definition::Relationship
2
+ attr_accessor :size
3
+
4
+ def initialize(factory, options = {})
5
+ super(factory, options)
6
+ self.size = (self.options.delete(:size) || 2)
7
+ end
8
+
9
+ def build
10
+ results = []
11
+ self.size.times do
12
+ if self.klass
13
+ results << self.klass
14
+ else
15
+ if self.code_block
16
+ b = KathyLee::Definition::Binding.new(self.factory, self.options, self.code_block)
17
+ b.process!
18
+ results << b.result
19
+ else
20
+ results << KathyLee.build(self.factory, self.options)
21
+ end
22
+ end
23
+ end
24
+ [results].flatten
25
+ end
26
+
27
+ end
@@ -0,0 +1,3 @@
1
+ class KathyLee::Definition::HasOne < KathyLee::Definition::Relationship
2
+
3
+ end
@@ -0,0 +1,14 @@
1
+ class KathyLee::Definition::Relationship
2
+ attr_accessor :options
3
+ attr_accessor :code_block
4
+ attr_accessor :klass
5
+ attr_accessor :factory
6
+
7
+ def initialize(factory, options = {})
8
+ self.factory = factory
9
+ self.options = options
10
+ self.klass = self.options.delete(:klass)
11
+ self.code_block = self.options.delete(:code_block)
12
+ end
13
+
14
+ end
@@ -0,0 +1,38 @@
1
+ # Houses the definition of a factory.
2
+ #
3
+ # Examples:
4
+ # KathyLee.define(:user) do
5
+ # user = User.new(options)
6
+ # ... # do some more work
7
+ # user
8
+ # end
9
+ #
10
+ # KathyLee.define(:user) do
11
+ # has_one :blog # will call the :blog factory and assign it to the
12
+ # # user object when it's returned from the block.
13
+ #
14
+ # user = User.new(options)
15
+ # ... # do some more work
16
+ # user
17
+ # end
18
+ class KathyLee::Definition
19
+
20
+ attr_accessor :factory_name
21
+ attr_accessor :attributes
22
+ attr_accessor :code_block
23
+
24
+ def initialize(factory_name, attributes = {}, &block)
25
+ self.attributes = attributes
26
+ self.factory_name = factory_name
27
+ self.code_block = block
28
+ end
29
+
30
+ # Execute the code block in it's own building, with it's own attributes
31
+ # and return the result.
32
+ def build(attribs = {})
33
+ b = KathyLee::Definition::Binding.new(self.factory_name, self.attributes.merge(attribs), &self.code_block)
34
+ b.process!
35
+ return b.result
36
+ end
37
+
38
+ end
@@ -1,25 +1,41 @@
1
- module KathyLee
1
+ class KathyLee
2
+ # A registry for procs that can be called to generate random, or fake, data.
2
3
  class Fakes
3
4
  include Singleton
4
-
5
+
6
+ # List of all the fake procs in the system.
5
7
  attr_accessor :list
6
-
7
- def initialize
8
+
9
+ def initialize # :nodoc:
8
10
  self.reset!
9
11
  end
10
-
11
- def reset!
12
+
13
+ def reset! # :nodoc:
12
14
  self.list = {}
13
15
  end
14
-
16
+
17
+ # Add a new proc to the system.
18
+ #
19
+ # Example:
20
+ # KathyLee::Fakes.add(:birth_date) {(rand(80) + 13).years.ago}
15
21
  def add(name, &block)
16
22
  self.list[name.to_sym] = block
17
23
  end
18
24
 
25
+ # Create an alias from one fake proc to another.
26
+ #
27
+ # Example:
28
+ # KathyLee::Fakes.add(:birth_date) {(rand(80) + 13).years.ago}
29
+ # KathyLee::Fakes.alias(:birthday, :birth_date)
19
30
  def alias(from, to)
20
31
  self.list[from.to_sym] = KathyLee::Fakes::Alias.new(to)
21
32
  end
22
-
33
+
34
+ # Executes the specified fake proc. Raise KathyLee::Errors::NoFakeRegistered
35
+ # if the fake proc is not registered with the system.
36
+ #
37
+ # Example:
38
+ # KathyLee::Fakes.execute(:email) # => 'bob@example.com'
23
39
  def execute(name, *args)
24
40
  block = self.list[name.to_sym]
25
41
  if block.is_a?(KathyLee::Fakes::Alias)
@@ -28,17 +44,17 @@ module KathyLee
28
44
  if block
29
45
  return block.call(*args)
30
46
  end
31
- raise KathyLee::Errors::NoFakeRegistered.new(name)
47
+ raise "No fake has been registered for '#{name}'!"
32
48
  end
33
-
49
+
34
50
  class << self
35
- def method_missing(sym, *args, &block)
51
+ def method_missing(sym, *args, &block) # :nodoc:
36
52
  KathyLee::Fakes.instance.send(sym, *args, &block)
37
53
  end
38
54
  end # class << self
39
-
55
+
40
56
  private
41
- class Alias
57
+ class Alias # :nodoc:
42
58
  attr_accessor :to
43
59
  def initialize(to)
44
60
  self.to = to
@@ -48,34 +64,80 @@ module KathyLee
48
64
  end # Fakes
49
65
  end # KathyLee
50
66
 
51
- %w{first_name last_name name prefix suffix}.each do |m|
52
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Name.#{m}(*args)}")
67
+ %w{zip_code us_state us_state_short city street_name street_address neighborhood}.each do |m|
68
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Address.#{m}}")
53
69
  end
54
70
 
55
- %w{city city_prefix city_suffix secondary_address street_address street_name
56
- street_suffix uk_country uk_county uk_postcode us_state us_state_abbr zip_code}.each do |m|
57
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Address.#{m}(*args)}")
71
+ %w{name catch_phrase bs}.each do |m|
72
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Company.#{m}}")
58
73
  end
59
74
 
60
- %w{bs catch_phrase name suffix}.each do |m|
61
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Company.#{m}(*args)}")
75
+ KathyLee::Fakes.add(:company_name) {|*args| Dummy::Company.name}
76
+
77
+ %w{lat lng}.each do |m|
78
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Geolocation.#{m}}")
62
79
  end
63
80
 
64
- %w{domain_name domain_suffix domain_word email free_email user_name}.each do |m|
65
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Internet.#{m}(*args)}")
81
+ %w{email username password url}.each do |m|
82
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Internet.#{m}}")
66
83
  end
67
84
 
68
- %w{paragraph paragraphs sentence sentences words}.each do |m|
69
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Lorem.#{m}(*args)}")
85
+ KathyLee::Fakes.alias(:login, :username)
86
+
87
+ %w{sentence sentences paragraph paragraphs}.each do |m|
88
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Lorem.#{m}}")
70
89
  end
71
90
 
72
- %w{phone_number}.each do |m|
73
- eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::PhoneNumber.#{m}(*args)}")
91
+ KathyLee::Fakes.add(:lorem) do |*args|
92
+ lorem = []
93
+ 3.times {lorem << Dummy::Lorem.paragraph}
94
+ lorem.join("\n")
74
95
  end
75
96
 
76
- KathyLee::Fakes.add(:url) {|*args| 'http://' + Faker::Internet.domain_name(*args)}
77
- KathyLee::Fakes.add(:lorem) {|*args| Faker::Lorem.paragraphs(*args).join("\n")}
78
- KathyLee::Fakes.add(:name) {|*args| Faker::Name.first_name + ' ' + Faker::Name.last_name}
79
97
  KathyLee::Fakes.alias(:body, :lorem)
98
+
99
+ %w{name first_name last_name}.each do |m|
100
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::Name.#{m}}")
101
+ end
102
+
80
103
  KathyLee::Fakes.alias(:full_name, :name)
81
- KathyLee::Fakes.alias(:title, :sentence)
104
+
105
+ %w{phone_number phone_number_short}.each do |m|
106
+ eval("KathyLee::Fakes.add(:#{m}) {|*args| Dummy::PhoneNumber.#{m}}")
107
+ end
108
+
109
+ # %w{first_name last_name name prefix suffix}.each do |m|
110
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Name.#{m}(*args)}")
111
+ # end
112
+ #
113
+ # %w{city city_prefix city_suffix secondary_address street_address street_name
114
+ # street_suffix uk_country uk_county uk_postcode us_state us_state_abbr zip_code}.each do |m|
115
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Address.#{m}(*args)}")
116
+ # end
117
+ #
118
+ # %w{bs catch_phrase name suffix}.each do |m|
119
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Company.#{m}(*args)}")
120
+ # end
121
+ #
122
+ # %w{domain_name domain_suffix domain_word email free_email user_name}.each do |m|
123
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Internet.#{m}(*args)}")
124
+ # end
125
+ #
126
+ # %w{paragraph paragraphs sentence sentences words}.each do |m|
127
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::Lorem.#{m}(*args)}")
128
+ # end
129
+ #
130
+ # %w{phone_number}.each do |m|
131
+ # eval("KathyLee::Fakes.add(:#{m}) {|*args| Faker::PhoneNumber.#{m}(*args)}")
132
+ # end
133
+ #
134
+ # KathyLee::Fakes.add(:url) {|*args| 'http://' + Faker::Internet.domain_name(*args)}
135
+ # KathyLee::Fakes.add(:lorem) {|*args| Faker::Lorem.paragraphs(*args).join("\n")}
136
+ # KathyLee::Fakes.add(:name) {|*args| Faker::Name.first_name + ' ' + Faker::Name.last_name}
137
+ # KathyLee::Fakes.add(:birth_date) {|*args| (rand(80) + 13).years.ago}
138
+ # KathyLee::Fakes.add(:title) {|*args| Faker::Company.catch_phrase.slice(0..250)}
139
+ # KathyLee::Fakes.add(:username) {|*args| Faker::Internet.user_name}
140
+ # KathyLee::Fakes.add(:company_name) {|*args| Faker::Company.name}
141
+ # KathyLee::Fakes.alias(:login, :username)
142
+ # KathyLee::Fakes.alias(:body, :lorem)
143
+ # KathyLee::Fakes.alias(:full_name, :name)
@@ -1,15 +1,68 @@
1
- module KathyLee
1
+ # Put your gem code here:
2
+
3
+ class KathyLee
4
+ include Singleton
5
+
6
+ attr_accessor :factories
7
+ attr_accessor :factory_attributes
8
+
9
+ def initialize
10
+ self.factories = {}
11
+ self.factory_attributes = {}
12
+ end
13
+
14
+ def build(factory_name, attributes = {})
15
+ if self.factories[factory_name.to_sym]
16
+ return self.factories[factory_name.to_sym].build(attributes)
17
+ else
18
+ self.define(factory_name, attributes) do
19
+ object = factory_name.to_s.classify.constantize.new(options)
20
+ object
21
+ end
22
+ self.build(factory_name, attributes)
23
+ end
24
+ end
25
+
26
+ def create(factory_name, attributes = {})
27
+ object = self.build(factory_name, attributes)
28
+ object.save!
29
+ return object
30
+ end
31
+
32
+ def attributes(factory_name, attributes = {}, &block)
33
+ if block_given?
34
+ self.factory_attributes[factory_name] = KathyLee::Attributes.new(attributes, &block)
35
+ end
36
+ if self.factory_attributes.has_key?(factory_name)
37
+ return self.factory_attributes[factory_name].process(attributes)
38
+ end
39
+ return nil
40
+ end
41
+
42
+ def define(factory_name, attributes = {}, &block)
43
+ self.factories[factory_name.to_sym] = KathyLee::Definition.new(factory_name, attributes, &block)
44
+ end
45
+
46
+ def sweatshop(factory_name, *options, count)
47
+ results = []
48
+ count.times do
49
+ results << self.build(factory_name, (options.first || {}))
50
+ end
51
+ return results
52
+ end
53
+
54
+ def sweatshop!(factory_name, *options, count)
55
+ results = self.sweatshop(factory_name, *options, count)
56
+ results.each {|x| x.save!}
57
+ return results
58
+ end
2
59
 
3
60
  class << self
4
61
 
5
- def const_missing(klass, for_klass = klass)
6
- @klass = klass
7
- @for_klass = for_klass
8
- result = ERB.new(File.read(File.join(File.dirname(__FILE__), 'templates', 'proxy.html.erb'))).result(binding)
9
- eval(result)
10
- return "KathyLee::#{klass}".constantize
62
+ def method_missing(sym, *args, &block)
63
+ KathyLee.instance.send(sym, *args, &block)
11
64
  end
12
65
 
13
- end # class << self
66
+ end
14
67
 
15
- end
68
+ end
data/lib/kathy_lee.rb CHANGED
@@ -1,16 +1,20 @@
1
1
  require 'singleton'
2
- require 'faker'
3
- require 'benchmark'
4
- require 'erb'
2
+ require 'active_support'
3
+ require 'dummy'
5
4
 
6
- class Symbol
7
-
8
- def classify
9
- self.to_s.classify
5
+ # A monkey patch for dummy:
6
+ class Array
7
+ def rand
8
+ self[Kernel.rand(self.length)]
10
9
  end
11
-
12
10
  end
13
11
 
14
- Dir.glob(File.join(File.dirname(__FILE__), 'kathy_lee', '**/*.rb')).each do |f|
15
- require File.expand_path(f)
12
+
13
+ path = File.join(File.dirname(__FILE__), 'kathy_lee')
14
+
15
+ %w{kathy_lee definition definition/binding definition/relationship
16
+ definition/has_one definition/has_many attributes attributes/binding fakes}.each do |file|
17
+ require File.expand_path(File.join(path, file))
16
18
  end
19
+
20
+ # require File.join(File.dirname(__FILE__), 'generators', 'kathy_lee')
metadata CHANGED
@@ -1,7 +1,12 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: kathy_lee
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ prerelease: false
5
+ segments:
6
+ - 0
7
+ - 2
8
+ - 0
9
+ version: 0.2.0
5
10
  platform: ruby
6
11
  authors:
7
12
  - markbates
@@ -9,21 +14,37 @@ autorequire:
9
14
  bindir: bin
10
15
  cert_chain: []
11
16
 
12
- date: 2010-01-04 00:00:00 -05:00
17
+ date: 2010-08-25 00:00:00 -04:00
13
18
  default_executable:
14
19
  dependencies:
15
20
  - !ruby/object:Gem::Dependency
16
- name: faker
21
+ name: activesupport
22
+ requirement: &id001 !ruby/object:Gem::Requirement
23
+ none: false
24
+ requirements:
25
+ - - ">="
26
+ - !ruby/object:Gem::Version
27
+ segments:
28
+ - 0
29
+ version: "0"
17
30
  type: :runtime
18
- version_requirement:
19
- version_requirements: !ruby/object:Gem::Requirement
31
+ prerelease: false
32
+ version_requirements: *id001
33
+ - !ruby/object:Gem::Dependency
34
+ name: dummy
35
+ requirement: &id002 !ruby/object:Gem::Requirement
36
+ none: false
20
37
  requirements:
21
38
  - - ">="
22
39
  - !ruby/object:Gem::Version
23
- version: 0.3.1
24
- version:
40
+ segments:
41
+ - 0
42
+ version: "0"
43
+ type: :runtime
44
+ prerelease: false
45
+ version_requirements: *id002
25
46
  description: "kathy_lee was developed by: markbates"
26
- email: ""
47
+ email: mark+kathylee@markbates.com
27
48
  executables: []
28
49
 
29
50
  extensions: []
@@ -32,18 +53,23 @@ extra_rdoc_files:
32
53
  - README
33
54
  - LICENSE
34
55
  files:
35
- - lib/kathy_lee/errors/no_fake_registered.rb
56
+ - lib/generators/kathy_lee/model/model_generator.rb
57
+ - lib/generators/kathy_lee/model/templates/fixtures.rb
58
+ - lib/generators/kathy_lee.rb
59
+ - lib/kathy_lee/attributes/binding.rb
60
+ - lib/kathy_lee/attributes.rb
61
+ - lib/kathy_lee/definition/binding.rb
62
+ - lib/kathy_lee/definition/has_many.rb
63
+ - lib/kathy_lee/definition/has_one.rb
64
+ - lib/kathy_lee/definition/relationship.rb
65
+ - lib/kathy_lee/definition.rb
36
66
  - lib/kathy_lee/fakes.rb
37
67
  - lib/kathy_lee/kathy_lee.rb
38
- - lib/kathy_lee/proxy.rb
39
- - lib/kathy_lee/proxy_manager.rb
40
- - lib/kathy_lee/templates/proxy.html.erb
41
- - lib/kathy_lee/transaction.rb
42
68
  - lib/kathy_lee.rb
43
69
  - README
44
70
  - LICENSE
45
71
  has_rdoc: true
46
- homepage: ""
72
+ homepage: http://www.metabates.com
47
73
  licenses: []
48
74
 
49
75
  post_install_message:
@@ -52,21 +78,26 @@ rdoc_options: []
52
78
  require_paths:
53
79
  - lib
54
80
  required_ruby_version: !ruby/object:Gem::Requirement
81
+ none: false
55
82
  requirements:
56
83
  - - ">="
57
84
  - !ruby/object:Gem::Version
85
+ hash: -2942405895079934725
86
+ segments:
87
+ - 0
58
88
  version: "0"
59
- version:
60
89
  required_rubygems_version: !ruby/object:Gem::Requirement
90
+ none: false
61
91
  requirements:
62
92
  - - ">="
63
93
  - !ruby/object:Gem::Version
94
+ segments:
95
+ - 0
64
96
  version: "0"
65
- version:
66
97
  requirements: []
67
98
 
68
99
  rubyforge_project: magrathea
69
- rubygems_version: 1.3.5
100
+ rubygems_version: 1.3.7
70
101
  signing_key:
71
102
  specification_version: 3
72
103
  summary: kathy_lee
@@ -1,11 +0,0 @@
1
- module KathyLee
2
- module Errors
3
- class NoFakeRegistered < StandardError
4
-
5
- def initialize(name)
6
- super("No fake has been registered for '#{name}'!")
7
- end
8
-
9
- end # NoFakeRegistered
10
- end # Errors
11
- end # KathyLee
@@ -1,113 +0,0 @@
1
- module KathyLee
2
- class Proxy
3
- attr_accessor :for
4
- attr_accessor :attributes
5
- attr_accessor :belongs_tos
6
- attr_accessor :has_manys
7
-
8
- class << self
9
-
10
- def define(options = {}, &block)
11
- KathyLee::ProxyManager.set_attributes(self, options, &block)
12
- end
13
-
14
- def create(options = {})
15
- model = self.new(options)
16
- model.save!
17
- return model
18
- end
19
-
20
- def new(options = {})
21
- proxy = super(options)
22
- KathyLee::Transaction.execute do
23
- proxy.build_new
24
- end
25
- end
26
-
27
- def sweatshop(count, options = {}, &block)
28
- models = []
29
- count.times do |i|
30
- model = self.new(options)
31
- yield model, i if block_given?
32
- models << model
33
- end
34
- return models
35
- end
36
-
37
- def sweatshop!(count, &block)
38
- nmodels = []
39
- models = self.sweatshop(count, &block)
40
- models.each do |m|
41
- m.save!
42
- nmodels << m
43
- end
44
- return models
45
- end
46
-
47
- end # class << self
48
-
49
- def initialize(options = {})
50
- self.for = self.class.for
51
- self.belongs_tos = {}
52
- self.has_manys = {}
53
-
54
- opts = KathyLee::ProxyManager.get_attributes(self.class)
55
- self.attributes = opts[:attributes]
56
- instance_eval(&opts[:definition_block]) if opts[:definition_block]
57
- self.attributes.merge!(options) if options.is_a?(Hash)
58
- end
59
-
60
- def build_new
61
- model = self.for.send(:new, self.attributes)
62
- KathyLee::Transaction.register(model)
63
- model = build_has_manys(model)
64
- model = build_belongs_to(model)
65
- return model
66
- end
67
-
68
- def method_missing(sym, *args)
69
- self.attributes[sym] = *args
70
- end
71
-
72
- def belongs_to(owner, options = {})
73
- self.belongs_tos[owner.to_sym] = options
74
- end
75
-
76
- def has_many(things, options = {})
77
- self.has_manys[things.to_sym] = options
78
- end
79
-
80
- def fake(sym, *args)
81
- KathyLee::Fakes.execute(sym, *args)
82
- end
83
-
84
- protected
85
- def build_has_manys(model)
86
- hm = self.has_manys.dup
87
- hm.each do |things, opts|
88
- options = opts.dup
89
- size = options.delete(:size) || 2
90
- thing_klass = "::KathyLee::#{things.classify}".constantize
91
- model.send("#{things}=", []) # clear out any parents versions of this
92
- model.send(things) << thing_klass.sweatshop(size)
93
- end
94
-
95
- return model
96
- end
97
-
98
- def build_belongs_to(model)
99
- bt = self.belongs_tos.dup
100
-
101
- bt.each do |owner, opts|
102
- thing_klass = "::KathyLee::#{owner.classify}".constantize
103
- thing = KathyLee::Transaction.get_model(thing_klass.for) do
104
- thing_klass.new(opts)
105
- end
106
- model.send("#{owner}=", thing)
107
- end
108
-
109
- return model
110
- end
111
-
112
- end # Proxy
113
- end # KathyLee
@@ -1,34 +0,0 @@
1
- module KathyLee
2
- class ProxyManager
3
- include Singleton
4
-
5
- attr_accessor :proxies
6
-
7
- def initialize
8
- self.reset!
9
- end
10
-
11
- def reset!
12
- self.proxies = {}
13
- end
14
-
15
- def get_attributes(klass)
16
- proxy = self.proxies[klass]
17
- return proxy if proxy
18
- return {:attributes => {}}
19
- end
20
-
21
- def set_attributes(klass, attributes = {}, &block)
22
- options = {:attributes => attributes}
23
- options[:definition_block] = block if block_given?
24
- self.proxies[klass] = options
25
- end
26
-
27
- class << self
28
- def method_missing(sym, *args, &block)
29
- KathyLee::ProxyManager.instance.send(sym, *args, &block)
30
- end
31
- end # class << self
32
-
33
- end # ProxyManager
34
- end # KathyLee
@@ -1,15 +0,0 @@
1
- class KathyLee::<%= @klass %> < KathyLee::Proxy
2
-
3
- class << self
4
-
5
- def for
6
- ::<%= @for_klass %>
7
- end
8
-
9
- def const_missing(klass, for_klass = <%= @klass %>)
10
- KathyLee.const_missing(klass, for_klass)
11
- end
12
-
13
- end
14
-
15
- end
@@ -1,51 +0,0 @@
1
- module KathyLee
2
- class Transaction
3
- include Singleton
4
-
5
- attr_accessor :started
6
- attr_accessor :models
7
- attr_accessor :transaction_id
8
-
9
- class << self
10
- def method_missing(sym, *args, &block)
11
- KathyLee::Transaction.instance.send(sym, *args, &block)
12
- end
13
- end
14
-
15
- def initialize
16
- self.reset!
17
- end
18
-
19
- def reset!
20
- self.started = false
21
- self.models = {}
22
- end
23
-
24
- def register(model)
25
- self.models[model.class.name.to_sym] = model
26
- end
27
-
28
- def get_model(klass, &block)
29
- model = self.models[klass.name.to_sym]
30
- if block_given? && model.nil?
31
- model = yield
32
- self.register(model)
33
- end
34
- return model
35
- end
36
-
37
- def execute(&block)
38
- unless self.started
39
- self.transaction_id = rand.to_s.gsub('0.', '')
40
- self.started = true
41
- results = yield if block_given?
42
- self.reset!
43
- return results
44
- else
45
- results = yield if block_given?
46
- return results
47
- end
48
- end
49
-
50
- end # Transaction
51
- end # KathyLee