Reconstituting a date


#1

In my view code, I have <%= datetime_select “in_out”, “time_in” %>

which returns in params
:in_out: !map:HashWithIndifferentAccess
time_in(1i): “2006”
time_in(2i): “6”
time_in(3i): “12”
time_in(4i): “20”
time_in(5i): “24”

and I want to save that datetime to a column in the db…

if params[:user][:in_out] == "In"
   @in_out.time_in = params[:in_out][:time_in]
elsif params[:user][:in_out] == "Out"
   @in_out.time_out = params[:in_out][:time_in]
   params[:in_out][:time_in] = nil
end

but since it really isn’t a date time, only a null gets saved.

How do I reconstitute it as a date because

@in_out.time_in.to_date = params[:in_out][:time_in] generates an error
and doesn’t work.

Craig


#2

Hi Craig,

Not sure if this will help, but if you look in
gems/activerecord-1.14.x/lib/active_record , you’ll see

def attributes=(new_attributes)
return if new_attributes.nil?
attributes = new_attributes.dup
attributes.stringify_keys!

multi_parameter_attributes = []
remove_attributes_protected_from_mass_assignment(attributes).each do
|k,
v|
k.include?("(") ? multi_parameter_attributes << [ k, v ] : send(k +
“=”,
v)
end

assign_multiparameter_attributes(multi_parameter_attributes)
end

the line that starts k.include gives you a key as to how rails deals
with
hash keys that includes ‘(’. If you then go through
assign_multiparameter_attributes and the methods referenced there, you
should have a pretty good understanding of how multiparameter attributes
work in rails.

What error are you getting? From what I understand, if @in_out is a
model
object where time_in corresponds to a datetime field or a date field,
what
you’re doing should be ok.

Daniel


#3

On Mon, 2006-06-12 at 18:44 -1000, Daniel H. wrote:

multi_parameter_attributes = []
the line that starts k.include gives you a key as to how rails deals with
hash keys that includes ‘(’. If you then go through
assign_multiparameter_attributes and the methods referenced there, you
should have a pretty good understanding of how multiparameter attributes
work in rails.

What error are you getting? From what I understand, if @in_out is a model
object where time_in corresponds to a datetime field or a date field, what
you’re doing should be ok.


NoMethodError
You have a nil object when you didn’t expect it!
The error occured while evaluating nil.to_date=

Request
Parameters: {“user”=>{“will_return”=>"", “in_out”=>“In”}, “commit”=>"
Save ", “in_out”=>{“time_in(1i)”=>“2006”, “time_in(2i)”=>“6”,
“time_in(3i)”=>“12”, “time_in(4i)”=>“21”, “time_in(5i)”=>“51”},
“id”=>“4”}

:in_out: !map:HashWithIndifferentAccess
time_in(1i): “2006”
time_in(2i): “6”
time_in(3i): “12”
time_in(4i): “21”
time_in(5i): “51”

subject line that has the error…
@in_out.time_in.to_time = params[:in_out][:time_in]

prior to the line causing the error…
@in_out = InOut.new # model in_out - table in_outs
time_in is a datetime field in table in_outs or as postgresql calls
it…timestamp without time zone

Craig


#4

Hmm proofreading would have done that email good - I meant setter method
of
“to_date=”, not setter value.


#5

OK, so @in_out.time_in is a nil object, but you’re trying to call a
method
on it. Two questions: is @in_out.time_in supposed to be nil at this
point?
And, dose @in_out.time_in.to_date= actually exist? I’d think that with
a
name like “to_date”, the method would only return a value, and a
“setter”
value of “to_date=” wouldn’t exist.

Daniel


#6

Yeah, you’re right but even the other way causes the same error…

@my_time = params[:in_out][:time_in].to_date

I get a nil object error


#7

On Tue, 2006-06-13 at 00:21 -0500, Rick O. wrote:

How do I reconstitute it as a date because

@in_out.time_in.to_date = params[:in_out][:time_in] generates an error and doesn’t work.

Craig

http://rails.techno-weenie.net/tip/2006/6/1/datetime_form_fields_to_time


closer…

@my_time = Time.parse_from_attributes(params[:in_out, :time_in])

ArgumentError
wrong number of arguments (2 for 1)

Parameters: {“user”=>{“will_return”=>"", “in_out”=>“Out”}, “commit”=>"
Save ", “in_out”=>{“time_in(1i)”=>“2006”, “time_in(2i)”=>“6”,
“time_in(3i)”=>“12”, “time_in(4i)”=>“22”, “time_in(5i)”=>“18”},
“id”=>“2”}

