Hi, I have a model called Stock with a value called “strength.” I
wrote a simple method in the Stock.rb model file to update the value
of “strength” for each record in the stocks table. I created a
controller called fix_controller.rb. I don’t have access to the live
system, so the idea is that an admin will go to http://url/fix and a
script will run to check and potentially update the “strength” value
for every record in the stocks table.
fix_controller.rb
^^^^^^^^^^^^^^^
class FixController < ApplicationController
def index
stocks = Stock.find(:all)
stocks.each do |s|
if s.strength.nil? || s.strength == ''
puts 'nothing to update'
else
s.update_units
end
end
NoMethodError: private method `gsub’ called for nil:NilClass
I’m sure this is a simple error and/or I’m not going about this the
correct way. I really only need to run this code once… Any idea why
I’m getting that error? I’m checking for nil…
it looks like you are trying to strip a leading space from each
“strength” value if its not nil.
something like
stocks = Stock.find(:all, :conditions => ‘(strength IS NOT NULL) AND
(strength != “”)’)
would give you all the stocks values with non-blank values. So you can
skip a lot of your testing above.
You could then do something like
stocks.each do |stock|
stock.strength = stock.strength.to_s.gsub(/^\s+/,’’)
stock.save
end
the above is using a regular expression to match the leading spaces.
the to_s shouldn’t be necessary, because you should only be dealing
with non-nil strength values at this point, but it’s defensive coding.
rails has a string extension .blank? which returns true for empty or
nil or spaces values, e.g.
Stock.rb
^^^^^^^^^
self.strength = self.strength.gsub!(’ ml’, ‘ml’) if
The “gsub bang” method returns nil if no changes are made: it’s a
method for changing string variables in place, not really for
assigning the return value (unless you’re using the return value to
check whether any replacements were made.
The “gsub bang” method returns nil if no changes are made: it’s a
method for changing string variables in place, not really for
assigning the return value (unless you’re using the return value to
check whether any replacements were made.
If you assign a value to a variable:
my_variable = “100 mg”
you can alter the variable using the bang method without using an =
operator to assign
so :
my_variable = my_variable.gsub(’ mg’, ‘mg’)
is the same as:
my_variable.gsub!(’ mg’, ‘mg’)
but beware of:
my_variable = my_variable.gsub!(’ mg’, ‘mg’)
as if no substitution is made, the new value of my_variable will be
“nil” (as you discovered