simple_record 2.1.10 → 2.1.11

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.
@@ -62,18 +62,18 @@ module SimpleRecord
62
62
  class << self;
63
63
  attr_accessor :aws_access_key, :aws_secret_key
64
64
 
65
- # Deprecated
65
+ # Deprecated
66
66
  def enable_logging
67
67
  @@logging = true
68
68
  @@logger.level = Logger::DEBUG
69
69
  end
70
70
 
71
- # Deprecated
71
+ # Deprecated
72
72
  def disable_logging
73
73
  @@logging = false
74
74
  end
75
75
 
76
- # Deprecated
76
+ # Deprecated
77
77
  def logging?
78
78
  @@logging
79
79
  end
@@ -82,9 +82,9 @@ module SimpleRecord
82
82
  @@logger
83
83
  end
84
84
 
85
- # This can be used to log queries and what not to a file.
86
- # Params:
87
- # :select=>{:filename=>"file_to_write_to", :format=>"csv"}
85
+ # This can be used to log queries and what not to a file.
86
+ # Params:
87
+ # :select=>{:filename=>"file_to_write_to", :format=>"csv"}
88
88
  def log_usage(types={})
89
89
  @usage_logging_options = {} unless @usage_logging_options
90
90
  return if types.nil?
@@ -109,26 +109,26 @@ module SimpleRecord
109
109
  end
110
110
 
111
111
 
112
- # Create a new handle to an Sdb account. All handles share the same per process or per thread
113
- # HTTP connection to Amazon Sdb. Each handle is for a specific account.
114
- # The +params+ are passed through as-is to Aws::SdbInterface.new
115
- # Params:
116
- # { :server => 'sdb.amazonaws.com' # Amazon service host: 'sdb.amazonaws.com'(default)
117
- # :port => 443 # Amazon service port: 80(default) or 443
118
- # :protocol => 'https' # Amazon service protocol: 'http'(default) or 'https'
119
- # :signature_version => '0' # The signature version : '0' or '1'(default)
120
- # :connection_mode => :default # options are
121
- # :default (will use best known safe (as in won't need explicit close) option, may change in the future)
122
- # :per_request (opens and closes a connection on every request to SDB)
123
- # :single (one thread across entire app)
124
- # :per_thread (one connection per thread)
125
- # :pool (uses a connection pool with a maximum number of connections - NOT IMPLEMENTED YET)
126
- # :logger => Logger Object # Logger instance: logs to STDOUT if omitted
112
+ # Create a new handle to an Sdb account. All handles share the same per process or per thread
113
+ # HTTP connection to Amazon Sdb. Each handle is for a specific account.
114
+ # The +params+ are passed through as-is to Aws::SdbInterface.new
115
+ # Params:
116
+ # { :server => 'sdb.amazonaws.com' # Amazon service host: 'sdb.amazonaws.com'(default)
117
+ # :port => 443 # Amazon service port: 80(default) or 443
118
+ # :protocol => 'https' # Amazon service protocol: 'http'(default) or 'https'
119
+ # :signature_version => '0' # The signature version : '0' or '1'(default)
120
+ # :connection_mode => :default # options are
121
+ # :default (will use best known safe (as in won't need explicit close) option, may change in the future)
122
+ # :per_request (opens and closes a connection on every request to SDB)
123
+ # :single (one thread across entire app)
124
+ # :per_thread (one connection per thread)
125
+ # :pool (uses a connection pool with a maximum number of connections - NOT IMPLEMENTED YET)
126
+ # :logger => Logger Object # Logger instance: logs to STDOUT if omitted
127
127
  def establish_connection(aws_access_key=nil, aws_secret_key=nil, options={})
128
128
  @aws_access_key = aws_access_key
129
129
  @aws_secret_key = aws_secret_key
130
130
  @@options.merge!(options)
131
- #puts 'SimpleRecord.establish_connection with options: ' + @@options.inspect
131
+ #puts 'SimpleRecord.establish_connection with options: ' + @@options.inspect
132
132
  SimpleRecord::ActiveSdb.establish_connection(aws_access_key, aws_secret_key, @@options)
133
133
  if options[:connection_mode] == :per_thread
134
134
  @@auto_close_s3 = true
@@ -147,17 +147,17 @@ module SimpleRecord
147
147
 