Craig


#8

On 6/12/06, Craig W. removed_email_address@domain.invalid wrote:

and I want to save that datetime to a column in the db…
How do I reconstitute it as a date because

@in_out.time_in.to_date = params[:in_out][:time_in] generates an error and doesn’t work.

Craig

http://rails.techno-weenie.net/tip/2006/6/1/datetime_form_fields_to_time


#9

I tried that already, that strangely reports the same error except…

wrong number of arguments (1 for 2)

I can’t win on this and clearly rails is a PITA where it comes to using
date helpers

Craig


#10

In Ruby, [] is an operator, so when you have params[:in_out, :time_in]
and
you get the error you got, Ruby’s telling you that you you need to lose
“:time_in”. The way you had it before was correct:
params[:in_out][:time_in]


#11

OK, let’s try this differently…how can I access

time_in(1i) etc… from the following?

Parameters: {“user”=>{“will_return”=>"", “in_out”=>“Out”}, “commit”=>"
Save ", “in_out”=>{“time_in(1i)”=>“2006”, “time_in(2i)”=>“6”,
“time_in(3i)”=>“12”, “time_in(4i)”=>“22”, “time_in(5i)”=>“18”},
“id”=>“2”}

params[:in_out]:time_in
params[:in_out][:time_in][1i]
params[:in_out][:time_in].1i

all give me errors and my thinking is that I could parse them into a
string and then use to_date to convert them back

Craig


#12

Hi Craig,

Craig W. wrote

OK, let’s try this differently…how can I access

time_in(1i) etc… from the following?

Parameters: {“user”=>{“will_return”=>"", “in_out”=>“Out”}, “commit”=>"
Save ", “in_out”=>{“time_in(1i)”=>“2006”, “time_in(2i)”=>“6”,
“time_in(3i)”=>“12”, “time_in(4i)”=>“22”, “time_in(5i)”=>“18”},
“id”=>“2”}

Don’t know if this will work but, since you didn’t say you’d tried it,
I’d
try params[:in_out][:time_in(1i)] since the ‘(1i)’ is inside the quotes.
I
haven’t done much with accessing dates in pieces so it might not work.

hth,
Bill


#13

This works for me in a date testing method in controller/application.rb:

def test_date(object,attribute)
Date.valid_civil?(params[object][attribute + ‘(1i)’].to_i,
params[object][attribute + ‘(2i)’].to_i,
params[object][attribute + ‘(3i)’].to_i)
end

Object and attribute are passed as symbols, i.e. in your case:

test_date(:in_out,:time_in)


– Tom M.


#14

On Tue, 2006-06-13 at 10:12 -0700, Tom M. wrote:

test_date(:in_out,:time_in)


gee…on my second day with this issue of trying to take a date/time
from a ‘helper’ and making it save a useful date/time in my table…

this_time = (params[:user][:data_time_date + ‘(1i)’].to_i,
params[:user][:data_time_date + ‘(2i)’].to_i,
params[:user][:data_time_date + ‘(3i)’].to_i,
params[:user][:data_time_date + ‘(4i)’].to_i,
params[:user][:data_time_date + ‘(5i)’].to_i)

SyntaxError
app/controllers/in_outs_controller.rb:58: syntax error, unexpected ‘)’,
expecting ‘=’

