Module | Sequel::Model::InstanceMethods
In: | lib/sequel/model/base.rb

Sequel::Model instance methods that implement basic model functionality.

- All of the methods in `HOOKS` and `AROUND_HOOKS` create instance methods that are called by Sequel when the appropriate action occurs. For example, when destroying a model object, Sequel will call `around_destroy`, which will call `before_destroy`, do the destroy, and then call `after_destroy`.
- The following instance_methods all call the class method of the same name: columns, db, primary_key, db_schema.
- All of the methods in `BOOLEAN_SETTINGS` create attr_writers allowing you to set values for the attribute. It also creates instance getters returning the value of the setting. If the value has not yet been set, it gets the default value from the class by calling the class method of the same name.

### Methods

== === [] []= autoincrementing_primary_key changed_columns delete destroy each eql? errors exists? extend freeze hash id inspect keys lock! marshallable! modified! modified? new new? pk pk_hash refresh reload save save_changes set set_all set_except set_fields set_only set_server set_values singleton_method_added this update update_all update_except update_fields update_only valid? validate

### External Aliases

values | -> | to_hash
class | -> | model
| class is defined in Object, but it is also a keyword, and since a lot of instance methods call class methods, this alias makes it so you can use model instead of self.class.
      Artist.new.model # => Artist

### Attributes

values | [R] | The hash of attribute values. Keys are symbols with the names of the underlying database columns.
      Artist.new(:name=>'Bob').values # => {:name=>'Bob'}
      Artist[1].values # => {:id=>1, :name=>'Jim', ...}

### Public Class methods

new(values = {}, from_db = false) {|self if block_given?| ...}

Creates new instance and passes the given values to set. If a block is given, yield the instance to the block unless from_db is true. This method runs the after_initialize hook after it has optionally yielded itself to the block.

Arguments:

values : | should be a hash to pass to set.
from_db : | only for backwards compatibility, forget it exists.

      Artist.new(:name=>'Bob')

      Artist.new do |a|
        a.name = 'Bob'
      end

[Source]

         # File lib/sequel/model/base.rb, line 892
    892:       def initialize(values = {}, from_db = false)
    893:         if from_db
    894:           set_values(values)
    895:         else
    896:           @values = {}
    897:           @new = true
    898:           @modified = true
    899:           initialize_set(values)
    900:           changed_columns.clear
    901:           yield self if block_given?
    902:         end
    903:         after_initialize
    904:       end

### Public Instance methods

==(obj)

Alias of eql?

[Source]

         # File lib/sequel/model/base.rb, line 934
    934:       def ==(obj)
    935:         eql?(obj)
    936:       end

===(obj)

If pk is not nil, true only if the objects have the same class and pk. If pk is nil, false.

      Artist[1] === Artist[1] # true
      Artist.new === Artist.new # false
      Artist[1].set(:name=>'Bob') == Artist[1] # => true

[Source]

         # File lib/sequel/model/base.rb, line 944
    944:       def ===(obj)
    945:         pk.nil? ? false : (obj.class == model) && (obj.pk == pk)
    946:       end

[](column)

Returns value of the column‘s attribute.

      Artist[1][:id] #=> 1

[Source]

         # File lib/sequel/model/base.rb, line 909
    909:       def [](column)
    910:         @values[column]
    911:       end

[]=(column, value)

Sets the value for the given column. If typecasting is enabled for this object, typecast the value based on the column‘s type. If this is a new record or the typecasted value isn‘t the same as the current value for the column, mark the column as changed.

      a = Artist.new
      a[:name] = 'Bob'
      a.values #=> {:name=>'Bob'}

[Source]

         # File lib/sequel/model/base.rb, line 921
    921:       def []=(column, value)
    922:         # If it is new, it doesn't have a value yet, so we should
    923:         # definitely set the new value.
    924:         # If the column isn't in @values, we can't assume it is
    925:         # NULL in the database, so assume it has changed.
    926:         v = typecast_value(column, value)
    927:         vals = @values
    928:         if new? || !vals.include?(column) || v != (c = vals[column]) || v.class != c.class
    929:           change_column_value(column, v)
    930:         end
    931:       end

