• 使用 Rails 构建 API 实践 at January 19, 2016

    #126 楼 @night_7th 好建议,其实我 demo https://github.com/baya/build-an-api-rails-demo 里已经加了 skip_before_action :verify_authenticity_token, 我在文章里注明下

  • 使用 Rails 构建 API 实践 at January 05, 2016

    #123 楼 @brasbug 我自己跑的时候是没有问题的,你这个是不是传错了 user id, 你找一个数据库里实际存在的 user 去测试下

  • 大规模 I18n 实践 at January 05, 2016

    #3 楼 @xiaoronglv 我们的工作内容也差不多,客户那边有专职的翻译人员,我们程序员提供翻译的模版和翻译的 key

  • 大规模 I18n 实践 at January 05, 2016

    #1 楼 @peter 其实就是从 redis 里删除一个 key, 可以自己写个界面来做这个工作或者干脆忽略这个功能。

  • 使用 Rails 构建 API 实践 at January 05, 2016

    #121 楼 @gnodiah 嗯,rails 5 有这个功能,我当时写这个帖子也是顺应这个趋势,rails 即可以写 api 也可以写传统的 web 项目,没有必要使用 --api 选项将 rails 的功能限定在 api.

  • 使用 Rails 构建 API 实践 at January 05, 2016

    #119 楼 @thxagain 用不着的东西就去掉

  • 使用 Rails 构建 API 实践 at December 31, 2015

    #117 楼 @shin 图片和一般的 web form 表单提交文件差不多,没有特别的地方。你可以写一个空的方法接收客户端传过来的 image data, 在方法里打印 image data 的类型等细节,然后根据实际情况写些代码将图片写入到磁盘或者文件服务器。

  • 使用 Rails 构建 API 实践 at December 22, 2015

    我刚才试验了下没有问题:

    curl -i -X POST -d "user[email][email protected]&user[password]=123123" http://localhost:3000/api/v1/sessions
    HTTP/1.1 200 OK 
    X-Frame-Options: SAMEORIGIN
    X-Xss-Protection: 1; mode=block
    X-Content-Type-Options: nosniff
    Content-Type: application/json; charset=utf-8
    X-Ratelimit-Limit: 10000
    X-Ratelimit-Remaining: 9999
    Etag: W/"c0e0519f9c89a846b241a7b0dccd6369"
    Cache-Control: max-age=0, private, must-revalidate
    X-Request-Id: 22758305-9c86-496d-9223-a76c5828038a
    X-Runtime: 0.547032
    Vary: Origin
    Server: WEBrick/1.3.1 (Ruby/2.1.2/2014-05-08)
    Date: Tue, 22 Dec 2015 05:09:27 GMT
    Content-Length: 150
    Connection: Keep-Alive
    Set-Cookie: request_method=POST; path=/
    
    {"session":{"id":1,"name":"gg-user","admin":false,"token":"izrFiion7xEe2ccTj0v0mOcuNoT3FvpPqI31WLSCEBLvuz4xSr0d9+VI2+xVvAJjECIoju5MaoytEcg6Md773w=="}}%  
    

    你可以看下我写的 demo 代码: https://github.com/baya/build-an-api-rails-demo

  • 使用 Rails 构建 API 实践 at December 21, 2015

    #114 楼 @amrxjks 有时间我试验下

  • 使用 Rails 构建 API 实践 at December 07, 2015

    #112 楼 @yuze1995 嗯嗯,范例有点问题,我当时是用 curl 做的请求没有出现这种问题。这个和安全无关。

  • 使用 Rails 构建 API 实践 at December 07, 2015

    #110 楼 @yuze1995 看 109 楼 @hging 的回复

  • 使用 Rails 构建 API 实践 at December 06, 2015

    #107 楼 @yuze1995 你试下 /api/v1/users/1.json, 你少写了版本号:v1

  • 提供一个折衷的方法,需要在路由中加一个辅助方法:

    Rails.application.routes.draw do
    
      def point_to_latest(version = "v1", path)
        to = {
          "search" => "#{version}/issues#search"
        }[path]
    
        return "latest/#{path}", {to: to}
      end
    
     namespace :rest do
        namespace :api do
          namespace :v1 do
            get '/search', to: 'issues#search'
          end
    
          # 我希望latest自动指向v1版本下的controller处理
          # match 'latest/*path', to: redirect{|params, request| "/rest/api/v1/#{params[:path]}?#{request.query_string}"} , via: :get
          get *point_to_latest("search")
        end
      end
    
    end
    
  • 使用 Rails 构建 API 实践 at September 01, 2015

    #100 楼 @springwq 已经改过来了,谢谢

  • 中国版的 The Rails 4 Way?

  • #27 楼 @shawnyu 能从 12 台机器减到 3 台,这本身是一个了不起的成功,我看你们的技术迁移也是非常接地气的,做了很多的试验,不是脑袋一热,拍下脑门就做出的决定,这个是非常值得我们这些同行学习。

  • 我还是习惯性的想为 ruby 辩解几句,sidekiq_worker(重构前的 worker) = sidekiq + 暴走 rails app, go_worker(重构后的 worker) = go_workers + 精简的暴走业务代码,看到区别了没有,一个是拖家带口臃肿不堪,一个是轻装上阵如履平地。按楼主提供的信息:8 核 16G 机器 跑 sidekiq 的任务,我保守猜测一下,一台机器启动了 8 * 2 = 16 个 workers, 每个 worker 消耗 500M 内存 (我现在有一个中等规模的 rails 项目,每个 woker 平均消耗 400 M 内存,以暴走的规模来看应该比我们消耗的内存多些), 总共 8 G 内存,什么任务都没有跑就已经吃掉 8G 内存了,但这不是 ruby 的错,是 rails 的错。其实如果脱离 rails, 单纯用 ruby 来写这些后台业务代码,效果也会不错的。

  • 这么低调的炫耀妹子,其他公司可以学学

  • #98 楼 @lazybios 不错的建议,我等下看看,谢谢

  • mock 代码:

    module A
      class User
    
        def self.transaction(&block)
          puts "A::User transaction call #{block.call}"
        end
    
      end
    end
    
    
    module B
      class User
    
        def self.transaction(&block)
          puts "B::User transaction call #{block.call}"
        end
    
      end
    end
    
    
    
    module C
      class User
    
        def self.transaction(&block)
          puts "C::User transaction call #{block.call}"
        end
    
      end
    end
    
    
    module D
      class User
    
        def self.transaction(&block)
          puts "D::User transaction call #{block.call}"
        end
    
      end
    end
    
    

    解决代码:

    def tr(*args, &block)
      bl = block
      args.reverse.each {|arg|
       # 这里不能使用 bl = -> { arg.transaction(&bl)}, 否则 lambda 的闭包作用会导致 SystemStackError
        bl = create_tr_lambda(arg, &bl)
      }
      bl.call
    end
    
    def create_tr_lambda(arg, &block)
      -> {arg.transaction(&block)}
    end
    
    tr(A::User, B::User, C::User, D::User) do
      puts "begin transaction from D::user"
    end
    
    

    分析过程:

    inner_bl = -> {}
    d = -> {D::User.transaction(&inner_bl)}
    c = -> {C::User.transaction(&d)}
    b = -> {B::User.transaction(&c)}
    a = -> {A::User.transaction(&b)}
    
  • 汪汪汪 是几层意思,已经承认是小狗了?

  • 这楼层盖的,我还以为留了动作片的种子 😄

  • #47 楼 @fleuria 你说了个人体会,这点我是赞同的,关于测试这块的一些评价我也是出于自己的个人经验有感而发的,我其实有一段非常长的写测试的经历,我对写测试的熟练程度可能比这个坛子里大多数人都要多些,并且我现在仍然会对系统的一些比较重要,比较核心的地方写测试。你说的覆盖到好过没覆盖到, 差的测试好过没有测试 等等这些我认为是写测试的忌讳,写测试是一件很耗费精力的事情,这个精力既包括脑力,也包括体力,程序员的精力既是有限的,也是宝贵的,把程序员的这些宝贵精力消耗在差的测试上,或者是一些并不是很重要的代码的覆盖上岂不是一种严重浪费,当然如果你觉得自己精力好,或者觉得项目的每一个地方都很重要,都不能有任何闪失,你可以继续这样做。以我的个人经验做个小结:如果决定写测试,那务必就写出质量好的,能够用在刀刃上的测试代码,如果做不到,还不如前期认认真真思考,做好全面的设计,忘记重构,忘记以后再去改善代码质量等等之类将来的事情,并且索性大方点把测试的任务交给 QA 团队去做。

  • #93 楼 @idlesong :plus1: 我的 demo 用的是 Rails 4.2.0 版本,所以当时没有出现这个问题

  • #92 楼 @idlesong 我说话比较直接,你不要太介意,在技术论坛里交流,除了瞎扯淡,提供的信息越多越好,这样大家都节约时间,你提供的信息越多,步骤越详细,我们会越认为你是认真的,越会愿意花时间帮你 😄

  • #88 楼 @nuc093 , 我写这篇文章花费了很多精力,这比平时写代码繁琐太多了,不信你可以自己试试,这篇文章虽然介绍的都是非常基础的知识,但是为确保不出问题,每一步我都事无巨细反复测试过,并且我提供了详细的代码,我建议你,出了问题首先想想是不是自己的原因,即使不是自己的原因,如果你能自己解决,并且告诉作者解决方法,那么这才是对双方有益的事,以后别这样做了,给人的感觉很不好

  • #89 楼 @idlesong 并没有出错,这只是一个提醒日志:Can't verify CSRF token authenticity, 如果不喜欢这种日志,可以加上

    skip_before_filter :verify_authenticity_token

    class Api::V1::BaseController < ApplicationController
    
     + skip_before_filter :verify_authenticity_token
    
    end
    

    为什么遇到一点问题就不能自己 google 搜索一下?

  • #84 楼 @nuc093 提供下相关的代码,我这边测试了没有问题

  • #38 楼 @yue 你说的不错,写测试代码确实是一件好事,甚至可以说是一件政治正确的事情,但是好人也经常干坏事,写测试代码就如同一个经常干坏事的好人,虽然它的本意是想做些好事情,但是很多不好事情的事情确实是发生在测试代码中,我补充一些我的观点,下面这些场景以我为主角,

    1. 片面追求测试覆盖率,导致写了很多类似于 assert 1==1 之类的测试代码;

    2. 大量的使用 mock, stub 之类的东西 (很多时候为了解耦测试代码,又不得不用这些东西),虽然测试通过了,但是上线后,系统被残酷的线上环境虐成渣渣;

    3. 自认为自己写的测试代码很清晰,可以当作文档,然后就真的不写文档了,但是过一段时间后,发现读测试代码比读源码还难;

    4. 写了些测试代码后,盲目地自信,整天惦记着重构的事,当真的要重构时,却发现项目代码和测试代码要一块重构,每天改测试代码改的要死;

    5. 写了些测试代码后,盲目地自信,认为打造一个 自动化 (automatic), 反复进行 (regression tests) 的测试系统很简单,并且幻想这个自动化测试系统会很可靠,于是每次通过 CI 成功提交代码后,都会自欺欺人地说:妥妥的。然后第二天被老板骂的找不到北。 打造一个可靠的自动化测试系统,需要一个研发团队持续不断的努力,需要大量的工具,流程和文档,而不只是一些测试代码。

  • #35 楼 @emanon TDD 滥用,就像一个有点犯二的强迫症患者,每次出门都特意去检查房间的灯是否关了,当然家里没有人,灯是需要关闭的,但是这种检查应该是下意识的动作,不应该耗费大量的精力去特意检查,我们需要培养的是随手关灯的习惯,而不是这种变态的检查,退一步讲,即使哪天回到家,发现灯没有关,这也不是一件大不了的事情,无非是浪费了些电,减少了些灯泡的寿命。

    编写代码很多时候讲究的是一气呵成,TDD 那种写点代码,测试一下,写点代码,测试一下的节奏实在是像一群讨厌的苍蝇在你的耳朵边不停地嗡来嗡去,很痛苦的。

    我曾经参与过一个 rails 项目的开发,此项目的测试覆盖率达到了惊人的 99.99999%, 测试代码的规模和复杂程度已经远远超过项目本身了,有时候花了 10 分钟改个代码,却需要花一个小时甚至更长的时间写测试,更气人的是你还必须写测试。让人啼笑皆非的是有次我发现项目中有段代码没有用处,然后把它删除了,然后测试时一片红,后来我跟同事确认这段代码在项目中确实没有什么用,但是测试需要它,更恐怖的是这些测试代码是耦合的,所以为了测试通过,这段代码一直保留着。

    现在很多用 rails 的公司要求程序员 TDD,这实在是一个不明智的要求。