Hash data being altered when sent to class - ruby-on-rails

My endpoint sends params to a class/worker.
def end_point
SomeClass.new.perform(params)
end
SomeClass starts defining variables.
def perform(params)
#variable = params[:variable]
end
If I do #variable.count in a pry session, it will return 2. But if I do params[:variable].count, it returns 1(the correct value). The data is being altered from within the method.
I tried renaming the arguments from params, I tried setting the variable in pry manually (this will result in 1), but when it is defined inside the method, it still results in 2. I inspected to make sure nothing is being altered sending from the controller. Any help would be greatly appreciated.
params
{"variable"=>
[{"id"=>68,
"ed"=>5213,
"lo_id"=>2192,
"lo_name"=>"Arkan",
"state"=>"created",
"closed_at"=>nil,
"unstarted"=>false,
"crtal"=>0,
"cas_eived"=>0,
"or_payments"=>0,
"cips"=>0,
"g_sles"=>0,
"ters"=>0,
"itews"=>
[{"id"=>615,
"unit_re"=>{"id"=>708, "name"=>"each", "abbreviation"=>"ea", "quantity"=>"1.0", "stock_item_id"=>985, "default_for"=>["base"]},
"pce"=>0,
"nme"=>"1 Yer nant",
"sol]unt"=>0,
"cgory_id"=>nil,
"caty_name"=>"Uncategorized",
"sub_rows"=>nil,
"prev_count"=>0,
"preransfunt"=>0,
"pre_nt"=>0,
"staount"=>0,
"actrt_count"=>0,
"id_evecount"=>0,
"minsfers_out_ount"=>0,
"wasunt"=>0,
"grunt"=>0,
"ennt"=>0,
"ovunt"=>0,
"gont"=>0,
"quane"=>1,
"expunt"=>0,
"goes"=>0,
"staiance"=>0,
"vance"=>0,
"paramsToConvert"=>
["scount",
"pent_transfer_in_count",
"pent_transfer_out_count",
"s_end_count",
"o_count",
"e_count",
"g_count",
"a_start_count",
"m_transfers_in_count",
"m_transfers_out_count",
"g_count",
"w_count",
"s_count"]},
"action"=>"batch_print",
"controller"=>"s",
"event_id"=>"53",
"format"=>"pdf"
}

Related

Checking if a table has been created not working

Using the code:
function createNewBody(name,mass)
if not world.body[name]==nil then
print("This body has already been created. Maybe you meant to update it's values?\n")
else
world.body[name]={mass=m,x=0,y=0,xAccel=0,yAccel=0,xR=0,yR=0,properties={gaseous=false,texture=""}}
world.bodies=world.bodies+1
end
end
This code shows no errors, but when I bind createNewBody(moon,1.622) to a key and then use it, it lets me spam the key without showing the error message.
And, yes, I have defined world.bodies and world.body
not world.body[name]==nil is parsed as (not world.body[name])==nil. Since the result of not is a boolean, it is never nil.
Try not(world.body[name]==nil) or world.body[name]~=nil.

no block given yield

So executing this gives me back an error:
no block given (yield)
Well never had a deep look at blocks in ruby, which seems to be an issue in here. If you have a better solution please provider, otherwise I wanted to find a workaround for the this legacy code...
def tab_groupings
result = at_a_glance_grouping
result += rating_grouping if #domain_context.include_ratings and (controller.controller_name !='rewards_credit_cards')
result += specific_tab_groupings
result
end
def at_a_glance_grouping
result = [[:at_a_glance, yield]]
product_type = controller.controller_name == 'fairfax' ? #product_type_helper[:controller] : controller.controller_name
result[0][1].insert(0, :overall_rating) if #domain_context.include_ratings and (product_type !='rewards_credit_cards')
result
end
yield is used to execute a block that you pass to the method, and then you do something with the result of that call.
Your method at_a_glance_grouping therefore expects you to pass a block to it... which it will then execute on the following line (where you use yield)
You don't pass any blocks to at_a_glance_grouping in the first line of tab_groupings, and therefore ruby rightfully complains.
What are you trying to achieve with the yield ?
Do you really need it at all?
If not - then just remove it.
If sometimes you do pass a block to this method, then you need to check for that before calling yield eg:
result = [[:at_a_glance, yield]] if block_given?

Rails 3: object.save is writing the old values to database

I have code which is updating a model's property then calling save!. A Rails.logger.info call shows that the model thinks it has the new values. But the SQL write performed by the save! call is writing the old value to the database.
At first it wasn't writing anything to the database at all when I called save!. I thought it was that the object wasn't thinking its value had changed for some reason: changed? returned false, so I used a _will_change! notification to force a write. But now it is doing a write, but with the old values.
This doesn't happen from the "rails console" command line: there I'm able to update the property and it will return changed? of true, and let me save successfully.
Excerpt from the server log follows. Note that the object thinks it has log_ids of '1234,5678,1137', but writes to the database '1234,5678'.
current log ids are [1234, 5678]
new log ids are [1234, 5678, 1137]; writing log_ids of '1234,5678,1137' to NewsList 13 with dirty true
SQL (2.0ms) UPDATE "news_lists" SET "log_ids" = '1234,5678', "updated_at" = '2012-01-02 02:12:17.612283' WHERE ("news_lists"."id" = 13)
The object property in question is log_ids, which is a string containing several IDs of another kind of object.
The source code that produced the output above:
def add_log(new_log)
new_ids = get_log_ids
Rails.logger.info("current log ids are #{new_ids}")
if new_ids.length >= NewsList.MAX_LENGTH
new_ids.shift
end
log_ids_will_change!
new_ids.push new_log.id
log_ids = new_ids.join ","
Rails.logger.info("new log ids are #{new_ids}; writing log_ids of '#{log_ids}' to NewsList #{id} with dirty #{changed?}")
save!
end
def get_log_ids
if log_ids
log_ids.split(",").map &:to_i
else
[]
end
end
Can anyone suggest what might be going on here?
Add the self to self.log_ids = new_ids.join "," otherwise you will just be assigning to the local variable (namesake) instead of the db-persisted attribute (column).

Not able to hit mixpanel in delayed job?

I am using delayed_job to do some background task. In between I want to track some events. I am using mixpanel gem to track the events. In controller its working perfectly fine. But not in Delayed Job.
Code I am using
#original_message = Message.find(message_id)
#mixpanel= Mixpanel::Tracker.new("43242637426346287482", message_id, true)
#mixpanel.track_event("blank_body", {:reset_result => "sucess" })
//message_id is a unique for every request.
I have specified
gem 'mixpanel' in gemfile
{undefined method `[]=' for 45:Fixnum
/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/mixpanel-0.9.0/lib/mixpanel/tracker.rb:38:in clear_queue'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/mixpanel-0.9.0/lib/mixpanel/tracker.rb:13:ininitialize'\n/Users/mohit/projects/textadda/lib/message_job.rb:109:in new'\n/Users/mohit/projects/textadda/lib/message_job.rb:109:inperform'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/backend/base.rb:87:in invoke_job'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:120:inrun'\n/Users/mohit/.rvm/rubies/ruby-1.8.7-p334/lib/ruby/1.8/timeout.rb:67:in timeout'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:120:inrun'\n/Users/mohit/.rvm/rubies/ruby-1.8.7-p334/lib/ruby/1.8/benchmark.rb:308:in realtime'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:119:inrun'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:177:in reserve_and_run_one_job'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:104:inwork_off'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:103:in times'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:103:inwork_off'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:78:in start'\n/Users/mohit/.rvm/rubies/ruby-1.8.7-p334/lib/ruby/1.8/benchmark.rb:308:inrealtime'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:77:in start'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:74:inloop'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/worker.rb:74:in start'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/delayed_job-2.1.4/lib/delayed/tasks.rb:9\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:205:incall'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:205:in execute'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:200:ineach'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:200:in execute'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:158:ininvoke_with_call_chain'\n/Users/mohit/.rvm/rubies/ruby-1.8.7-p334/lib/ruby/1.8/monitor.rb:242:in synchronize'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:151:ininvoke_with_call_chain'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/task.rb:144:in invoke'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:112:ininvoke_task'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:90:in top_level'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:90:ineach'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:90:in top_level'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:129:instandard_exception_handling'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:84:in top_level'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:62:inrun'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:129:in standard_exception_handling'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/lib/rake/application.rb:59:inrun'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/gems/rake-0.9.2/bin/rake:32\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/bin/rake:19:in `load'\n/Users/mohit/.rvm/gems/ruby-1.8.7-p334/bin/rake:19
EDIT
I have implemented mixpanel in background process using standard get request. But I am still looking for the solution how can I use Mixpanel gem in background process.
You should just be doing something like this:
#mixpanel= Mixpanel::Tracker.new("43242637426346287482", {:REMOTE_ADDR => message_id}, true)
#mixpanel.track_event("blank_body", {:reset_result => "sucess" })
The gem expects the second variable to be the request environment, so will get the ip address that way, and send that to mixpanel.com. But I am not even sure if that is really needed, so I think that even a simple
#mixpanel= Mixpanel::Tracker.new("43242637426346287482", {}, true)
#mixpanel.track_event("blank_body", {:reset_result => "sucess" })
should work.
Hope this helps.
NOTE: THIS ANSWER IS NOW OUT OF DATE AS OF OCT 15 2012 AS THE INITIALIZE METHOD NO LONGER TAKES A ENV PARAMETER
The example on https://github.com/zevarito/mixpanel Mixpanel::Tracker.new gets called like this:
Mixpanel::Tracker.new("YOUR_MIXPANEL_API_TOKEN", request.env, true)
In a controller context, request.env is a hash.
In your code above your passing in message_id as the second argument, which looks like an integer. Sorry, can't help anymore than that, don't know anything about the mixpanel gem, but that's the root of your problem.
If the mixpanel API documentation tells you you can pass an integer as the second parameter, it's incorrect. Here's the code relevant to your error from https://github.com/zevarito/mixpanel/blob/master/lib/mixpanel/tracker.rb
module Mixpanel
class Tracker
def initialize(token, env, async = false)
#token = token
#env = env
#async = async
clear_queue
end
# snip
def clear_queue
#env["mixpanel_events"] = []
end
# snip
end
end
Passing an integer as the second argument to the initializer will not work, because the Fixnum class doesn't have a hash assignment ([]=) method, which is exactly the error message you are getting.
If the documentation tells you this can be an integer, you should probably file an issue against mixpanel.

Disable rails class_caching mechanism for Time.now?

I'm currently fighting with the rails class_caching mechanism as I need to return a file path that changes discrete over time. It is used to constantly change a log file path after the amount of GRAIN seconds and returns a fully working timestamp:
GRAIN = 30
def self.file_path
timestamp = (Time.now.to_i / GRAIN) * GRAIN
return FILE_DIR + "tracking_#{timestamp.call}.csv"
end
This works really great if the class_caching of rails is set to false. But of course the app is to run with enabled class caching. And as soon as I enable it, either the timestamp variable is cached or the Time.now expression.
I tried to solve this with a proc block, but no success:
def self.file_path
timestamp = Proc.new { (Time.now.to_i / GRAIN) * GRAIN }
return FILE_DIR + "tracking_#{timestamp.call}.csv"
end
Is there anything like a cache disabled scope I could use or something like skip_class_caching :file_path? Or any other solutions?
Thank you for your help!
It's not entirely clear where your code is located, but ActiveRecord has an uncached method that suspends the cache for whatever is inside its block.
I found the problem. Not the Time.now was beeing cached but a logger instance. It was assigned in another method calling the file_path.
As long as the class caching was disabled the environment forgot about the class variable between the requests. But as soon as it was enabled the class variable stayed the same - and desired value - but never changed.
So I had to add a simple condition that checks if the file_path changed since the last request. If so, the class variable is reassigned, otherwise it keeps the same desired value.
I changed from:
def self.tracker
file_path = Tracking.file_path
##my_tracker ||= Logger.new(file_path)
end
to:
def self.tracker
file_path = Tracking.file_path
##my_tracker = Logger.new(file_path) if ##my_tracker.nil? or Tracking.shift_log?(file_path)
##my_tracker
end
Thank you for your help anyways!

Resources