autoincrementing_primary_key()

The autoincrementing primary key for this model object. Should be overridden if you have a composite primary key with one part of it being autoincrementing.

[Source]

         # File lib/sequel/model/base.rb, line 959
    959:       def autoincrementing_primary_key
    960:         primary_key
    961:       end

changed_columns()

The columns that have been updated. This isn‘t completely accurate, as it could contain columns whose values have not changed.

      a = Artist[1]
      a.changed_columns # => []
      a.name = 'Bob'
      a.changed_columns # => [:name]

[Source]

         # File lib/sequel/model/base.rb, line 970
    970:       def changed_columns
    971:         @changed_columns ||= []
    972:       end

delete()

Deletes and returns `self`. Does not run destroy hooks. Look into using `destroy` instead.

      Artist[1].delete # DELETE FROM artists WHERE (id = 1)
      # => #<Artist {:id=>1, ...}>

[Source]

         # File lib/sequel/model/base.rb, line 979
    979:       def delete
    980:         raise Sequel::Error, "can't delete frozen object" if frozen?
    981:         _delete
    982:         self
    983:       end

destroy(opts = {})

Like delete but runs hooks before and after delete. If before_destroy returns false, returns false without deleting the object the the database. Otherwise, deletes the item from the database and returns self. Uses a transaction if use_transactions is true or if the :transaction option is given and true.

      Artist[1].destroy # BEGIN; DELETE FROM artists WHERE (id = 1); COMMIT;
      # => #<Artist {:id=>1, ...}>

[Source]

         # File lib/sequel/model/base.rb, line 994
    994:       def destroy(opts = {})
    995:         raise Sequel::Error, "can't destroy frozen object" if frozen?
    996:         checked_save_failure(opts){checked_transaction(opts){_destroy(opts)}}
    997:       end

each(&block)

Iterates through all of the current values using each.

     Album[1].each{|k, v| puts "#{k} => #{v}"}
     # id => 1
     # name => 'Bob'

[Source]

          # File lib/sequel/model/base.rb, line 1004
    1004:       def each(&block)
    1005:         @values.each(&block)
    1006:       end

eql?(obj)

Compares model instances by values.

      Artist[1] == Artist[1] # => true
      Artist.new == Artist.new # => true
      Artist[1].set(:name=>'Bob') == Artist[1] # => false

[Source]

          # File lib/sequel/model/base.rb, line 1013
    1013:       def eql?(obj)
    1014:         (obj.class == model) && (obj.values == @values)
    1015:       end

errors()

Returns the validation errors associated with this object. See `Errors`.

[Source]

          # File lib/sequel/model/base.rb, line 1019
    1019:       def errors
    1020:         @errors ||= Errors.new
    1021:       end

exists?()

Returns true when current instance exists, false otherwise. Generally an object that isn‘t new will exist unless it has been deleted. Uses a database query to check for existence, unless the model object is new, in which case this is always false.

      Artist[1].exists? # SELECT 1 FROM artists WHERE (id = 1)
      # => true
      Artist.new.exists?
      # => false

[Source]

          # File lib/sequel/model/base.rb, line 1033
    1033:       def exists?
    1034:         new? ? false : !this.get(1).nil?
    1035:       end

extend(mod)

Ignore the model‘s setter method cache when this instances extends a module, as the module may contain setter methods.

[Source]

          # File lib/sequel/model/base.rb, line 1039
    1039:       def extend(mod)
    1040:         @singleton_setter_added = true
    1041:         super
    1042:       end

freeze()

Freeze the object in such a way that it is still usable but not modifiable. Once an object is frozen, you cannot modify it‘s values, changed_columns, errors, or dataset.

[Source]

          # File lib/sequel/model/base.rb, line 1047
    1047:       def freeze
    1048:         values.freeze
    1049:         changed_columns.freeze
    1050:         errors
    1051:         validate
    1052:         errors.freeze
    1053:         this.freeze unless new?
    1054:         super
    1055:       end