Parameters: {“user”=>{“data_time_date(3i)”=>“13”, “will_return”=>"",
“data_time_date(4i)”=>“14”, “in_out”=>“In”, “data_time_date(5i)”=>“00”,
“data_time_date(1i)”=>“2006”, “data_time_date(2i)”=>“6”}, “commit”=>"
Save "}

I’m astonished that the above works for you Tom as that methodology is
clearly not working for me.

Lemme see now…decimals don’t necessarily work, dates apparently
require magic incantations…I’m losing faith.

Craig

Parameters: {“user”=>{“will_return”=>"", “in_out”=>“Out”},
“commit”=>"
Save ", “in_out”=>{“time_in(1i)”=>“2006”, “time_in(2i)”=>“6”,
“time_in(3i)”=>“12”, “time_in(4i)”=>“22”, “time_in(5i)”=>“18”},
“id”=>“2”}

Don’t know if this will work but, since you didn’t say you’d tried
it, I’d try params[:in_out][:time_in(1i)] since the ‘(1i)’ is
inside the quotes. I haven’t done much with accessing dates in
pieces so it might not work.


Note to Bill…thanks, didn’t work

Craig


#15

Hey Craig-

I just had to deal with a date_select like this. When you can use

object.update_attributes params[:object] the ActiveRecord will deal
with sorting out the (1i) params fro you. Unfortunately if you can’t
just hand these params straight into an update_attributes call it is
a little harder to deal with. But this works for me:

Date.new(params[‘violation’][‘date(1i)’].to_i,params[‘violation’]
[‘date(2i)’].to_i,params[‘violation’][‘date(3i)’].to_i)

Hope that helps.

-Ezra


#16

On Tue, 2006-06-13 at 17:13 -0700, Craig W. wrote:

[‘date(2i)’].to_i,params[‘violation’][‘date(3i)’].to_i)
returns to postgresql as 2006-06-13 00:00:00
and it should be like 2006-06-13 17:06:00

But all in all…not bad for a day and a half’s effort


found an answer on technoweenie but not the one that he pointed me to…

this_time = Time.local(params['user']['data_time_date(1i)'].to_i,
                       params['user']['data_time_date(2i)'].to_i,
                       params['user']['data_time_date(3i)'].to_i,
                       params['user']['data_time_date(4i)'].to_i,
                       params['user']['data_time_date(5i)'].to_i)

local was the key. Reported in case others stumble in my footsteps

Thanks everyone

Craig


#17

On Tue, 2006-06-13 at 19:26 -0700, Craig W. wrote:

Date.new(params[‘violation’][‘date(1i)’].to_i,params[‘violation’]

                       params['user']['data_time_date(4i)'].to_i,
                       params['user']['data_time_date(5i)'].to_i)

local was the key. Reported in case others stumble in my footsteps


I’ll also point out that I ended up ditching this very hard acquired
knowledge in favor of the plugin flextimes which has many distinct
advantages.

http://seanicus.blogspot.com/2006/05/flextimes-moved.html

Craig


#18

On Tue, 2006-06-13 at 14:56 -0700, Ezra Z. wrote:

Hey Craig-

I just had to deal with a date_select like this. When you can use
object.update_attributes params[:object] the ActiveRecord will deal
with sorting out the (1i) params fro you. Unfortunately if you can’t
just hand these params straight into an update_attributes call it is
a little harder to deal with. But this works for me:

Date.new(params[‘violation’][‘date(1i)’].to_i,params[‘violation’]
[‘date(2i)’].to_i,params[‘violation’][‘date(3i)’].to_i)


that helps a lot but I am trying to do a DateTime class so I can have
the timestamp as well.

this_time = DateTime.new(params[‘user’][‘data_time_date(1i)’].to_i,
params[‘user’][‘data_time_date(2i)’].to_i,
params[‘user’][‘data_time_date(3i)’].to_i,
params[‘user’][‘data_time_date(4i)’].to_i,
params[‘user’][‘data_time_date(5i)’].to_i)

returns to postgresql as 2006-06-13 00:00:00
and it should be like 2006-06-13 17:06:00

But all in all…not bad for a day and a half’s effort

Craig