148
148
  end
149
149
 
150
- # Call this to close the connection to SimpleDB.
151
- # If you're using this in Rails with per_thread connection mode, you should do this in
152
- # an after_filter for each request.
150
+ # Call this to close the connection to SimpleDB.
151
+ # If you're using this in Rails with per_thread connection mode, you should do this in
152
+ # an after_filter for each request.
153
153
  def close_connection()
154
154
  SimpleRecord::ActiveSdb.close_connection
155
155
  @@s3.close_connection if @@auto_close_s3
156
156
  end
157
157
 
158
- # If you'd like to specify the s3 connection to use for LOBs, you can pass it in here.
159
- # We recommend that this connection matches the type of connection you're using for SimpleDB,
160
- # at least if you're using per_thread connection mode.
158
+ # If you'd like to specify the s3 connection to use for LOBs, you can pass it in here.
159
+ # We recommend that this connection matches the type of connection you're using for SimpleDB,
160
+ # at least if you're using per_thread connection mode.
161
161
  def s3=(s3)
162
162
  @@s3 = s3
163
163
  end
@@ -196,7 +196,7 @@ module SimpleRecord
196
196
  include SimpleRecord::Callbacks
197
197
  end
198
198
  include SimpleRecord::Validations
199
-
199
+ extend SimpleRecord::Validations::ClassMethods
200
200
 
201
201
  include SimpleRecord::Translations
202
202
  # include SimpleRecord::Attributes
@@ -217,7 +217,7 @@ module SimpleRecord
217
217
 
218
218
  initialize_base(attrs)
219
219
 
220
- # Convert attributes to sdb values
220
+ # Convert attributes to sdb values
221
221
  attrs.each_pair do |name, value|
222
222
  set(name, value, true)
223
223
  end
@@ -226,7 +226,7 @@ module SimpleRecord
226
226
  def initialize_base(attrs={})
227
227
 
228
228
  #we have to handle the virtuals.
229
- Attributes.handle_virtuals(attrs)
229
+ handle_virtuals(attrs)
230
230
 
231
231
  clear_errors
232
232
 
@@ -278,10 +278,10 @@ module SimpleRecord
278
278
  attr_accessor :domain_prefix
279
279
  end
280
280
 
281
- #@domain_name_for_class = nil
281
+ #@domain_name_for_class = nil
282
282
 
283
283
  @@cache_store = nil
284
- # Set the cache to use
284
+ # Set the cache to use
285
285
  def self.cache_store=(cache)
286
286
  @@cache_store = cache
287
287
  end
@@ -290,18 +290,18 @@ module SimpleRecord
290
290
  return @@cache_store
291
291
  end
292
292
 
293
- # If you want a domain prefix for all your models, set it here.
293
+ # If you want a domain prefix for all your models, set it here.
294
294
  def self.set_domain_prefix(prefix)
295
295
  #puts 'set_domain_prefix=' + prefix
296
296
  self.domain_prefix = prefix
297
297
  end
298
298
 
299
- # Same as set_table_name
299
+ # Same as set_table_name
300
300
  def self.set_table_name(table_name)
301
301
  set_domain_name table_name
302
302
  end
303
303
 
304
- # Sets the domain name for this class
304
+ # Sets the domain name for this class
305
305
  def self.set_domain_name(table_name)
306
306
  super
307
307
  end
@@ -405,12 +405,12 @@ module SimpleRecord
405
405
  set(SimpleRecord.options[:updated_col] || :updated, Time.now)
406
406
  end
407
407
 
408
- # an aliased method since many people use created_at/updated_at naming convention
408
+ # an aliased method since many people use created_at/updated_at naming convention
409
409
  def created_at
410
410
  self.created
411
411
  end
412
412
 
413
- # an aliased method since many people use created_at/updated_at naming convention
413
+ # an aliased method since many people use created_at/updated_at naming convention
414
414
  def updated_at
415
415
  self.updated
416
416
  end
@@ -438,17 +438,17 @@ module SimpleRecord
438
438
 
439
439
  @create_domain_called = false
440
440
 