hash()

Value that should be unique for objects with the same class and pk (if pk is not nil), or the same class and values (if pk is nil).

      Artist[1].hash == Artist[1].hash # true
      Artist[1].set(:name=>'Bob').hash == Artist[1].hash # true
      Artist.new.hash == Artist.new.hash # true
      Artist.new(:name=>'Bob').hash == Artist.new.hash # false

[Source]

          # File lib/sequel/model/base.rb, line 1064
    1064:       def hash
    1065:         case primary_key
    1066:         when Array
    1067:           [model, !pk.all? ? @values.sort_by{|k,v| k.to_s} : pk].hash
    1068:         when Symbol
    1069:           [model, pk.nil? ? @values.sort_by{|k,v| k.to_s} : pk].hash
    1070:         else
    1071:           [model, @values.sort_by{|k,v| k.to_s}].hash
    1072:         end
    1073:       end

id()

Returns value for the :id attribute, even if the primary key is not id. To get the primary key value, use `pk`.

      Artist[1].id # => 1

[Source]

          # File lib/sequel/model/base.rb, line 1079
    1079:       def id
    1080:         @values[:id]
    1081:       end

inspect()

Returns a string representation of the model instance including the class name and values.

[Source]

          # File lib/sequel/model/base.rb, line 1085
    1085:       def inspect
    1086:         "#<#{model.name} @values=#{inspect_values}>"
    1087:       end

keys()

Returns the keys in `values`. May not include all column names.

      Artist.new.keys # => []
      Artist.new(:name=>'Bob').keys # => [:name]
      Artist[1].keys # => [:id, :name]

[Source]

          # File lib/sequel/model/base.rb, line 1094
    1094:       def keys
    1095:         @values.keys
    1096:       end

lock!()

Refresh this record using `for_update` unless this is a new record. Returns self. This can be used to make sure no other process is updating the record at the same time.

      a = Artist[1]
      Artist.db.transaction do
        a.lock!
        a.update(...)
      end

[Source]

          # File lib/sequel/model/base.rb, line 1107
    1107:       def lock!
    1108:         _refresh(this.for_update) unless new?
    1109:         self
    1110:       end

marshallable!()

Remove elements of the model object that make marshalling fail. Returns self.

      a = Artist[1]
      a.marshallable!
      Marshal.dump(a)

[Source]

          # File lib/sequel/model/base.rb, line 1117
    1117:       def marshallable!
    1118:         @this = nil
    1119:         self
    1120:       end

modified!()

Explicitly mark the object as modified, so `save_changes`/`update` will run callbacks even if no columns have changed.

      a = Artist[1]
      a.save_changes # No callbacks run, as no changes
      a.modified!
      a.save_changes # Callbacks run, even though no changes made

[Source]

          # File lib/sequel/model/base.rb, line 1129
    1129:       def modified!
    1130:         @modified = true
    1131:       end

modified?()

Whether this object has been modified since last saved, used by save_changes to determine whether changes should be saved. New values are always considered modified.

      a = Artist[1]
      a.modified? # => false
      a.set(:name=>'Jim')
      a.modified? # => true

[Source]

          # File lib/sequel/model/base.rb, line 1141
    1141:       def modified?
    1142:         @modified || !changed_columns.empty?
    1143:       end

new?()

Returns true if the current instance represents a new record.

      Artist.new.new? # => true
      Artist[1].new? # => false

[Source]

          # File lib/sequel/model/base.rb, line 1149
    1149:       def new?
    1150:         defined?(@new) ? @new : (@new = false)
    1151:       end

pk()

Returns the primary key value identifying the model instance. Raises an `Error` if this model does not have a primary key. If the model has a composite primary key, returns an array of values.

      Artist[1].pk # => 1
      Artist[[1, 2]].pk # => [1, 2]

