Rails undefined method `+' for nil:NilClass - ruby-on-rails

I have a method 'calc_price' that was working previously, and still works in console, but is now giving me the following error in a browser:
NoMethodError in Quotes#index
undefined method `+' for nil:NilClass
18: Price: $<%= f.calc_price %><br />
app/models/quote.rb:33:in `block in calc_price'
app/models/quote.rb:13:in `calc_price'
app/views/quotes/index.html.erb:18:in `block in _app_views_quotes_index_html_erb__1788058106025144185_70227449765940'
app/views/quotes/index.html.erb:15:in `each'
app/views/quotes/index.html.erb:15:in `_app_views_quotes_index_html_erb__1788058106025144185_70227449765940'
The fact that it still works in console is confusing to me, especially since I didn't change the method at all for it to break. The method:
def calc_price
self.items.each do |item|
pr = if item.amount < 10
item.product.pricerange0
elsif item.amount < 25
item.product.pricerange1
elsif item.amount < 50
item.product.pricerange2
elsif item.amount < 100
item.product.pricerange3
elsif item.amount < 250
item.product.pricerange4
elsif item.amount < 500
item.product.pricerange5
end
screens = 0
sd = item.shirtdesigns.count
pd = item.pantdesigns.count
screens = (sd+pd)
screenprice = (screens*25)
inkprice = ((item.inkcolors-1)*0.5)
newprice = ((pr+inkprice)*item.amount+screenprice)
item.price = newprice
item.save
end
newprice = self.items.sum('price')
self.price = newprice
self.save
return self.price
end
quote controller
def index
#quote = Quote.find(:all)
#myquotes = Quote.find(:all, :conditions => { :user_email => current_user.email })
end
I tried adding screenprice = 0, newprice = 0 and inkprice = 0 to see if that would make a difference but it did not.
If it still works in console does that mean maybe its not the method itself that is broken?
Any help would be greatly appreciated! Thanks

pr is most likely nil. An item with an amount greater than 500 would result in pr being nil in the code above.

Related

Cannot convert data from cookies

I want to make a method that will count the number of user actions on the site.
I have the code:
def actions_counter
if cookies[:"actions"] != nil
cookies[:"actions"].to_i += 1
else
cookies[:"actions"] = 0
end
end
But for some reason this does not work.
NoMethodError in PostsController#show
undefined method `to_i=' for "1":String Did you mean? to_i to_r to_f to_s to_d to_c
Just change your method to
def actions_counter
if cookies[:actions]
cookies[:actions] = cookies[:actions].to_i + 1
else
cookies[:actions] = 0
end
end
The issue is that Ruby understands cookies[:"actions"].to_i += 1 as
cookies[:"actions"].to_i = cookies[:"actions"].to_i + 1
# and this ^^^^^^^^ doesn't make sense

Service throwing "undefined method" error

