浏览 10949 次
锁定老帖子 主题:Rails3学习笔记一,中秋假期
该帖已经被评为良好帖
|
|
---|---|
作者 | 正文 |
发表时间:2010-09-24
最后修改:2010-09-25
废话不说, 引用 Terminal=》ruby -v
ruby 1.8.7 (2009-06-12 patchlevel 174) [universal-darwin10.0] OK,符合Rails3的要求,更新Gems。。。。。 首先看看rails命令的帮助 rails -h,看看都有什么 引用 Usage:
rails new APP_PATH [options] -J, [--skip-prototype] # Skip Prototype files -T, [--skip-test-unit] # Skip Test::Unit files 额额,Prototype换成我更熟悉的Jquery,Test::Unit换成Rspec,好就这么办 引用 rails new Capricorn -TJ
mate . 代码生成完毕,看了一下public/javascripts/下面的controls.js,dragdrop.js,effects.js,prototype.js是没有的;同时test目录也是没有的。 第二件事情,处理Gemfile,这个比较好理解,就是Ruby的Maven gem 'unicorn' gem 'haml-rails' gem 'jquery-rails' group :development, :test do gem "rspec-rails", ">= 2.0.0.beta.22" gem 'autotest' gem 'rails3-generators' gem 'factory_girl_rails' gem 'webrat' end unicorn是类似Mongrel的一个东东,特点在于socket,以及kill -USR2 master_pid master的类似Nginx的启动方式让我很心仪。 haml-rails和jquery-rails是从rails3-generators分离出来的,针对Rails3和Haml以及Jquery的特方便集成。 rspec-rails就不用说了。 autotest会自动监视你的代码的改动,自动运行测试,所以你只要Command+t一个Terminal窗口就好。 rails3-generators的存在就是为了factory_girl_rails,后者是替换Rails3自带的fixtures的。 webrat也没什么好说的。 运行 引用 bundle install
配置依赖 安装rspec 引用 rails g rspec:install
{ create .rspec create spec create spec/spec_helper.rb create autotest create autotest/discover.rb } 安装Jquery 引用 rails g jquery:install
{ remove public/javascripts/controls.js remove public/javascripts/dragdrop.js remove public/javascripts/effects.js remove public/javascripts/prototype.js create public/javascripts/jquery.min.js create public/javascripts/jquery.js create public/javascripts/rails.js } 配置factory_girl,修改application.rb,添加 config.generators do |g| g.fixture_replacement :factory_girl, :dir => "spec/factories" end 修改rspec_helper.rb,替换 config.fixture_path = "#{::Rails.root}/spec/factories" 接下来,该干真格的了,先干用户登录模块 引用 rails g model User login:string name:string email:string crypted_password:string salt:string
查看输出结果为 引用 invoke active_record
create db/migrate/20100924033208_create_users.rb create app/models/user.rb invoke rspec create spec/models/user_spec.rb invoke factory_girl create spec/factories/users.rb 额额,从结果来看,Rspec和Factory_girl是配置OK的。 Java的TDD经验告诉我,先从user_spec.rb下手。额额,Ruby代码写起来比较不给力啊,千言万语不知从何说起,TMD先用JAVA经验往上套吧,再看看别人的代码是怎么写的,能抄就抄,活人不能让尿憋死,罗马也不是一天就能建起来的,慢慢来。 describe 'being created' do before do @user = nil @creating_user = lambda do @user = create_user end end it 'increments User#count' do @creating_user.should change(User, :count).by(1) end end protected def create_user(options = {}) u = User.new({ :login => 'PenG', :email => 'PenG@example.com', :password => 'peng82', :password_confirmation => 'peng82' }.merge(options)) u.save! if u.valid? u end 先这样,运行一下看看再说 引用 autotest
额额,找不到Users,哦,忘了rake db:migrate和rake db:test:prepare。连续两次Control+c中断autotest,再运行 引用 rake db:migrate
rake db:test:prepare autotest 哦了! 在做一些老俗套的事情 it 'requires login' do lambda do create_user(:login => nil).should_not be_valid end.should_not change(User, :count) end describe 'allows legitimate logins:' do ['123', '1234567890_234567890_234567890_234567890', 'hello.-_there@funnychar.com'].each do |login_str| it "'#{login_str}'" do lambda do u = create_user(:login => login_str) u.errors[:login].should be_empty end.should change(User, :count).by(1) end end end describe 'disallows illegitimate logins:' do ['12', '1234567890_234567890_234567890_234567890_', "tab\t", "newline\n", "Iñtërnâtiônàlizætiøn hasn't happened to ruby 1.8 yet", 'semicolon;', 'quote"', 'tick\'', 'backtick`', 'percent%', 'plus+', 'space '].each do |login_str| it "'#{login_str}'" do lambda do u = create_user(:login => login_str) u.errors[:login].should_not be_empty end.should_not change(User, :count) end end end it 'requires password' do lambda do u = create_user(:password => nil) u.should_not be_valid end.should_not change(User, :count) end it 'requires password confirmation' do lambda do u = create_user(:password_confirmation => nil) u.should_not be_valid end.should_not change(User, :count) end it 'requires email' do lambda do u = create_user(:email => nil) u.should_not be_valid end.should_not change(User, :count) end describe 'allows legitimate emails:' do ['foo@bar.com', 'foo@newskool-tld.museum', 'foo@twoletter-tld.de', 'foo@nonexistant-tld.qq', 'r@a.wk', '1234567890-234567890-234567890-234567890-234567890-234567890-234567890-234567890-234567890@gmail.com', 'hello.-_there@funnychar.com', 'uucp%addr@gmail.com', 'hello+routing-str@gmail.com', 'domain@can.haz.many.sub.doma.in'].each do |email_str| it "'#{email_str}'" do lambda do u = create_user(:email => email_str) u.errors[:email].should be_empty end.should change(User, :count).by(1) end end end describe 'disallows illegitimate emails' do ['!!@nobadchars.com', 'foo@no-rep-dots..com', 'foo@badtld.xxx', 'foo@toolongtld.abcdefg', 'Iñtërnâtiônàlizætiøn@hasnt.happened.to.email', 'need.domain.and.tld@de', "tab\t", "newline\n", 'r@.wk', '1234567890-234567890-234567890-234567890-234567890-234567890-234567890-234567890-234567890@gmail2.com', 'uucp!addr@gmail.com', 'semicolon;@gmail.com', 'quote"@gmail.com', 'tick\'@gmail.com', 'backtick`@gmail.com', 'space @gmail.com', 'bracket<@gmail.com', 'bracket>@gmail.com'].each do |email_str| it "'#{email_str}'" do lambda do u = create_user(:email => email_str) u.errors[:email].should_not be_empty end.should_not change(User, :count) end end end describe 'allows legitimate names:' do ['Andre The Giant (7\'4", 520 lb.) -- has a posse', '', '1234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890'].each do |name_str| it "'#{name_str}'" do lambda do u = create_user(:name => name_str) u.errors[:name].should be_empty end.should change(User, :count).by(1) end end end describe "disallows illegitimate names" do ["tab\t", "newline\n", '1234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890_234567890_'].each do |name_str| it "'#{name_str}'" do lambda do u = create_user(:name => name_str) u.errors[:name].should_not be_empty end.should_not change(User, :count) end end end 以上代码皆抄自于restful_authentication,修改的地方就是u.errors处的API在Rails3中有改动。Rails3会返回[],也就是说原来这里的判定为be_nil是不行的,基本上都要改。 上述代码和我以前写的Rspec代码有3个明显的优点我认为, def clean_user(options = {}) user = User.new({:name => 'Tom.Zhao', :email => 'Tom.Zhao@example.com', :password => 'Tom.Zhao'}.merge(options)) end it 'should require name, email password' do clean_user(:name => '').should_not be_valid clean_user(:email => '').should_not be_valid clean_user(:password => '').should_not be_valid end it 'has lengh 5 ~ 40 of password' do clean_user(:password => '1234').should_not be_valid clean_user(:password => '1234' * 10 + '1' ).should_not be_valid clean_user(:password => '12345').should be_valid clean_user(:password => '1234' * 10).should be_valid end 1:由lambda匿名函数执行验证测试,并且返回一个Proc对象直接验证是否save! 2:大量的条件验证,[].each do |name_str|的用法出来的结果更直观,同时代码可读性更高一些。 3:对于在model中的validates:format => {:with => RE_EMAIL_OK, :message => MSG_EMAIL_BAD},可以直接验证返回的错误message。 测试写好了,我们该给model添加东西了,Rails3推出了validates可以让我们的写法更性感,它可以使用的参数为 引用 * :acceptance => Boolean
* :confirmation => Boolean * :exclusion => { :in => Ennumerable } * :inclusion => { :in => Ennumerable } * :format => { :with => Regexp } * :length => { :minimum => Fixnum, maximum => Fixnum, } * :numericality => Boolean * :presence => Boolean * :uniqueness => Boolean 修改user.rb include ApplicationHelper validates :login, :presence => true, :uniqueness => { :case_sensitive => false }, :length => {:minimum => 3, :maximum => 40}, :format => {:with => RE_LOGIN_OK, :message => MSG_LOGIN_BAD} validates :email, :presence => true, :uniqueness => { :case_sensitive => false }, :length => {:minimum => 6, :maximum => 100}, :format => {:with => RE_EMAIL_OK, :message => MSG_EMAIL_BAD} validates :name, :length => {:maximum => 100}, :format => {:with => RE_NAME_OK, :message => MSG_NAME_BAD} validates :password, :presence => true validates :password_confirmation, :presence => true attr_accessor :password, :password_confirmation Rails3的新validates我十分喜欢,作用一目了然,并且十分性感。顺便说一下 :format => {:with => EmailRegexp}这里,针对常用的验证,比如Email,可以抽出来,在lib目录下新加一个email_validator.rb class EmailValidator < ActiveModel::EachValidator EmailAddress = begin qtext = '[^\\x0d\\x22\\x5c\\x80-\\xff]' dtext = '[^\\x0d\\x5b-\\x5d\\x80-\\xff]' atom = '[^\\x00-\\x20\\x22\\x28\\x29\\x2c\\x2e\\x3a-' + '\\x3c\\x3e\\x40\\x5b-\\x5d\\x7f-\\xff]+' quoted_pair = '\\x5c[\\x00-\\x7f]' domain_literal = "\\x5b(?:#{dtext}|#{quoted_pair})*\\x5d" quoted_string = "\\x22(?:#{qtext}|#{quoted_pair})*\\x22" domain_ref = atom sub_domain = "(?:#{domain_ref}|#{domain_literal})" word = "(?:#{atom}|#{quoted_string})" domain = "#{sub_domain}(?:\\x2e#{sub_domain})*" local_part = "#{word}(?:\\x2e#{word})*" addr_spec = "#{local_part}\\x40#{domain}" pattern = /\A#{addr_spec}\z/ end def validate_each(record, attribute, value) unless value =~ EmailAddress record.errors[attribute] << (options[:message] || "is not valid") end end end 那这里的代码可以直接这样写 validates :email, :presence => true, :length => {:minimum => 3, :maximum => 254}, :uniqueness => true, :email => true 回到目前代码中。 同时定义一些常量在ApplicationHelper中 unless defined? CONSTANTS_DEFINED RE_LOGIN_OK = /\A\w[\w\.\-_@]+\z/ MSG_LOGIN_BAD = "use only letters, numbers, and .-_@ please." RE_NAME_OK = /\A[^[:cntrl:]\\<>\/&]*\z/ MSG_NAME_BAD = "avoid non-printing characters and \\><&/ please." RE_EMAIL_NAME = '[\w\.%\+\-]+' RE_DOMAIN_HEAD = '(?:[A-Z0-9\-]+\.)+' RE_DOMAIN_TLD = '(?:[A-Z]{2}|com|org|net|gov|mil|biz|info|mobi|name|aero|jobs|museum)' RE_EMAIL_OK = /\A#{RE_EMAIL_NAME}@#{RE_DOMAIN_HEAD}#{RE_DOMAIN_TLD}\z/i MSG_EMAIL_BAD = "should look like an email address." CONSTANTS_DEFINED = 'yup' end 保存之后,看到autotest窗口测试全部通过,OK! 接下来处理密码加密,以及Email激活,是用Rails3自带的状态机,还是用state_machine呢?这是个问题。 10月1号搞定下一步。 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2010-09-25
使用jquery的话,RJS是个有点麻烦的问题,jrails长久不更新了,一点也不好用。
|
|
返回顶楼 | |
发表时间:2010-09-25
还没研究到那里,嘿嘿(目前我这只菜鸟飞的很慢)。不过从朋友那边反馈到的情况是,RJS口碑不太好,没必要完全ROR风格,Javascript原来怎么用,就怎么用就好。Unobtrusive JavaScript又不是ROR发明的。后面我会自己好好研究一下。
|
|
返回顶楼 | |
发表时间:2010-09-25
fanjunt 写道 还没研究到那里,嘿嘿(目前我这只菜鸟飞的很慢)。不过从朋友那边反馈到的情况是,RJS口碑不太好,没必要完全ROR风格,Javascript原来怎么用,就怎么用就好。Unobtrusive JavaScript又不是ROR发明的。后面我会自己好好研究一下。
嗯,从没用过rjs...还是直接写jquery好~ |
|
返回顶楼 | |
发表时间:2010-09-26
rails3的话直接抛弃rjs吧
|
|
返回顶楼 | |
发表时间:2010-10-01
楼主国庆期间还在努力的学习,精神可嘉。
|
|
返回顶楼 | |