[Source]

          # File lib/sequel/model/base.rb, line 1159
    1159:       def pk
    1160:         raise(Error, "No primary key is associated with this model") unless key = primary_key
    1161:         if key.is_a?(Array)
    1162:           vals = @values
    1163:           key.map{|k| vals[k]}
    1164:         else
    1165:           @values[key]
    1166:         end
    1167:       end

pk_hash()

Returns a hash identifying mapping the receivers primary key column(s) to their values.

      Artist[1].pk_hash # => {:id=>1}
      Artist[[1, 2]].pk_hash # => {:id1=>1, :id2=>2}

[Source]

          # File lib/sequel/model/base.rb, line 1173
    1173:       def pk_hash
    1174:         model.primary_key_hash(pk)
    1175:       end

refresh()

Reloads attributes from database and returns self. Also clears all changed_columns information. Raises an `Error` if the record no longer exists in the database.

      a = Artist[1]
      a.name = 'Jim'
      a.refresh
      a.name # => 'Bob'

[Source]

          # File lib/sequel/model/base.rb, line 1185
    1185:       def refresh
    1186:         raise Sequel::Error, "can't refresh frozen object" if frozen?
    1187:         _refresh(this)
    1188:         self
    1189:       end

reload()

Alias of refresh, but not aliased directly to make overriding in a plugin easier.

[Source]

          # File lib/sequel/model/base.rb, line 1192
    1192:       def reload
    1193:         refresh
    1194:       end

save(*columns)

Creates or updates the record, after making sure the record is valid and before hooks execute successfully. Fails if:

- the record is not valid, or
- before_save returns false, or
- the record is new and before_create returns false, or
- the record is not new and before_update returns false.

If `save` fails and either raise_on_save_failure or the :raise_on_failure option is true, it raises ValidationFailed or HookFailed. Otherwise it returns nil.

If it succeeds, it returns self.

You can provide an optional list of columns to update, in which case it only updates those columns, or a options hash.

Takes the following options:

:changed : | save all changed columns, instead of all columns or the columns given
:raise_on_failure : | set to true or false to override the current `raise_on_save_failure` setting
:server : | set the server/shard on the object before saving, and use that server/shard in any transaction.
:transaction : | set to true or false to override the current `use_transactions` setting
:validate : | set to false to skip validation

[Source]

          # File lib/sequel/model/base.rb, line 1223
    1223:       def save(*columns)
    1224:         raise Sequel::Error, "can't save frozen object" if frozen?
    1225:         opts = columns.last.is_a?(Hash) ? columns.pop : {}
    1226:         set_server(opts[:server]) if opts[:server]
    1227:         if opts[:validate] != false
    1228:           unless checked_save_failure(opts){_valid?(true, opts)}
    1229:             raise(ValidationFailed.new(errors)) if raise_on_failure?(opts)
    1230:             return
    1231:           end
    1232:         end
    1233:         checked_save_failure(opts){checked_transaction(opts){_save(columns, opts)}}
    1234:       end

save_changes(opts={})

Saves only changed columns if the object has been modified. If the object has not been modified, returns nil. If unable to save, returns false unless `raise_on_save_failure` is true.

      a = Artist[1]
      a.save_changes # => nil
      a.name = 'Jim'
      a.save_changes # UPDATE artists SET name = 'Bob' WHERE (id = 1)
      # => #<Artist {:id=>1, :name=>'Jim', ...}

[Source]

          # File lib/sequel/model/base.rb, line 1245
    1245:       def save_changes(opts={})
    1246:         save(opts.merge(:changed=>true)) || false if modified?
    1247:       end

set(hash)

Updates the instance with the supplied values with support for virtual attributes, raising an exception if a value is used that doesn‘t have a setter method (or ignoring it if `strict_param_setting = false`). Does not save the record.

      artist.set(:name=>'Jim')
      artist.name # => 'Jim'

[Source]

          # File lib/sequel/model/base.rb, line 1256
    1256:       def set(hash)
    1257:         set_restricted(hash, nil, nil)
    1258:       end

set_all(hash)