I may be missing something obvious, but I can't figure out where my problem is. I have a service called GoodMorning (app/services/good_morning.rb)
class GoodMorning
def self.dawn(user)
if user.goal_days.where("day = ?", Date.today).count == 0
user.goals.each do |goal|
if goal[time.strftime("%A")] == true
GoalDay.create(goal_id: goal.id, body: goal.body, target: goal.target, actual: 0, day: Date.today)
end
end
session[:sun] = true
end
end
end
And then in a controller called Clearing (app/controllers/clearing_controller.rb) I call it:
def index
#user = current_user
#goals_today = GoalDay.where("user_id = ? AND day = ?", #user.id, Date.today)
if session[:sun] == true
if #goals_today.count == 0
session[:sun] = false
end
else
GoodMorning(#user).dawn
end
end
I get the following error:
undefined method `GoodMorning' for #
Thank you for any help seeing what I'm missing! I restarted the server etc.
Try...
GoodMorning.dawn(#user)

Ruby each block next when exception or error is raised

I have the following method in my rake task.
def call
orders = Spree::Order.complete.where('completed_at >= :last_day', last_day: Time.now - 30.days)
orders.each do |order|
order_tracking = order.shipments.first.tracking
next if order_tracking.nil?
shipment = order.shipments.first
results = fedex.track(tracking_number: order_tracking)
tracking_info = results.first
status = tracking_info.status.to_s
delivery_date = tracking_info.delivery_at
shipment.is_delivered = delivered?(status)
shipment.date_delivered = delivery_date
shipment.save
puts "-> Shipping status was updated for #{order.number}"
end
end
If there is an order with no tracking number I skipping it with next on line 5.
My question: How would I do next if a tracking number is invalid and the following error is raised:
Fedex::RateError: Invalid tracking number.
Ideally I would like to change line 5 to:
next if order_tracking.nil? || order_tracking.raised(Fedex::RateError) # something like that
Thank you in advance.
Also RateError is raised here:
def process_request
api_response = self.class.post(api_url, :body => build_xml)
puts api_response if #debug == true
response = parse_response(api_response)
if success?(response)
options = response[:track_reply][:track_details]
if response[:track_reply][:duplicate_waybill].downcase == 'true'
shipments = []
[options].flatten.map do |details|
options = {:tracking_number => #package_id, :uuid => details[:tracking_number_unique_identifier]}
shipments << Request::TrackingInformation.new(#credentials, options).process_request
end
shipments.flatten
else
[options].flatten.map do |details|
Fedex::TrackingInformation.new(details)
end
end
else
error_message = if response[:track_reply]
response[:track_reply][:notifications][:message]
else
"#{api_response["Fault"]["detail"]["fault"]["reason"]}\n--#{api_response["Fault"]["detail"]["fault"]["details"]["ValidationFailureDetail"]["message"].join("\n--")}"
end rescue $1
raise RateError, error_message
end
end
added:
private
def fedex_track(tracking)
fedex.track(tracking_number: tracking)
end
And changed results on line 7 to:
results = fedex_track(order_tracking) rescue next

Ruby: Am I using the 'do block' incorrectly? I'm getting "undefined method `scan' for #<Hash:>"

I'm trying to display unique IPS alerts for my dashboard. If I display #filtered_snort_detail_query I get loads of alerts, and many could be ignored since alerts are packet based and one attack can generate 100's or 1000's of alerts. No need to display all of them. I'm trying to use scan to find the sig ID, source IP, and destination IP.
When it's all said and done, I'm looking to display #snort_dash_info in my view vs. #filtered_snort_detail_query
My error:
undefined method `scan' for #<Hash:0x007f088a7a4830>
app/controllers/csdashboard_controller.rb:139:in `block in index'
app/controllers/csdashboard_controller.rb:138:in `each'
app/controllers/csdashboard_controller.rb:138:in `index'
Code from the controller (Line 139 starts with sid_data):
if #es_snort_detail_query.count > 0
#filtered_snort_detail_query = Array.new
#es_snort_detail_query.each do |ips_detail|
next if ips_detail['_source']['type'] != 'snort-ips'
next if ips_detail['_source']['#timestamp'] < #ts
#filtered_snort_detail_query.push(ips_detail)
end
if #filtered_snort_detail_query.count > 0
#snort_dash_info = Array.new
sid = Array.new
ip_src = Array.new
ip_dst = Array.new
#filtered_snort_detail_query.each do |ips_alerts|
sid_data = ips_alerts.scan(/\[\d+:\d+:\d+\]/)
src_ip_data = ips_alerts.scan(/(?:[0-9]{1,3}\.){3}[0-9]{1,3}/)
dst_ip_data = ips_alerts.scan(/(?:[0-9]{1,3}\.){3}[0-9]{1,3}/)
sid.push(sid_data[0]) unless sid_data[0].nil?
ip_src.push(src_ip_data[0]) unless src_ip_data[0].nil?
ip_dst.push(dst_ip_data[1]) unless dst_ip_data[1].nil?
snort_details = [{:ips_info => sid},{:ips_info => ip_src}, {:ips_info => ip_dst}]
snort_details_info = snort_details.uniq do |show_me|
show_me[:ips_info]
end
#snort_dash_info.push(snort_details_info)
end
end
end
Use each_pair like:
ips_alerts.each_pair { |k, v| puts "#{k} #{v}" }
So in order to get what you want, try:
ips_alerts.each_pair do |k, v|
if k == "sid_data" # pure assumption on my part
sid_data = v.scan(/(?:[0-9]{1,3}\.){3}[0-9]{1,3}/)
end
end
Sorry I can't think of a prettier way but it works.
Got it some what working, so I guess this question should be done. I'm not getting the undefined method for scan anymore, and I've verified that my unique_ids are working. The only issue is I'm now displaying the unique_ids and not using them to remove duplicate alerts. That's for another question I guess..
Code:
if #es_snort_detail_query.count > 0
sid = Array.new
ip_src = Array.new
ip_dst = Array.new
#snort_dash_info = Array.new
#es_snort_detail_query.each do |ips_detail|
next if ips_detail['_source']['type'] != 'snort-ips'
next if ips_detail['_source']['#timestamp'] < #ts
if ips_detail['_source']['message'].nil?
text_msg = ips_detail['_source']['message']
else
text_msg = ips_detail['_source']['message']
end
unless text_msg.nil?
sid_data = text_msg.scan(/\[\d+:\d+:\d+\]/)
src_ip_data = text_msg.scan(/(?:[0-9]{1,3}\.){3}[0-9]{1,3}/)
dst_ip_data = text_msg.scan(/(?:[0-9]{1,3}\.){3}[0-9]{1,3}/)
sid.push(sid_data[0]) unless sid_data[0].nil?
ip_src.push(src_ip_data[0]) unless src_ip_data[0].nil?
ip_dst.push(dst_ip_data[1]) unless dst_ip_data[1].nil?
unique_ids = [{:ips_info => sid},{:ips_info => ip_src}, {:ips_info => ip_dst}]
snort_details_info = unique_ids.uniq do |show_me|
show_me[:ips_info]
end
#snort_dash_info.push(snort_details_info)
end
end
end

Rails Fixnum Error

I have a simple query that Rails seems to be interpreting as a fixnum, but I'm not sure why. My code looks like this:
#user_with_points = Point.select("sum(points) as points, user_id").order("points desc").group("user_id")
#user_with_points.each_with_index do |user_with_point, index|
When I add puts #user_with_points, it shows:
#<Point:0x6360138>
#<Point:0x6322f38>
However, I'm receiving this error this error:
NoMethodError: undefined method 'each' for 75:Fixnum
adding Entire Code
def self.update_overall_rank_and_points
#user_with_points = Point.select("sum(points) as points, user_id").order("points desc").group("user_id")
rank = 0
points = 0
#user_with_points.each_with_index do |user_with_point, index|
#user = User.find(user_with_point.user_id)
if user_with_point.points != points
points = user_with_point.points
rank += 1
end
#user.rank = rank
#user.points = user_with_point.points
#user.save
end
end
Your query is returning a scalar value which the sum of points as an integer. The total of your query happens to be 75, hence the error. Therefore you can't do an each against it since it's not an enumeration.
Try:
#user_with_points = Point.sum(:points, :group => :user_id, :order => 'sum(points)')
#user_with_points.each do |user_id, points|
#...
user = User.find(user_id)
if user.points != points
puts "not equal!"
end
end

Resources