[Nitro] Validations, was re: 0.26.0 preview
George Moschovitis
george.moschovitis at gmail.com
Tue Dec 20 04:06:47 EST 2005
Bryan, please resend me the patch with this implementation!
regards,
George.
On 12/17/05, Bryan Soto <bryan.a.soto at gmail.com> wrote:
> <code>
>
> require 'nitro'
> require 'og'
> require 'user'
>
> require 'dev-utils/debug'
>
> Og.setup
>
> class ValidationTest
> def index
> out = "The number of validations for User is
> #{User.validations.length}.<br />"
> u = User.new
> u.username = 'bryan'
> u.password = 'bryan'
> if u.valid?
> u.save
> else
> out << "<br />#{u.errors.errors.inspect}<br />"
> end
> out
> end
> end
>
> Nitro.run ValidationTest
>
> </code>
>
> Run against gems and dev version.
>
> Touch user.rb. Await reload message on console, then refresh browser.
>
> Notice how in gem version, the number of validations increases, but the
> number of errors remains unchanged.
>
> Repeat using dev version. Notice that the number of validations increases
> as well as the number of error message entries.
>
> Basically, the gem version evals the code _once_ in eval_validate
> (glue/lib/validations.rb) the first time #valid? is called, so it ignores
> the repeated validations.
>
> Hope this clears things up as too what I'm talking about. I need to brush
> up on my communication skills. It all made sense to me every single time I
> wrote 8^).
>
> --
>
> As too future design, I was thinking something more like:
>
> <code>
>
> class ValidationKey
> attr_reader :validation
> attr_reader :field_name
>
> def initialize(val, field)
> @validation, @field_name = val.to_s, field.to_s
> end
>
> def hash
> "#{@validation}-#{@field_name}".hash
> end
>
> def ==(other)
> self.validation == other.validation and self.field_name ==
> other.field_name
> end
> end
>
> vk = ValidationKey.new(:validate_unique, :username)
>
> validations[vk] = validate_unique_proc_goes_here
>
> </code>
>
> as the key and the proc as the value in the hash. Then the new key would
> just overwrite the old. No more duplicate entries.
>
> And as for application level validations, I was thinking someone with a
> shopping cart might have written their own validate_credit_card_number. Or
> validate_password, where password requires at least one number. Basically,
> some sort of validation that only makes sense in their particular
> application. Though I suppose most people just use aspects for that.
>
> bryan
>
>
> On 12/16/05, Brian Bugh <brian at xsi-design.com> wrote:
> > I'm not sure I understand what you mean. The new code is functionally
> > identical to the old way, only it's using blocks and Proc objects
> > instead of using eval. Try this simple Nitro app with both the old and
> > new code:
> >
> > require 'nitro'
> > require 'og'
> > require 'user'
> >
> > Og.setup
> >
> > class ValidationTest
> > def index
> > "The number of validations for User is
> > #{User.validations.length}."
> > end
> > end
> >
> > Nitro.run ValidationTest
> >
> > Check it in the browser, and it will say 2, then touch user.rb and it
> > will say 4. The old way basically copy and pasted code into a function,
> > whereas now that code is a list of anonymous methods in an array that is
> > iterated. That array is only iterated when validate or valid? is called
> > - the same times as the long function was called before. Hopefully that
> > helps clarify the issue for you.
> >
> > --
> >
> > I have thought about your suggestion, and I think it is a possibility.
> > Do you mean only store the validation list and each field like this:
> >
> > {:validate_unique => [:username], :validate_value => [:password]}
> >
> > If so, how would we determine what a validation code block was? One
> > option is to have a list of private instance methods (like
> > validate_values) that check the fields in question, but I am not sure if
> > having one function to declare it and one function to check it is ideal.
> > The names could be confusing because of their similarity. Using a
> > hashed set like that could possibly move the validation logic solely to
> > when valid? is called, rather than when the validation is first
> > declared. I like the idea and will try to think of some solutions.
> >
> > By the way, what are application level validations? Nitro application
> > or Og/Glue? I am not familiar at all with Nitro, because the project
> > I'm doing that got me interested in Og in the first place doesn't use
> > anything else.
> >
> > Brian B.
> >
> >
> > On Thu, 2005-12-15 at 23:20 -0800, Bryan Soto wrote:
> > > Interesting... I guess noone ever noticed since the code was eval'd on
> > > the first call made to #valid? in the previous implementation. The
> > > array was only iterated through when defining validate(). Now it's
> > > being iterated through on every call.
> > >
> > > Perhaps if, instead of an array, validations were stored in a hash
> > > with the key consisting of the validation type and field name, it
> > > would avoid the duplication and performance hit? It might make
> > > application level validations a bit more complicated, though I'm not
> > > sure if anyone actually uses them. Does anyone?
> > >
> > > On 12/15/05, Brian Bugh < brian at xsi-design.com> wrote:
> > > Ah, I see. The current release gem package does this as well,
> > > so it's a
> > > general issue with the way validations are handled. I'm
> > > innocent! ;)
> > >
> > > I've tested with extend_object and append_features methods and
> > > the
> > > on_included block, and I can't seem to find a reliable way to
> > > check if
> > > the file is being loaded/extended again. The problem is that
> > > when it is
> > > reloaded, the class is just reopened and declared the same way
> > > it was
> > > before.
> > >
> > > Any logic I can think of to add to validations for uniqueness
> > > checking
> > > will have a performance penalty in production, even though
> > > production
> > > doesn't have the reload issue.
> > >
> > > I will spend more time on this tomorrow to see if I can find
> > > a
> > > easy/quick solution for your upcoming release.
> > >
> > > Brian B.
> > >
> > >
> > > On Thu, 2005-12-15 at 13:24 -0800, Bryan Soto wrote:
> > > > Sorry if I wasn't clear. In debug mode, i.e. webrick, files
> > > are
> > > > automatically reloaded on change. I noticed after adding and
> > > removing a
> > > > field to test Mysql evolution that my validations had
> > > increased. Something
> > > > along the lines of:
> > > >
> > > > # user.rb
> > > > class User
> > > > property :username
> > > > property :password
> > > >
> > > > validate_unique :username
> > > > validate_value :password
> > > > end
> > > >
> > > > User.validations.size # => 2
> > > >
> > > > # touch user.rb
> > > >
> > > > User.validations.size # => 4
> > > >
> > > > assuming user.rb is a model class in a Nitro application.
> > > Basically, after
> > > > the touch is performed, the file is reloaded and the
> > > validations are added
> > > > anew to the already existing validations array (speculation
> > > on my part as to
> > > > your implementation) in the already existing User class.
> > > >
> > > > As I said, it's not that a big a deal. A stop and restart of
> > > the webrick
> > > > server clears it up. I just happended to notice twice as
> > > many error messages
> > > > as I expected from a form. Just make sure your production
> > > apps aren't in
> > > > debug mode.
> > > >
> > > > bryan
> > > >
> >
> >
> > _______________________________________________
> > Nitro-general mailing list
> > Nitro-general at rubyforge.org
> > http://rubyforge.org/mailman/listinfo/nitro-general
> >
>
>
> _______________________________________________
> Nitro-general mailing list
> Nitro-general at rubyforge.org
> http://rubyforge.org/mailman/listinfo/nitro-general
>
>
>
--
http://www.gmosx.com
http://www.navel.gr
http://www.nitrohq.com
More information about the Nitro-general
mailing list