Set all values using the entries in the hash, ignoring any setting of allowed_columns or restricted columns in the model.

      Artist.set_restricted_columns(:name)
      artist.set_all(:name=>'Jim')
      artist.name # => 'Jim'

[Source]

          # File lib/sequel/model/base.rb, line 1266
    1266:       def set_all(hash)
    1267:         set_restricted(hash, false, false)
    1268:       end

set_except(hash, *except)

Set all values using the entries in the hash, except for the keys given in except. You should probably use `set_fields` or `set_only` instead of this method, as blacklist approaches to security are a bad idea.

      artist.set_except({:name=>'Jim'}, :hometown)
      artist.name # => 'Jim'

[Source]

          # File lib/sequel/model/base.rb, line 1276
    1276:       def set_except(hash, *except)
    1277:         set_restricted(hash, false, except.flatten)
    1278:       end

set_fields(hash, fields, opts=nil)

For each of the fields in the given array `fields`, call the setter method with the value of that `hash` entry for the field. Returns self.

You can provide an options hash, with the following options currently respected:

:missing : | Can be set to :skip to skip missing entries or :raise to raise an Error for missing entries. The default behavior is not to check for missing entries, in which case the default value is used. To be friendly with most web frameworks, the missing check will also check for the string version of the argument in the hash if given a symbol.

Examples:

      artist.set_fields({:name=>'Jim'}, [:name])
      artist.name # => 'Jim'

      artist.set_fields({:hometown=>'LA'}, [:name])
      artist.name # => nil
      artist.hometown # => 'Sac'

      artist.name # => 'Jim'
      artist.set_fields({}, [:name], :missing=>:skip)
      artist.name # => 'Jim'

      artist.name # => 'Jim'
      artist.set_fields({}, [:name], :missing=>:raise)
      # Sequel::Error raised

[Source]

          # File lib/sequel/model/base.rb, line 1306
    1306:       def set_fields(hash, fields, opts=nil)
    1307:         if opts
    1308:           case opts[:missing]
    1309:           when :skip
    1310:             fields.each do |f|
    1311:               if hash.has_key?(f)
    1312:                 send("#{f}=", hash[f])
    1313:               elsif f.is_a?(Symbol) && hash.has_key?(sf = f.to_s)
    1314:                 send("#{sf}=", hash[sf])
    1315:               end
    1316:             end
    1317:           when :raise
    1318:             fields.each do |f|
    1319:               if hash.has_key?(f)
    1320:                 send("#{f}=", hash[f])
    1321:               elsif f.is_a?(Symbol) && hash.has_key?(sf = f.to_s)
    1322:                 send("#{sf}=", hash[sf])
    1323:               else
    1324:                 raise(Sequel::Error, "missing field in hash: #{f.inspect} not in #{hash.inspect}")
    1325:               end
    1326:             end
    1327:           else
    1328:             fields.each{|f| send("#{f}=", hash[f])}
    1329:           end
    1330:         else
    1331:           fields.each{|f| send("#{f}=", hash[f])}
    1332:         end
    1333:         self
    1334:       end

set_only(hash, *only)

Set the values using the entries in the hash, only if the key is included in only. It may be a better idea to use `set_fields` instead of this method.

      artist.set_only({:name=>'Jim'}, :name)
      artist.name # => 'Jim'

      artist.set_only({:hometown=>'LA'}, :name) # Raise Error

[Source]

          # File lib/sequel/model/base.rb, line 1344
    1344:       def set_only(hash, *only)
    1345:         set_restricted(hash, only.flatten, false)
    1346:       end

set_server(s)

Set the shard that this object is tied to. Returns self.

[Source]

          # File lib/sequel/model/base.rb, line 1349
    1349:       def set_server(s)
    1350:         @server = s
    1351:         @this.opts[:server] = s if @this
    1352:         self
    1353:       end

set_values(hash)

Replace the current values with hash. Should definitely not be used with untrusted input, and should probably not be called directly by user code.