441
- # Options:
442
- # - :except => Array of attributes to NOT save
443
- # - :dirty => true - Will only store attributes that were modified. To make it save regardless and have it update the :updated value, include this and set it to false.
444
- # - :domain => Explicitly define domain to use.
445
- #
441
+ # Options:
442
+ # - :except => Array of attributes to NOT save
443
+ # - :dirty => true - Will only store attributes that were modified. To make it save regardless and have it update the :updated value, include this and set it to false.
444
+ # - :domain => Explicitly define domain to use.
445
+ #
446
446
 
447
447
  def save(options={})
448
448
  puts 'SAVING: ' + self.inspect if SimpleRecord.logging?
449
- # todo: Clean out undefined values in @attributes (in case someone set the attributes hash with values that they hadn't defined)
449
+ # todo: Clean out undefined values in @attributes (in case someone set the attributes hash with values that they hadn't defined)
450
450
  clear_errors
451
- # todo: decide whether this should go before pre_save or after pre_save? pre_save dirties "updated" and perhaps other items due to callbacks
451
+ # todo: decide whether this should go before pre_save or after pre_save? pre_save dirties "updated" and perhaps other items due to callbacks
452
452
  if options[:dirty]
453
453
  # puts '@dirtyA=' + @dirty.inspect
454
454
  return true if @dirty.size == 0 # Nothing to save so skip it
@@ -470,7 +470,7 @@ module SimpleRecord
470
470
  is_create = new_record? # self[:id].nil?
471
471
 
472
472
  dirty = @dirty
473
- # puts 'dirty before=' + @dirty.inspect
473
+ # puts 'dirty before=' + @dirty.inspect
474
474
  if options[:dirty]
475
475
  # puts '@dirty=' + @dirty.inspect
476
476
  return true if @dirty.size == 0 # This should probably never happen because after pre_save, created/updated dates are changed
@@ -500,7 +500,7 @@ module SimpleRecord
500
500
  # end
501
501
 
502
502
  def create_or_update(options) #:nodoc:
503
- # puts 'create_or_update'
503
+ # puts 'create_or_update'
504
504
  ret = true
505
505
  _run_save_callbacks do
506
506
  result = new_record? ? create(options) : update(options)
@@ -538,7 +538,7 @@ module SimpleRecord
538
538
  save(options) || raise(RecordNotSaved.new(self))
539
539
  end
540
540
 
541
- # this is a bit wonky, save! should call this, not sure why it's here.
541
+ # this is a bit wonky, save! should call this, not sure why it's here.
542
542
  def save_with_validation!(options={})
543
543
  save!
544
544
  end
@@ -642,21 +642,21 @@ module SimpleRecord
642
642
 
643
643
  def is_dirty?(name)
644
644
  # todo: should change all the dirty stuff to symbols?
645
- # puts '@dirty=' + @dirty.inspect
646
- # puts 'name=' +name.to_s
645
+ # puts '@dirty=' + @dirty.inspect
646
+ # puts 'name=' +name.to_s
647
647
  @dirty.include? name.to_s
648
648
  end
649
649
 
650
650
  def s3
651
651
 
652
652
  return SimpleRecord.s3 if SimpleRecord.s3
653
- # todo: should optimize this somehow, like use the same connection_mode as used in SR
654
- # or keep open while looping in ResultsArray.
653
+ # todo: should optimize this somehow, like use the same connection_mode as used in SR
654
+ # or keep open while looping in ResultsArray.
655
655
  Aws::S3.new(SimpleRecord.aws_access_key, SimpleRecord.aws_secret_key)
656
656
  end
657
657
 
658
- # options:
659
- # :s3_bucket => :old/:new/"#{any_bucket_name}". :new if want to use new bucket. Defaults to :old for backwards compatability.
658
+ # options:
659
+ # :s3_bucket => :old/:new/"#{any_bucket_name}". :new if want to use new bucket. Defaults to :old for backwards compatability.
660
660
  def s3_bucket(create=false, options={})
661
661
  s3.bucket(s3_bucket_name(options[:s3_bucket]), create)
662
662
  end
@@ -725,7 +725,7 @@ module SimpleRecord
725
725
  return false unless ok
726
726
  end
727
727
 
728
- # Now for callbacks
728
+ # Now for callbacks
729
729
  unless @@active_model
730
730
  ok = respond_to?(:before_save) ? before_save : true
731
731
  if ok
@@ -766,8 +766,8 @@ module SimpleRecord
766
766
  return to_delete
