consider scenario,

User model with name, birth_date fields (here birth_date is not mandatory
field)

inside view form birth_date is assigned as '31/31/1985' which is invalid

ideally user object should be invalid and while save raise an error on
birth_date field but that's not happening and user object gets saved with
birth_date as blank which is completely misleading.

After debugging found that while assigning attributes birth_date value it
gets assigned as blank and as birth_date is optional object gets saved.

class User < ActiveRecord::Base

def initialize(args={})
logger.info args[:birth_date] #invalid value comes upto here but
vanishes afterwords

super
end
end

Any clue how to get validation working properly for not mandatory date fields ??



--
sαη∂ιρ Rαηѕιηg

---
www.funonrails.com

twitter, github @sandipransing

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
To post to this group, send email to rubyonrails-talk@googlegroups.com.
To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.

Search Discussions

  • Neethu Satheesh at Feb 1, 2012 at 8:52 am
    Hi Sandip,

    You can provide model level validation for the date as follows.

    class User < ActiveRecord::Base

    validate :validate_birth_date

    def initialize(args={})

    super
    end


    def validate_birth_date
    valid_date_format = /<write a regex for the date in the
    appropriate format>/
    if !birth_date.blank? && !birth_date.match(valid_date_format)
    errors.add(:base, "Birth date is invalid")
    end
    end

    end

    You can explore more about errors in
    http://guides.rubyonrails.org/active_record_validations_callbacks.html#working_with_validation_errors-errors

    Thanks,

    Neethu

    --
    Posted via http://www.ruby-forum.com/.

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Sandip ransing at Feb 1, 2012 at 9:12 am
    thanks for reply but its unusable bcz value gets blank before validation.

    example.
    u = User.new
    u.birth_date = '31/31/2011'
    u.birth_date #=> nil
    u.valid? #=> true

    u.birth_date = '1/1/2011'
    u.birth_date #=> Sat, 01 Jan 2011
    On Wed, Feb 1, 2012 at 2:21 PM, Neethu Satheesh wrote:

    Hi Sandip,

    You can provide model level validation for the date as follows.

    class User < ActiveRecord::Base

    validate :validate_birth_date

    def initialize(args={})

    super
    end


    def validate_birth_date
    valid_date_format = /<write a regex for the date in the
    appropriate format>/
    if !birth_date.blank? && !birth_date.match(valid_date_format)
    errors.add(:base, "Birth date is invalid")
    end
    end

    end

    You can explore more about errors in

    http://guides.rubyonrails.org/active_record_validations_callbacks.html#working_with_validation_errors-errors

    Thanks,

    Neethu

    --
    Posted via http://www.ruby-forum.com/.

    --
    You received this message because you are subscribed to the Google Groups
    "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to
    rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at
    http://groups.google.com/group/rubyonrails-talk?hl=en.

    --
    sαη∂ιρ Rαηѕιηg

    ---
    www.funonrails.com

    twitter, github @sandipransing
    skype sandip.ransing

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Peter Vandenabeele at Feb 1, 2012 at 9:13 am

    On Wed, Feb 1, 2012 at 9:22 AM, sandip ransing wrote:

    consider scenario,

    User model with name, birth_date fields (here birth_date is not mandatory
    field)

    inside view form birth_date is assigned as '31/31/1985' which is invalid

    ideally user object should be invalid and while save raise an error on
    birth_date field but that's not happening and user object gets saved with
    birth_date as blank which is completely misleading.
    You are probably tripped up by the same unexpected behavior I recently
    discovered.

    At least with Postgresql, if you assign a completely invalid string to a
    date (or a datetime)
    field, it does not throw an exception but simply sets the value to nil:
    c.birth_date = "2012-01-15"
    => "2012-01-15"
    1.9.3-p0 :011 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = '2012-01-15', "updated_at"
    = '2012-02-01 08:52:13.063755' WHERE "children"."id" = 1
    (8.5ms) COMMIT
    => true
    1.9.3-p0 :012 > c.birth_date = "2012-01-45"
    => "2012-01-45"
    1.9.3-p0 :013 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = NULL, "updated_at" =
    '2012-02-01 08:54:46.965404' WHERE "children"."id" = 1
    (18.8ms) COMMIT
    => true

    I would have expected an exception here as the POLS.

    But on 'true' it does raise an exception (I discovered this
    because Rails.logger.warning now returns true).

    c.birth_date = true
    => true
    1.9.3-p0 :015 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = 't', "updated_at" =
    '2012-02-01 08:56:00.771141' WHERE "children"."id" = 1
    PGError: ERROR: invalid input syntax for type date: "t"
    LINE 1: UPDATE "children" SET "birth_date" = 't', "updated_at" = '20...
    ^
    : UPDATE "children" SET "birth_date" = 't', "updated_at" = '2012-02-01
    08:56:00.771141' WHERE "children"."id" = 1
    (0.2ms) ROLLBACK
    ActiveRecord::StatementInvalid: PGError: ERROR: invalid input syntax for
    type date: "t"


    After debugging found that while assigning attributes birth_date value it
    gets assigned as blank and as birth_date is optional object gets saved.

    class User < ActiveRecord::Base


    def initialize(args={})
    logger.info args[:birth_date] #invalid value comes upto here but vanishes afterwords


    super
    end
    end

    Any clue how to get validation working properly for not mandatory date fields ??
    As for the validation. You could use a regex, as suggested by Neethu, but
    that has the limitation
    that it is hard do calculate that 2012-01-29 is OK en 2013-01-29 is not OK.

    Better may be to use a combination of strptime and rescue ArgumentError


    1.9.3-p0 :051 > begin
    1.9.3-p0 :052 > Date.strptime("29/02/2012", "%d/%m/%Y")
    1.9.3-p0 :053?> rescue ArgumentError
    1.9.3-p0 :054?> puts "This date is invalid"
    1.9.3-p0 :055?> end
    => Wed, 29 Feb 2012

    1.9.3-p0 :056 > begin
    1.9.3-p0 :057 > Date.strptime("2012-31-31", "%Y-%m-%d")
    1.9.3-p0 :058?> rescue ArgumentError
    1.9.3-p0 :059?> puts "This date is invalid"
    1.9.3-p0 :060?> end
    This date is invalid
    => nil #This comes from the last line in the rescue block, which is puts
    here

    1.9.3-p0 :061 > begin
    1.9.3-p0 :062 > Date.strptime("10/01/2012", "%d/%m/%Y")
    1.9.3-p0 :063?> rescue ArgumentError
    1.9.3-p0 :064?> puts "This date is invalid"
    1.9.3-p0 :065?> end
    => Tue, 10 Jan 2012 # Correct EU dd/mm/yyyy intepretation

    1.9.3-p0 :066 > begin
    1.9.3-p0 :067 > Date.strptime("10/01/2012", "%m/%d/%Y")
    1.9.3-p0 :068?> rescue ArgumentError
    1.9.3-p0 :069?> puts "This date is invalid"
    1.9.3-p0 :070?> end
    => Mon, 01 Oct 2012 # Correct US mm/dd/yyyy interpretation

    HTH,

    Peter

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Sandip ransing at Feb 1, 2012 at 9:25 am
    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model level
    it goes for toss bcz value gets nil before validation(at assignment level)

    Would you please go through my previous reply.


    On Wed, Feb 1, 2012 at 2:43 PM, Peter Vandenabeele
    wrote:
    On Wed, Feb 1, 2012 at 9:22 AM, sandip ransing wrote:

    consider scenario,

    User model with name, birth_date fields (here birth_date is not
    mandatory field)

    inside view form birth_date is assigned as '31/31/1985' which is invalid

    ideally user object should be invalid and while save raise an error on
    birth_date field but that's not happening and user object gets saved with
    birth_date as blank which is completely misleading.
    You are probably tripped up by the same unexpected behavior I recently
    discovered.

    At least with Postgresql, if you assign a completely invalid string to a
    date (or a datetime)
    field, it does not throw an exception but simply sets the value to nil:
    c.birth_date = "2012-01-15"
    => "2012-01-15"
    1.9.3-p0 :011 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = '2012-01-15',
    "updated_at" = '2012-02-01 08:52:13.063755' WHERE "children"."id" = 1
    (8.5ms) COMMIT
    => true
    1.9.3-p0 :012 > c.birth_date = "2012-01-45"
    => "2012-01-45"
    1.9.3-p0 :013 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = NULL, "updated_at" =
    '2012-02-01 08:54:46.965404' WHERE "children"."id" = 1
    (18.8ms) COMMIT
    => true

    I would have expected an exception here as the POLS.

    But on 'true' it does raise an exception (I discovered this
    because Rails.logger.warning now returns true).

    c.birth_date = true
    => true
    1.9.3-p0 :015 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = 't', "updated_at" =
    '2012-02-01 08:56:00.771141' WHERE "children"."id" = 1
    PGError: ERROR: invalid input syntax for type date: "t"
    LINE 1: UPDATE "children" SET "birth_date" = 't', "updated_at" = '20...
    ^
    : UPDATE "children" SET "birth_date" = 't', "updated_at" = '2012-02-01
    08:56:00.771141' WHERE "children"."id" = 1
    (0.2ms) ROLLBACK
    ActiveRecord::StatementInvalid: PGError: ERROR: invalid input syntax for
    type date: "t"


    After debugging found that while assigning attributes birth_date value it
    gets assigned as blank and as birth_date is optional object gets saved.

    class User < ActiveRecord::Base


    def initialize(args={})
    logger.info args[:birth_date] #invalid value comes upto here but vanishes afterwords




    super
    end
    end

    Any clue how to get validation working properly for not mandatory date fields ??
    As for the validation. You could use a regex, as suggested by Neethu, but
    that has the limitation
    that it is hard do calculate that 2012-01-29 is OK en 2013-01-29 is not OK.

    Better may be to use a combination of strptime and rescue ArgumentError


    1.9.3-p0 :051 > begin
    1.9.3-p0 :052 > Date.strptime("29/02/2012", "%d/%m/%Y")
    1.9.3-p0 :053?> rescue ArgumentError
    1.9.3-p0 :054?> puts "This date is invalid"
    1.9.3-p0 :055?> end
    => Wed, 29 Feb 2012

    1.9.3-p0 :056 > begin
    1.9.3-p0 :057 > Date.strptime("2012-31-31", "%Y-%m-%d")
    1.9.3-p0 :058?> rescue ArgumentError
    1.9.3-p0 :059?> puts "This date is invalid"
    1.9.3-p0 :060?> end
    This date is invalid
    => nil #This comes from the last line in the rescue block, which is puts
    here

    1.9.3-p0 :061 > begin
    1.9.3-p0 :062 > Date.strptime("10/01/2012", "%d/%m/%Y")
    1.9.3-p0 :063?> rescue ArgumentError
    1.9.3-p0 :064?> puts "This date is invalid"
    1.9.3-p0 :065?> end
    => Tue, 10 Jan 2012 # Correct EU dd/mm/yyyy intepretation

    1.9.3-p0 :066 > begin
    1.9.3-p0 :067 > Date.strptime("10/01/2012", "%m/%d/%Y")
    1.9.3-p0 :068?> rescue ArgumentError
    1.9.3-p0 :069?> puts "This date is invalid"
    1.9.3-p0 :070?> end
    => Mon, 01 Oct 2012 # Correct US mm/dd/yyyy interpretation

    HTH,

    Peter

    --
    You received this message because you are subscribed to the Google Groups
    "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to
    rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at
    http://groups.google.com/group/rubyonrails-talk?hl=en.


    --
    sαη∂ιρ Rαηѕιηg

    ---
    www.funonrails.com

    twitter, github @sandipransing
    skype sandip.ransing

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Colin Law at Feb 1, 2012 at 9:38 am

    On 1 February 2012 09:24, sandip ransing wrote:
    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model level
    it goes for toss bcz value gets nil before validation(at assignment level)
    The best thing is not to let the user enter a simple string for the
    date, but give him different fields for day, month and year and then
    combine them into a date. Allowing him to enter it as a string will
    cause problems as different users will expect different ordering of
    the date. I generally use date_select for dates as Rails will
    automatically combine the form fields for you.

    Colin

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Peter Vandenabeele at Feb 1, 2012 at 9:58 am

    On Wed, Feb 1, 2012 at 10:35 AM, Colin Law wrote:
    On 1 February 2012 09:24, sandip ransing wrote:
    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model level
    it goes for toss bcz value gets nil before validation(at assignment
    level)

    The best thing is not to let the user enter a simple string for the
    date, but give him different fields for day, month and year and then
    combine them into a date. Allowing him to enter it as a string will
    cause problems as different users will expect different ordering of
    the date. I generally use date_select for dates as Rails will
    automatically combine the form fields for you.
    I had experience that the typical administrative user, is _very_ fast at
    typing
    dates on her numeric keypad. It is really a lot easier for her to type a
    requested
    delivery_date as 300412 (that is delivery on 30 April 2012) even if we as
    developers frown upon it. Maybe a series of 3 boxes as you suggest
    may also be a good compromise.

    The protection against the problem of misinterpretation, is then to show the
    fully expanded date (preferably with a local fast javascript), to verify
    that the
    computer interpreted the data correctly. And use localisation, where users
    in
    EU get dd/mm/yyyy as default setting and users in US get mm/dd/yyyy as
    default input setting.

    HTH,

    Peter

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Sandip ransing at Feb 1, 2012 at 10:26 am
    @peter make sense!
    let me try with overridden birth_date= writer method in rails 3

    On Wed, Feb 1, 2012 at 3:28 PM, Peter Vandenabeele
    wrote:
    On Wed, Feb 1, 2012 at 10:35 AM, Colin Law wrote:
    On 1 February 2012 09:24, sandip ransing wrote:
    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model level
    it goes for toss bcz value gets nil before validation(at assignment
    level)

    The best thing is not to let the user enter a simple string for the
    date, but give him different fields for day, month and year and then
    combine them into a date. Allowing him to enter it as a string will
    cause problems as different users will expect different ordering of
    the date. I generally use date_select for dates as Rails will
    automatically combine the form fields for you.
    I had experience that the typical administrative user, is _very_ fast at
    typing
    dates on her numeric keypad. It is really a lot easier for her to type a
    requested
    delivery_date as 300412 (that is delivery on 30 April 2012) even if we as
    developers frown upon it. Maybe a series of 3 boxes as you suggest
    may also be a good compromise.

    The protection against the problem of misinterpretation, is then to show
    the
    fully expanded date (preferably with a local fast javascript), to verify
    that the
    computer interpreted the data correctly. And use localisation, where users
    in
    EU get dd/mm/yyyy as default setting and users in US get mm/dd/yyyy as
    default input setting.

    HTH,

    Peter

    --
    You received this message because you are subscribed to the Google Groups
    "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to
    rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at
    http://groups.google.com/group/rubyonrails-talk?hl=en.


    --
    sαη∂ιρ Rαηѕιηg

    ---
    www.funonrails.com

    twitter, github @sandipransing
    skype sandip.ransing

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Colin Law at Feb 1, 2012 at 10:54 am

    On 1 February 2012 09:58, Peter Vandenabeele wrote:
    On Wed, Feb 1, 2012 at 10:35 AM, Colin Law wrote:
    On 1 February 2012 09:24, sandip ransing wrote:
    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model
    level
    it goes for toss bcz value gets nil before validation(at assignment
    level)
    The best thing is not to let the user enter a simple string for the
    date, but give him different fields for day, month and year and then
    combine them into a date.  Allowing him to enter it as a string will
    cause problems as different users will expect different ordering of
    the date.  I generally use date_select for dates as Rails will
    automatically combine the form fields for you.

    I had experience that the typical administrative user, is _very_ fast at
    typing
    dates on her numeric keypad. It is really a lot easier for her to type a
    requested
    delivery_date as 300412 (that is delivery on 30 April 2012) even if we as
    developers frown upon it. Maybe a series of 3 boxes as you suggest
    may also be a good compromise.
    I agree that for what one might call an 'internal' app where users
    know what is expected that a single box may be ok. In the case of
    three boxes then provided tab can be used between them this can still
    be quick to type.
    The protection against the problem of misinterpretation, is then to show the
    fully expanded date (preferably with a local fast javascript), to verify
    that the
    computer interpreted the data correctly. And use localisation, where users
    in
    EU get dd/mm/yyyy as default setting and users in US get mm/dd/yyyy as
    default input setting.
    The most safe way is possibly to provide a drop down select box for
    the month then there is no confusion, but it is slower to enter. I
    think date_select will provide this.
    Of course there is no "correct" answer to this, different applications
    require different solutions.

    Colin

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Peter Vandenabeele at Feb 1, 2012 at 11:59 am

    On Wed, Feb 1, 2012 at 11:53 AM, Colin Law wrote:
    On 1 February 2012 09:58, Peter Vandenabeele wrote:
    I had experience that the typical administrative user, is _very_ fast at
    typing
    dates on her numeric keypad. It is really a lot easier for her to type a
    requested
    delivery_date as 300412 (that is delivery on 30 April 2012) even if we as
    developers frown upon it. Maybe a series of 3 boxes as you suggest
    may also be a good compromise.
    I agree that for what one might call an 'internal' app where users
    know what is expected that a single box may be ok.

    Indeed ! That was an internal application. On the external side, we had
    a Datepicker (slower to use, but no ambiguity).


    In the case of
    three boxes then provided tab can be used between them this can still
    be quick to type.
    Or even jump to next box automatically (my banking app does that for the
    account number that has 3 blocks in Belgium). But the inconvenience is
    that I cannot copy paste a full account number to it then :-/

    The protection against the problem of misinterpretation, is then to show the
    fully expanded date (preferably with a local fast javascript), to verify
    that the
    computer interpreted the data correctly. And use localisation, where users
    in
    EU get dd/mm/yyyy as default setting and users in US get mm/dd/yyyy as
    default input setting.
    The most safe way is possibly to provide a drop down select box for
    the month then there is no confusion, but it is slower to enter. I
    think date_select will provide this.
    Of course there is no "correct" answer to this, different applications
    require different solutions.
    +1

    Peter

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Peter Vandenabeele at Feb 1, 2012 at 9:49 am

    On Wed, Feb 1, 2012 at 10:24 AM, sandip ransing wrote:

    Hi Peter,

    validating date against Date.strptime('DATE STRING') will surely work.
    At controller level, i can able to do validation on date but at model
    level it goes for toss bcz value gets nil before validation(at assignment
    level)

    Would you please go through my previous reply.
    OK, get it. I continue below.


    On Wed, Feb 1, 2012 at 2:43 PM, Peter Vandenabeele <peter@vandenabeele.com
    wrote:
    On Wed, Feb 1, 2012 at 9:22 AM, sandip ransing wrote:

    consider scenario,

    User model with name, birth_date fields (here birth_date is not
    mandatory field)

    inside view form birth_date is assigned as '31/31/1985' which is invalid

    ideally user object should be invalid and while save raise an error on
    birth_date field but that's not happening and user object gets saved with
    birth_date as blank which is completely misleading.
    You are probably tripped up by the same unexpected behavior I recently
    discovered.

    At least with Postgresql, if you assign a completely invalid string to a
    date (or a datetime)
    field, it does not throw an exception but simply sets the value to nil:
    c.birth_date = "2012-01-15"
    => "2012-01-15"
    1.9.3-p0 :011 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = '2012-01-15',
    "updated_at" = '2012-02-01 08:52:13.063755' WHERE "children"."id" = 1
    (8.5ms) COMMIT
    => true
    1.9.3-p0 :012 > c.birth_date = "2012-01-45"
    => "2012-01-45"
    1.9.3-p0 :013 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = NULL, "updated_at" = '2012-02-01
    08:54:46.965404' WHERE "children"."id" = 1
    (18.8ms) COMMIT
    => true

    I would have expected an exception here as the POLS.

    But on 'true' it does raise an exception (I discovered this
    because Rails.logger.warning now returns true).

    c.birth_date = true
    => true
    1.9.3-p0 :015 > c.save!
    (0.2ms) BEGIN
    (0.4ms) UPDATE "children" SET "birth_date" = 't', "updated_at" = '2012-02-01
    08:56:00.771141' WHERE "children"."id" = 1
    PGError: ERROR: invalid input syntax for type date: "t"
    LINE 1: UPDATE "children" SET "birth_date" = 't', "updated_at" = '20...
    ^
    : UPDATE "children" SET "birth_date" = 't', "updated_at" = '2012-02-01 08:56:00.771141'
    WHERE "children"."id" = 1
    (0.2ms) ROLLBACK
    ActiveRecord::StatementInvalid: PGError: ERROR: invalid input syntax for
    type date: "t"


    After debugging found that while assigning attributes birth_date value it
    gets assigned as blank and as birth_date is optional object gets saved.

    class User < ActiveRecord::Base


    def initialize(args={})
    logger.info args[:birth_date] #invalid value comes upto here but vanishes afterwords





    super
    end
    end

    Any clue how to get validation working properly for not mandatory date fields ??
    As for the validation. You could use a regex, as suggested by Neethu, but
    that has the limitation
    that it is hard do calculate that 2012-01-29 is OK en 2013-01-29 is not
    OK.

    Better may be to use a combination of strptime and rescue ArgumentError


    1.9.3-p0 :051 > begin
    1.9.3-p0 :052 > Date.strptime("29/02/2012", "%d/%m/%Y")
    1.9.3-p0 :053?> rescue ArgumentError
    1.9.3-p0 :054?> puts "This date is invalid"
    1.9.3-p0 :055?> end
    => Wed, 29 Feb 2012

    1.9.3-p0 :056 > begin
    1.9.3-p0 :057 > Date.strptime("2012-31-31", "%Y-%m-%d")
    1.9.3-p0 :058?> rescue ArgumentError
    1.9.3-p0 :059?> puts "This date is invalid"
    1.9.3-p0 :060?> end
    This date is invalid
    => nil #This comes from the last line in the rescue block, which is puts
    here

    1.9.3-p0 :061 > begin
    1.9.3-p0 :062 > Date.strptime("10/01/2012", "%d/%m/%Y")
    1.9.3-p0 :063?> rescue ArgumentError
    1.9.3-p0 :064?> puts "This date is invalid"
    1.9.3-p0 :065?> end
    => Tue, 10 Jan 2012 # Correct EU dd/mm/yyyy intepretation

    1.9.3-p0 :066 > begin
    1.9.3-p0 :067 > Date.strptime("10/01/2012", "%m/%d/%Y")
    1.9.3-p0 :068?> rescue ArgumentError
    1.9.3-p0 :069?> puts "This date is invalid"
    1.9.3-p0 :070?> end
    => Mon, 01 Oct 2012 # Correct US mm/dd/yyyy interpretation
    With setting an error then:

    u = User.new
    u.birth_date = '31/31/2011'
    u.birth_date #=> nil
    u.valid? #=> true

    u.birth_date = '1/1/2011'
    u.birth_date #=> Sat, 01 Jan 2011


    UNTESTED:
    ONLY WORKs in Rails 3.2.x

    birth_date = is overriden and call the original birth_date = with a
    properly parsed Date object

    my_parsed_date will set an error if the parsing failed,
    so you object is not longer valid.

    NOT TESTED, but indicative of a style.

    class User

    def birth_date=(bd)
    super(my_parsed_date(bd, :birth_date))
    end

    end


    # this function could go in a library somewhere
    def my_parsed_date(bd, attr)
    begin
    Date.strptime(bd, "%m/%d/%Y")
    rescue ArgumentError
    self.errors.add(attr, "date is invalid")
    nil # this will be returned upon rescue
    end
    end


    HTH,

    Peter

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Neethu Satheesh at Feb 1, 2012 at 10:25 am
    In Ruby 1.9.2, Date.parse is now default to parse dd/mm/yyyy (European
    format) instead of mm/dd/yyyy. So the format in mm/dd/yyyy is an invalid
    date. home_run gem will help you to overcome this problem, but comes
    with lot of incompatibilities. In an application I'm using I had to
    revert this gem because it was causing trouble while running tests. Then
    I used Date.strptime for this.

    --
    Posted via http://www.ruby-forum.com/.

    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
  • Valery Kvon at Feb 1, 2012 at 12:02 pm
    This would be my solution:

    lib/formatted_date_time.rb:

    class ActiveRecord::Base

    def self.formatted_date_accessor(*names)
    names.each do |name|
    define_method("#{name}=") do |value|
    super(value)
    if value.present? && self[name].nil?
    class_eval do
    define_method name.to_sym do
    value
    end
    end
    self.class.validate do
    errors.add(name.to_sym, "can't be formatted")
    end
    end
    end
    end
    end

    end


    class User < ActiveRecord::Base
    formatted_date_accessor :birth_date

    end

    If you passing invalid date, it raises an validation error, but returns the invalid date to a form _at_request_.



    On 01.02.2012, at 12:22, sandip ransing wrote:

    consider scenario,

    User model with name, birth_date fields (here birth_date is not mandatory field)

    inside view form birth_date is assigned as '31/31/1985' which is invalid

    ideally user object should be invalid and while save raise an error on birth_date field but that's not happening and user object gets saved with birth_date as blank which is completely misleading.

    After debugging found that while assigning attributes birth_date value it gets assigned as blank and as birth_date is optional object gets saved.

    class User < ActiveRecord::Base


    def initialize(args={})
    logger.info args[:birth_date] #invalid value comes upto here but vanishes afterwords


    super
    end
    end

    Any clue how to get validation working properly for not mandatory date fields ??


    --
    sαη∂ιρ Rαηѕιηg

    ---
    www.funonrails.com

    twitter, github @sandipransing


    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.
    --
    You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group.
    To post to this group, send email to rubyonrails-talk@googlegroups.com.
    To unsubscribe from this group, send email to rubyonrails-talk+unsubscribe@googlegroups.com.
    For more options, visit this group at http://groups.google.com/group/rubyonrails-talk?hl=en.

Related Discussions

Discussion Navigation
viewthread | post
Discussion Overview
grouprubyonrails-talk @
categoriesrubyonrails
postedFeb 1, '12 at 8:23a
activeFeb 1, '12 at 12:02p
posts13
users5
websiterubyonrails.org
irc#RubyOnRails

People

Translate

site design / logo © 2021 Grokbase