[Source]

          # File lib/sequel/model/base.rb, line 1358
    1358:       def set_values(hash)
    1359:         @values = hash
    1360:       end

singleton_method_added(meth)

Clear the setter_methods cache when a method is added

[Source]

          # File lib/sequel/model/base.rb, line 1363
    1363:       def singleton_method_added(meth)
    1364:         @singleton_setter_added = true if meth.to_s =~ SETTER_METHOD_REGEXP
    1365:         super
    1366:       end

this()

Returns (naked) dataset that should return only this instance.

      Artist[1].this
      # SELECT * FROM artists WHERE (id = 1) LIMIT 1

[Source]

          # File lib/sequel/model/base.rb, line 1372
    1372:       def this
    1373:         @this ||= use_server(model.instance_dataset.filter(pk_hash))
    1374:       end

update(hash)

Runs set with the passed hash and then runs save_changes.

      artist.update(:name=>'Jim') # UPDATE artists SET name = 'Jim' WHERE (id = 1)

[Source]

          # File lib/sequel/model/base.rb, line 1379
    1379:       def update(hash)
    1380:         update_restricted(hash, nil, nil)
    1381:       end

update_all(hash)

Update all values using the entries in the hash, ignoring any setting of `allowed_columns` or `restricted_columns` in the model.

      Artist.set_restricted_columns(:name)
      artist.update_all(:name=>'Jim') # UPDATE artists SET name = 'Jim' WHERE (id = 1)

[Source]

          # File lib/sequel/model/base.rb, line 1388
    1388:       def update_all(hash)
    1389:         update_restricted(hash, false, false)
    1390:       end

update_except(hash, *except)

Update all values using the entries in the hash, except for the keys given in except. You should probably use `update_fields` or `update_only` instead of this method, as blacklist approaches to security are a bad idea.

      artist.update_except({:name=>'Jim'}, :hometown) # UPDATE artists SET name = 'Jim' WHERE (id = 1)

[Source]

          # File lib/sequel/model/base.rb, line 1397
    1397:       def update_except(hash, *except)
    1398:         update_restricted(hash, false, except.flatten)
    1399:       end

update_fields(hash, fields, opts=nil)

Update the instances values by calling `set_fields` with the arguments, then saves any changes to the record. Returns self.

      artist.update_fields({:name=>'Jim'}, [:name])
      # UPDATE artists SET name = 'Jim' WHERE (id = 1)

      artist.update_fields({:hometown=>'LA'}, [:name])
      # UPDATE artists SET name = NULL WHERE (id = 1)

[Source]

          # File lib/sequel/model/base.rb, line 1409
    1409:       def update_fields(hash, fields, opts=nil)
    1410:         set_fields(hash, fields, opts)
    1411:         save_changes
    1412:       end

update_only(hash, *only)

Update the values using the entries in the hash, only if the key is included in only. It may be a better idea to use `update_fields` instead of this method.

      artist.update_only({:name=>'Jim'}, :name)
      # UPDATE artists SET name = 'Jim' WHERE (id = 1)

      artist.update_only({:hometown=>'LA'}, :name) # Raise Error

[Source]

          # File lib/sequel/model/base.rb, line 1422
    1422:       def update_only(hash, *only)
    1423:         update_restricted(hash, only.flatten, false)
    1424:       end

valid?(opts = {})

Validates the object and returns true if no errors are reported.

      artist(:name=>'Valid').valid? # => true
      artist(:name=>'Invalid').valid? # => false
      artist.errors.full_messages # => ['name cannot be Invalid']

[Source]

          # File lib/sequel/model/base.rb, line 1440
    1440:       def valid?(opts = {})
    1441:         _valid?(false, opts)
    1442:       end

validate()

Validates the object. If the object is invalid, errors should be added to the errors attribute. By default, does nothing, as all models are valid by default. See the "Model Validations" guide. for details about validation. Should not be called directly by user code, call `valid?` instead to check if an object is valid.

[Source]

          # File lib/sequel/model/base.rb, line 1432
    1432:       def validate
    1433:       end

[Validate]