How to safely upgrade Rails

How to safely upgrade Rails

Rails Upgrade Casual Talks at Crowd Works
https://cw-meetup.doorkeeper.jp/events/40728

08d5432a5bc31e6d9edec87b94cb1db1?s=128

Takashi Kokubun

March 28, 2016
Tweet

Transcript

  1. How to safely upgrade Rails Rails Upgrade Casual Talks @k0kubun

  2. ࣗݾ঺հ • Takashi Kokubun (@k0kubun) • ΫοΫύου ٕज़෦ ։ൃج൫άϧʔϓ •

    Rails 4.1 -> 4.2 ͷΞοϓάϨʔυΛ్த͔Β୲౰
  3. ࠓ೔࿩͢͜ͱ • CookpadͷRailsΞοϓάϨʔυͷྲྀΕ • ϦϦʔεલͷ4ஈ֊ͷಈ࡞֬ೝ • Cookpad͕ૺ۰ͨ͠Rails 4.2ͷόά

  4. Cookpadͷ RailsΞοϓάϨʔυͷྲྀΕ Rails 4.1 → 4.2 ͷྫ

  5. CIʹRails 4.2༻δϣϒΛ༻ҙ • ·ͣ͸ςετΛ௨͢ • @a_matsuda ͞Μ͕fail࢒Γ5ݸ·ͰݮΒͨ͠ͷΛҾ͖ܧ ͗ɺ࢒ΓΛ௨͢ͷΛ୲౰ • ϦϦʔε͢Δ·Ͱmaster͔Βrebase͠ଓ͚Δrails42ϒϥϯ

    ν͕ςετΛ௨Δঢ়ଶΛอͭͨΊɺCIʹδϣϒΛ༻ҙ͢Δ • CIαʔόʔͷϦιʔε͕ۭ͍͍ͯΔૣேʹ࣮ߦ͢Δ
  6. cherry-pick • σϓϩΠޙͷ໰୊ͷ੾Γ෼͚Λ༰қʹͨ͠ΓɺϨϏϡʔ ͷෛ୲ܰݮͷͨΊϓϧϦΛ෼ׂ͢Δ • 4.1, 4.2྆ํͰಈ͘मਖ਼͸ઌʹग़ͯ͠͠·͏ • ઌʹΞοϓάϨʔυͰ͖Δgem͸ઌʹ΍͓ͬͯ͘

  7. cherry-pick fail࢒Γ5ͷ࣌఺ 1308 additions 1087 deletions 650 additions 477 deletions

    Ϛʔδͨ͠ϓϧϦ ໿൒෼
  8. ඇޓ׵ͷҰ࣌త཈੍ • Rails 4.2ͷAuthenticity Tokenͷมߋ͸ϩʔϧόοΫͰ͖ ͳ͍ͷͰɺRails 4.1ͷڍಈʹϞϯΩʔύονͰݻఆ • Masked Authenticity

    Token ͰຖճϥϯμϜͳtokenΛ ฦ͢Α͏ʹͳΔͷͰɺޙํޓ׵ੑ͕ͳ͍ • Rails 4.2σϓϩΠޙམ͍͔ͪͭͯΒ͜ͷύονΛ֎ͨ͠
  9. ඇޓ׵ͷҰ࣌త཈੍ ActiveSupport.on_load(:action_controller) do module ActionController module RequestForgeryProtectionExtension def form_authenticity_token session[:_csrf_token]

    ||= SecureRandom.base64(32) end end Base.prepend RequestForgeryProtectionExtension end end • Masked Authenticity TokenͷมߋΛ཈੍͢Δύον
  10. ಈ࡞֬ೝ • ن໛͕େ͖͘ɺશͯͷӨڹൣғͷ೺Ѳ͕ࠔ೉ͳͷͰɺ • ؔ܎෦ॺ͕ಈ࡞֬ೝͰ͖ΔظؒΛ2िؒఔ౓ઃ͚Δ • ຊ൪ʹ͍ۙ؀ڥͰΤϥʔ͕ग़Δ͔֬ೝ͢Δ • ৄࡉ͸ޙͷεϥΠυͰ

  11. cookpad.com ͷϦϦʔε • લ೔໷͔ΒίʔυϑϦʔζ • ӨڹΛখ͘͢͞ΔͨΊɺޕલ7࣌ग़ࣾɾ8࣌σϓϩΠ • ͳΔ΂͘τϥϑΟοΫ͕௿͍࣌ؒଳʹσϓϩΠ͍ͨ͠ ͕ɺؔ܎ऀશһʹਂ໷ͷग़ࣾΛཁٻ͢Δ΄ͲͰ͸ͳ͍

  12. ෳ਺ϒϥϯνӡ༻ • ಉ͡ϦϙδτϦʹ cookpad.com ΛؚΉ8ͭͷΞϓϦ͕ಉډ ͍ͯ͠Δ͕ɺҰ౓ʹશ෦ϦϦʔε͠ͳ͍ • 8ͭͷΞϓϦ: ؅ཧը໘, όον,

    API, ϫʔΧʔ, ... • ໿1ि͔͚ؒͯஈ֊తʹσϓϩΠ͢Δ • શͯRails 4.2ʹҠߦ͢Δ·Ͱ͸Rails 4.1༻ͷrails41ϒϥϯν Λ࡞ΓmasterͷมߋΛόοΫϙʔτ͠ଓ͚Δ
  13. σϓϩΠޙͷ؂ࢹ • ҎԼͷ2ͭΛ؂ࢹ͢Δ • Sentry: Τϥʔ • ࣗࣾ੡ϞχλϦϯάπʔϧ: ϨεϙϯελΠϜ

  14. σϓϩΠޙͷ؂ࢹ ϨεϙϯελΠϜ Τϥʔ

  15. ΞοϓάϨʔυϑϩʔͷ·ͱΊ • ςετΛ௨͠CIʹδϣϒΛ༻ҙ͢Δ • ϓϧϦͷ෼ׂ΍ඇޓ׵ͷ཈੍ʹΑΓมߋͷཻ౓Λখ͘͢͞Δ • 2िؒಈ࡞֬ೝ • ෳ਺ͷΞϓϦΛ1ि͔͚ؒͯஈ֊తʹϦϦʔε͢Δ •

    σϓϩΠޙɺϨεϙϯελΠϜͱΤϥʔΛ؂ࢹ
  16. ϦϦʔεલͷ4ஈ֊ͷಈ࡞֬ೝ

  17. 1. ։ൃ༻ͷݕূ؀ڥͰͷ֬ೝ • ։ൃ༻ͷDBΛࢀর͢Δݕূ؀ڥʹRails 4.2ͷϒϥϯνΛ σϓϩΠ • ΞοϓάϨʔυؔ܎ͳ͘΋ͱ΋ͱ೚ҙͷϒϥϯνΛ೚ҙ ͷαϒυϝΠϯʹσϓϩΠͰ͖ΔΑ͏ʹͳ͍ͬͯΔ •

    ྫ: https://rails42.staging.ʙ/ • ͜ͷ؀ڥͰ֤෦ॺʹಈ࡞֬ೝΛґཔ
  18. 2. ຊ൪؀ڥͰͷखಈ֬ೝ • Rails 4.2༻ͷϒϥϯνΛσϓϩΠͨ͠ຊ൪؀ڥΛ༻ҙ • Webͷ৔߹ • ಛผͳΫοΩʔΛ࣋ͭ৔߹ͷΈͦͷ؀ڥʹϓϩΩγ͞Ε ΔΑ͏ʹͯ͠खಈͰಈ࡞֬ೝ

    • ϞόΠϧΞϓϦ༻APIͷ৔߹ • ಛผͳϦΫΤετϔομʔΛ࣋ͭ৔߹ͷΈϓϩΩγ
  19. 2. ຊ൪؀ڥͰͷखಈ֬ೝ *OUFSOFU "QBDIF SBJMT SBJMT ௨ৗͷΫοΩʔ foocookie=1 • Webͷ৔߹

    consoleͰద౰ʹ $.cookie('foocookie', 1) CSPXTFS
  20. 2. ຊ൪؀ڥͰͷखಈ֬ೝ • ϞόΠϧΞϓϦ༻APIͷ৔߹ *OUFSOFU "QBDIF SBJMT SBJMT .PCJMF "QQ

    NJUNQSPYZ ϦΫΤετϔομʹ X-Foo=1 Λ͚ͭΔ X-Foo=1 ී௨ͷϦΫΤετ
  21. 3. Kage • https://github.com/cookpad/kage • ͋ΔαʔόʔʹདྷͨϦΫΤετΛRails 4.2ΛσϓϩΠͨ͠΋ͷʹ΋ྲྀ ͠ɺDBͳͲ΁ͷॻ͖ࠐΈ͸཈ࢭ͢Δ • MySQLͳΒBLACKHOLEɺmemcached

    ͳͲ͸ִ཭͢Δ • Τϥʔͷ༗ແ΍ύϑΥʔϚϯεΛ֬ೝ͢Δ • tail -f production.log • nginxͷϨεϙϯελΠϜ΍unicornͷϦιʔε࢖༻ྔ
  22. 3. Kage *OUFSOFU "QBDIF SBJMT ,BHF SBJMT ಉ͡ϦΫΤετ Ϩεϙϯε͸ࣺͯΔ Ϣʔβʔʹฦ͢

  23. 4. Production Test • CI੒ޭޙࣗಈతʹσϓϩΠ͞ΕΔɺ΄΅ຊ൪ͷ؀ڥ • ΞοϓάϨʔυؔ܎ͳ͍ͭ͘Ͱ΋͜͜Ͱಈ࡞֬ೝΛ͔ͯ͠ ΒσϓϩΠ͢Δ

  24. Cookpad͕ૺ۰ͨ͠Rails 4.2ͷόά

  25. Encoding::UndefinedConversionError • ϚϧνόΠτจࣈྻ͔ͭ൒֯ͷ"%"ΛؚΉϑΝΠϧ໊ͷϑ ΝΠϧΛΞοϓϩʔυͨ͠ࡍʹग़ΔϨΞͳΤϥʔ • Rails 4.1 → 4.2 ΞοϓάϨʔυ࣌ʹ།Ұग़ͨΤϥʔ

    • ຊՈʹ @eagletmt ͕ϓϧϦΛ౤͛ɺ4.2.4ʹऔΓࠐ·Εͨ • https://github.com/rails/rails/pull/21131
  26. Encoding::UndefinedConversionError

  27. undefined method `unpack' for nil:NilClass • Rails 4.2.4ͱRuby 2.0.0ͷ૊Έ߹ΘͤͰͷΈൃੜ͢ΔΤϥʔ •

    Ruby 2.0.0ͩͱ ERB::Util.url_encode ಺ͷgsubͷϒϩο ΫͰ $& Λࢀর͢Δ͕ɺAS::SafeBuffer ͩͱಈ͔ͳ͍ • ຊՈʹ @k0kubun ͕ϓϧϦΛ౤͛ɺ4.2.5ʹऔΓࠐ·Εͨ • https://github.com/rails/rails/pull/21402
  28. undefined method `unpack' for nil:NilClass

  29. ·ͱΊ • Ұ౓ʹσϓϩΠ͞ΕΔมߋΛখ͘͢͞Δ • ͳΔ΂͘ଟ͘ͷखͰɺͳΔ΂͘ຊ൪ʹ͍ۙ؀ڥͰಈ࡞֬ೝ • ΫοΫύουͰૺ۰ͨ͠Rails 4.2ͷόά͸ຊՈͰमਖ਼ࡁ