767
767
  end
768
768
 
769
- # Run pre_save on each object, then runs batch_put_attributes
770
- # Returns
769
+ # Run pre_save on each object, then runs batch_put_attributes
770
+ # Returns
771
771
  def self.batch_save(objects, options={})
772
772
  options[:create_domain] = true if options[:create_domain].nil?
773
773
  results = []
@@ -793,7 +793,7 @@ module SimpleRecord
793
793
  results
794
794
  end
795
795
 
796
- # Pass in an array of objects
796
+ # Pass in an array of objects
797
797
  def self.batch_delete(objects, options={})
798
798
  if objects
799
799
  # 25 item limit, we should maybe handle this limit in here.
@@ -801,15 +801,15 @@ module SimpleRecord
801
801
  end
802
802
  end
803
803
 
804
- #
805
- # Usage: ClassName.delete id
806
- #
804
+ #
805
+ # Usage: ClassName.delete id
806
+ #
807
807
  def self.delete(id)
808
808
  connection.delete_attributes(domain, id)
809
809
  @deleted = true
810
810
  end
811
811
 
812
- # Pass in the same OPTIONS you'd pass into a find(:all, OPTIONS)
812
+ # Pass in the same OPTIONS you'd pass into a find(:all, OPTIONS)
813
813
  def self.delete_all(options={})
814
814
  # could make this quicker by just getting item_names and deleting attributes rather than creating objects
815
815
  obs = self.find(:all, options)
@@ -821,7 +821,7 @@ module SimpleRecord
821
821
  return i
822
822
  end
823
823
 
824
- # Pass in the same OPTIONS you'd pass into a find(:all, OPTIONS)
824
+ # Pass in the same OPTIONS you'd pass into a find(:all, OPTIONS)
825
825
  def self.destroy_all(options={})
826
826
  obs = self.find(:all, options)
827
827
  i = 0
@@ -838,7 +838,7 @@ module SimpleRecord
838
838
  end
839
839
  super(options)
840
840
 
841
- # delete lobs now too
841
+ # delete lobs now too
842
842
  delete_lobs
843
843
  end
844
844
 
@@ -885,7 +885,7 @@ module SimpleRecord
885
885
 
886
886
  def self.quote_regexp(a, re)
887
887
  a =~ re
888
- #was there a match?
888
+ #was there a match?
889
889
  if $&
890
890
  before=$`
891
891
  middle=$&
@@ -905,19 +905,19 @@ module SimpleRecord
905
905
 
906
906
  @@regex_no_id = /.*Couldn't find.*with ID.*/
907
907
 
908
- #
909
- # Usage:
910
- # Find by ID:
911
- # MyModel.find(ID)
912
- #
913
- # Query example:
914
- # MyModel.find(:all, :conditions=>["name = ?", name], :order=>"created desc", :limit=>10)
915
- #
916
- # Extra options:
917
- # :per_token => the number of results to return per next_token, max is 2500.
918
- # :consistent_read => true/false -- as per http://developer.amazonwebservices.com/connect/entry.jspa?externalID=3572
919
- # :retries => maximum number of times to retry this query on an error response.
920
- # :shard => shard name or array of shard names to use on this query.
908
+ #
909
+ # Usage:
910
+ # Find by ID:
911
+ # MyModel.find(ID)
912
+ #
913
+ # Query example:
914
+ # MyModel.find(:all, :conditions=>["name = ?", name], :order=>"created desc", :limit=>10)
915
+ #
916
+ # Extra options:
917
+ # :per_token => the number of results to return per next_token, max is 2500.
918
+ # :consistent_read => true/false -- as per http://developer.amazonwebservices.com/connect/entry.jspa?externalID=3572
919
+ # :retries => maximum number of times to retry this query on an error response.
920
+ # :shard => shard name or array of shard names to use on this query.
921
921
  def self.find(*params)
922
922
  #puts 'params=' + params.inspect
923
923
 
@@ -941,12 +941,12 @@ module SimpleRecord
941
941
  return find_sharded(*params)
942
942
  end
943
943
 
944
- # Pad and Offset number attributes
944
+ # Pad and Offset number attributes
945
945
  params_dup = params.dup
946
946
  if params.size > 1
947
947
  options = params[1]
948
- #puts 'options=' + options.inspect
949
- #puts 'after collect=' + options.inspect
948
+ #puts 'options=' + options.inspect
949
+ #puts 'after collect=' + options.inspect
950
950
  convert_condition_params(options)
951
951
  per_token = options[:per_token]
952
952
  consistent_read = options[:consistent_read]
@@ -957,20 +957,20 @@ module SimpleRecord
957
957
  params_dup[1] = op_dup
958
958
  end
959
959
  end
960
- # puts 'params2=' + params.inspect
960
+ # puts 'params2=' + params.inspect
961
961
 
962
962
  ret = q_type == :all ? [] : nil
963
963
  begin
964
964
  results=find_with_metadata(*params_dup)
965
965
  #puts "RESULT=" + results.inspect
966
966
  write_usage(:select, domain, q_type, options, results)
967
- #puts 'params3=' + params.inspect
967
+ #puts 'params3=' + params.inspect
968
968
  SimpleRecord.stats.selects += 1
969
969
  if q_type == :count
970
970
  ret = results[:count]
971
971
  elsif q_type == :first
972
972
  ret = results[:items].first
973
- # todo: we should store request_id and box_usage with the object maybe?
973
+ # todo: we should store request_id and box_usage with the object maybe?
974
974
  cache_results(ret)
975
975
  elsif results[:single_only]
976
976
  ret = results[:single]
@@ -987,14 +987,14 @@ module SimpleRecord
987
987
  #puts "RESCUED: " + ex.message
988
988
  if (ex.message().index("NoSuchDomain") != nil)
989
989
  # this is ok
990
- # elsif (ex.message() =~ @@regex_no_id) This is RecordNotFound now
991
- # ret = nil
990
+ # elsif (ex.message() =~ @@regex_no_id) This is RecordNotFound now
991
+ # ret = nil
992
992
  else
993
993
  #puts 're-raising'
994
994
  raise ex
995
995
  end
996
996
  end
997
- # puts 'single2=' + ret.inspect
997
+ # puts 'single2=' + ret.inspect
998
998
  return ret
999
999
  end
1000
1000
 
@@ -1014,8 +1014,8 @@ module SimpleRecord
1014
1014
  find(:count, *args)
1015
1015
  end
1016
1016
 
1017
- # This gets less and less efficient the higher the page since SimpleDB has no way
1018
- # to start at a specific row. So it will iterate from the first record and pull out the specific pages.
1017
+ # This gets less and less efficient the higher the page since SimpleDB has no way
1018
+ # to start at a specific row. So it will iterate from the first record and pull out the specific pages.
1019
1019
  def self.paginate(options={})
1020
1020
  # options = args.pop
1021
1021
  # puts 'paginate options=' + options.inspect if SimpleRecord.logging?
@@ -1053,14 +1053,14 @@ module SimpleRecord
1053
1053
  class_name = item.class.name
1054
1054
  id = item.id
1055
1055
  cache_key = self.cache_key(class_name, id)
1056
- #puts 'caching result at ' + cache_key + ': ' + results.inspect
1056
+ #puts 'caching result at ' + cache_key + ': ' + results.inspect
1057
1057
  cache_store.write(cache_key, item, :expires_in =>30)
1058
1058
  end
1059
1059
  else
1060
1060
  class_name = results.class.name
1061
1061
  id = results.id
1062
1062
  cache_key = self.cache_key(class_name, id)
1063
- #puts 'caching result at ' + cache_key + ': ' + results.inspect
1063
+ #puts 'caching result at ' + cache_key + ': ' + results.inspect
1064
1064
  cache_store.write(cache_key, results, :expires_in =>30)
1065
1065
  end
1066
1066
  end
@@ -1094,7 +1094,7 @@ module SimpleRecord
1094
1094
 
1095
1095
  def changes
1096
1096
  ret = {}
1097
- #puts 'in CHANGES=' + @dirty.inspect
1097
+ #puts 'in CHANGES=' + @dirty.inspect
1098
1098
  @dirty.each_pair { |key, value| ret[key] = [value, get_attribute(key)] }
1099
1099
  return ret
1100
1100
  end
@@ -1119,7 +1119,7 @@ module SimpleRecord
1119
1119
  @referencevalue=referencevalue
1120
1120
  end
1121
1121
 
1122
- # Performance optimization if you know the array should be empty
1122
+ # Performance optimization if you know the array should be empty
1123
1123
 
1124
1124
  def init_empty
1125
1125
  @records = []
@@ -1177,7 +1177,7 @@ module SimpleRecord
1177
1177
 
1178
1178
  def find(*params)
1179
1179
  query=[:first, {}]
1180
- #{:conditions=>"id=>1"}
1180
+ #{:conditions=>"id=>1"}
1181
1181
  if params[0]
1182
1182
  if params[0]==:all
1183
1183
  query[0]=:all
@@ -1203,7 +1203,7 @@ module SimpleRecord
1203
1203
 
1204
1204
  end
1205
1205
 
1206
- # This is simply a place holder so we don't keep doing gets to s3 or simpledb if already checked.
1206
+ # This is simply a place holder so we don't keep doing gets to s3 or simpledb if already checked.
1207
1207
  class RemoteNil
1208
1208
 
1209
1209
  end
@@ -58,14 +58,14 @@ module SimpleRecord
58
58
  attr = Attribute.new(type, arg_options)
59
59
  defined_attributes[arg] = attr if defined_attributes[arg].nil?
60
60
 
61
- # define reader method
61
+ # define reader method
62
62
  arg_s = arg.to_s # to get rid of all the to_s calls
63
63
  send(:define_method, arg) do
64
64
  ret = get_attribute(arg)
65
65
  return ret
66
66
  end
67
67
 
68
- # define writer method
68
+ # define writer method
69
69
  send(:define_method, arg_s+"=") do |value|
70
70
  set(arg, value)
71
71
  end
@@ -81,13 +81,13 @@ module SimpleRecord
81
81
  @dirty.has_key?(sdb_att_name(arg_s))
82
82
  end
83
83
 
84
- # define change method
84
+ # define change method
85
85
  send(:define_method, arg_s + "_change") do
86
86
  old_val = @dirty[sdb_att_name(arg_s)]
87
87
  [old_val, get_attribute(arg_s)]
88
88
  end
89
89
 
90
- # define was method
90
+ # define was method
91
91
  send(:define_method, arg_s + "_was") do
92
92
  old_val = @dirty[sdb_att_name(arg_s)]
93
93
  old_val
@@ -149,21 +149,26 @@ module SimpleRecord
149
149
 
150
150
  end
151
151
 
152
+ def virtuals
153
+ @virtuals ||= []
154
+ @virtuals
155
+ end
156
+
152
157
  def has_virtuals(*args)
153
- @@virtuals = args
158
+ virtuals.concat(args)
154
159
  args.each do |arg|
155
160
  #we just create the accessor functions here, the actual instance variable is created during initialize
156
161
  attr_accessor(arg)
157
162
  end
158
163
  end
159
164
 
160
- # One belongs_to association per call. Call multiple times if there are more than one.
161
- #
162
- # This method will also create an {association)_id method that will return the ID of the foreign object
163
- # without actually materializing it.
164
- #
165
- # options:
166
- # :class_name=>"User" - to change the default class to use
165
+ # One belongs_to association per call. Call multiple times if there are more than one.
166
+ #
167
+ # This method will also create an {association)_id method that will return the ID of the foreign object
168
+ # without actually materializing it.
169
+ #
170
+ # options:
171
+ # :class_name=>"User" - to change the default class to use
167
172
  def belongs_to(association_id, options = {})
168
173
  arg = association_id
169
174
  arg_s = arg.to_s
@@ -171,29 +176,29 @@ module SimpleRecord
171
176
  attribute = Attribute.new(:belongs_to, options)
172
177
  defined_attributes[arg] = attribute
173
178
 
174
- # todo: should also handle foreign_key http://74.125.95.132/search?q=cache:KqLkxuXiBBQJ:wiki.rubyonrails.org/rails/show/belongs_to+rails+belongs_to&hl=en&ct=clnk&cd=1&gl=us
175
- # puts "arg_id=#{arg}_id"
176
- # puts "is defined? " + eval("(defined? #{arg}_id)").to_s
177
- # puts 'atts=' + @attributes.inspect
179
+ # todo: should also handle foreign_key http://74.125.95.132/search?q=cache:KqLkxuXiBBQJ:wiki.rubyonrails.org/rails/show/belongs_to+rails+belongs_to&hl=en&ct=clnk&cd=1&gl=us
180
+ # puts "arg_id=#{arg}_id"
181
+ # puts "is defined? " + eval("(defined? #{arg}_id)").to_s
182
+ # puts 'atts=' + @attributes.inspect
178
183
 
179
- # Define reader method
184
+ # Define reader method
180
185
  send(:define_method, arg) do
181
186
  return get_attribute(arg)
182
187
  end
183
188
 
184
189
 
185
- # Define writer method
190
+ # Define writer method
186
191
  send(:define_method, arg.to_s + "=") do |value|
187
192
  set(arg, value)
188
193
  end
189
194
 
190
195
 
191
- # Define ID reader method for reading the associated objects id without getting the entire object
196
+ # Define ID reader method for reading the associated objects id without getting the entire object
192
197
  send(:define_method, arg_id) do
193
198
  get_attribute_sdb(arg_s)
194
199
  end
195
200
 
196
- # Define writer method for setting the _id directly without the associated object
201
+ # Define writer method for setting the _id directly without the associated object
197
202
  send(:define_method, arg_id + "=") do |value|
198
203
  # rb_att_name = arg_s # n2 = name.to_s[0, name.length-3]
199
204
  set(arg_id, value)
@@ -237,14 +242,16 @@ module SimpleRecord
237
242
 
238
243
  end
239
244
 
240
- @@virtuals=[]
241
-
242
- def self.handle_virtuals(attrs)
243
- @@virtuals.each do |virtual|
244
- #we first copy the information for the virtual to an instance variable of the same name
245
- eval("@#{virtual}=attrs['#{virtual}']")
246
- #and then remove the parameter before it is passed to initialize, so that it is NOT sent to SimpleDB
247
- eval("attrs.delete('#{virtual}')")
245
+ def handle_virtuals(attrs)
246
+ puts 'handle_virtuals'
247
+ self.class.virtuals.each do |virtual|
248
+ puts 'virtual=' + virtual.inspect
249
+ #we first copy the information for the virtual to an instance variable of the same name
250
+ send("#{virtual}=", attrs[virtual])
251
+ #eval("@#{virtual}=attrs['#{virtual}']")
252
+ #and then remove the parameter before it is passed to initialize, so that it is NOT sent to SimpleDB
253
+ attrs.delete(virtual)
254
+ #eval("attrs.delete('#{virtual}')")
248
255
  end
249
256
  end
250
257
 
@@ -289,17 +296,17 @@ module SimpleRecord
289
296
  attname = name.to_s
290
297
  attvalue = att_meta.init_value(value)
291
298
  # attvalue = value
292
- #puts 'converted ' + value.inspect + ' to ' + attvalue.inspect
299
+ #puts 'converted ' + value.inspect + ' to ' + attvalue.inspect
293
300
  end
294
301
  end
295
302
  attvalue = strip_array(attvalue)
296
303
  make_dirty(name, attvalue) if dirtify
297
- # puts "ARG=#{attname.to_s} setting to #{attvalue}"
304
+ # puts "ARG=#{attname.to_s} setting to #{attvalue}"
298
305
  sdb_val = ruby_to_sdb(name, attvalue)
299
- # puts "sdb_val=" + sdb_val.to_s
306
+ # puts "sdb_val=" + sdb_val.to_s
300
307
  @attributes[attname] = sdb_val
301
- # attvalue = wrap_if_required(name, attvalue, sdb_val)
302
- # puts 'attvalue2=' + attvalue.to_s
308
+ # attvalue = wrap_if_required(name, attvalue, sdb_val)
309
+ # puts 'attvalue2=' + attvalue.to_s
303
310
 
304
311
  if store_rb_val
305
312
  @attributes_rb[name.to_s] = value
@@ -321,11 +328,11 @@ module SimpleRecord
321
328
  return ret
322
329
  end
323
330
 
324
- # Since SimpleDB supports multiple attributes per value, the values are an array.
325
- # This method will return the value unwrapped if it's the only, otherwise it will return the array.
331
+ # Since SimpleDB supports multiple attributes per value, the values are an array.
332
+ # This method will return the value unwrapped if it's the only, otherwise it will return the array.
326
333
  def get_attribute(name)
327
334
  # puts "get_attribute #{name}"
328
- # Check if this arg is already converted
335
+ # Check if this arg is already converted
329
336
  name_s = name.to_s
330
337
  name = name.to_sym
331
338
  att_meta = get_att_meta(name)
@@ -340,7 +347,7 @@ module SimpleRecord
340
347
  return ret
341
348
  end
342
349
  end
343
- # get it from s3
350
+ # get it from s3
344
351
  unless new_record?
345
352
  if self.class.get_sr_config[:single_clob]
346
353
  begin
@@ -362,7 +369,7 @@ module SimpleRecord
362
369
  else
363
370
  begin
364
371
  ret = s3_bucket.get(s3_lob_id(name))
365
- # puts 'got from s3 ' + ret.inspect
372
+ # puts 'got from s3 ' + ret.inspect
366
373
  SimpleRecord.stats.s3_gets += 1
367
374
  rescue Aws::AwsError => ex
368
375
  if ex.include?(/NoSuchKey/) || ex.include?(/NoSuchBucket/)
@@ -386,9 +393,9 @@ module SimpleRecord
386
393
  return ret unless ret.nil?
387
394
  return nil if ret.is_a? RemoteNil
388
395
  ret = get_attribute_sdb(name)
389
- # p ret
396
+ # p ret
390
397
  ret = sdb_to_ruby(name, ret)
391
- # p ret
398
+ # p ret
392
399
  @attributes_rb[name_s] = ret
393
400
  return ret
394
401
  end
@@ -404,7 +411,7 @@ module SimpleRecord
404
411
  end
405
412
 
406
413
 
407
- # Holds information about an attribute
414
+ # Holds information about an attribute
408
415
  class Attribute
409
416
  attr_accessor :type, :options
410
417
 
@@ -17,6 +17,20 @@ module SimpleRecord
17
17
  # end
18
18
  end
19
19
 
20
+ module ClassMethods
21
+
22
+ def uniques
23
+ @uniques ||= {}
24
+ @uniques
25
+ end
26
+
27
+ # only supporting single attr name right now
28
+ def validates_uniqueness_of(attr)
29
+ uniques[attr] = true
30
+ end
31
+
32
+ end
33
+
20
34
  def valid?
21
35
  # puts 'in rails2 valid?'
22
36
  errors.clear
@@ -26,9 +40,9 @@ module SimpleRecord
26
40
  am_valid?
27
41
  end
28
42
 
29
- # run_callbacks(:validate)
43
+ # run_callbacks(:validate)
30
44
  validate
31
-
45
+ validate_uniques
32
46
 
33
47
  if new_record?
34
48
  # run_callbacks(:validate_on_create)
@@ -51,6 +65,21 @@ module SimpleRecord
51
65
  @attributes[key.to_s]
52
66
  end
53
67
 
68
+ def validate_uniques
69
+ puts 'uniques=' + self.class.uniques.inspect
70
+ self.class.uniques.each_pair do |k, v|
71
+ val = self.send(k)
72
+ puts 'val=' + val.inspect
73
+ if val
74
+ ret = self.class.find(:first, :conditions=>["#{k}=?", val])
75
+ puts 'ret=' + ret.inspect
76
+ if ret
77
+ errors.add(k, "must be unique.")
78
+ end
79
+ end
80
+ end
81
+ end
82
+
54
83
  def validate
55
84
  true
56
85
  end
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: simple_record
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 2.1.10
5
+ version: 2.1.11
6
6
  platform: ruby
7
7
  authors:
8
8
  - Travis Reeder
@@ -12,7 +12,7 @@ autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
14
 
15
- date: 2011-07-04 00:00:00 Z
15
+ date: 2011-07-06 00:00:00 Z
16
16
  dependencies:
17
17
  - !ruby/object:Gem::Dependency
18
18
  name: aws
@@ -75,9 +75,6 @@ required_ruby_version: !ruby/object:Gem::Requirement
75
75
  requirements:
76
76
  - - ">="
77
77
  - !ruby/object:Gem::Version
78
- hash: 2579069880692294424
79
- segments:
80
- - 0
81
78
  version: "0"
82
79
  required_rubygems_version: !ruby/object:Gem::Requirement
83
80
  none: false