RubyKaigi 2011 メモ (2 日目)

RubyKaigi 2011 のメモ、2 日目です。rubykaigi.org に録画があることに気づいたので、リンクをつけてます。

安全なプログラムのつくりかた

安全なプログラムの作り方 | 日本Ruby会議2011(7月16日〜18日)

  • 西山 和広
  • 1995 頃、Perl / CGI で BBS 作成

    • 入力の HTML エスケープ、フィルタリング
    • onclick、javascript: の普及で危険に
  • 対策

    • 入力チェック
    • 出力はエスケープ
    • 環境の変化に注意
  • javascript URL

    • http / https へのリンクのみ許可
  • GET は冪等 (副作用なし)

    • js / form なしでアクセスさせられるため
    • GET で削除するようにしてたらクローラに削除された例も
  • /tmp を避ける

    • tmp 直下危険
    • 固定のファイル名は特に危険
    • symlink attack
    • Windows では /tmp ないし
    • tmpdir tempfile つかう
    • rails なら Rails.root + "tmp" でも
  • パーミッションは最小限に。

    • tmp 直下にソケット作って誰でもアクセスできる状態になっていた例
    • umask でデフォルトを最小限のパーミッションに
    • コードの所有者と、アップロードファイルなどの所有者を変えて、権限を設定する
    • 脆弱性があった場合に、コードの改変を変えられる可能性がある
  • 正規表現によるチェック

    • 予期しないものをスルーしないように
    • \w より [A-Za-z0-9] のほうが明確
    • [[:alnum]] でも
  • 任意のユーザー入力から正規表現を生成するのは危険

    • パターンによっては DoS 可能
  • コンソールへ任意の出力を許すのは危険。

  • コマンドライン処理でのエスケープ

  1. コードとしてのエスケープ
  2. シェルが処理するエスケープ
  3. 起動するプログラムが処理するエスケープ
  • 複数引数の system つかう
  • ファイル名に空白があっても良いか、ファイル名が - から始まってもよいか '"*\0 などが入っていても良いか
  • シェルによる違い
    • foo="aaa bbb"
    • some foo
    • だとシェルによって aaa と bbb だったり、aaa bbb だったり。
    • ARGV で確認

jpmobileのベストプラクティス

jpmobileのベストプラクティス | 日本Ruby会議2011(7月16日〜18日)

小川 伸一郎

  • https://github.com/jpmobile/jpmobile
  • らくらく連絡網

    • RoR + jpmobile
    • MySQL / TokyoTyrant / memcached
    • Apache/ nginx
  • emoji / kanji 変換

    • view を utf8 で書くとキャリアごとに変換して返す
    • docomo なら utf-8 -> sjis
    • リクエストもそれぞれの文字コードから utf8 にする
    • rack ミドルウェアで実現
      • mobile_carrier params_filter
    • Rails.application.config.jpmobile.mobile_filter
      • を initializer に書く
    • session id
    • a なら url 埋め込み
    • form なら hidden に埋め込み
    • cookie が使えないときのみ
  • view selecter

    • 規約にそってファイルを探す。
    • index_mobile_docomo.html.erb みたいな
    • controller で include Jpmobile::ViewSelector
    • disable_mobile_view! で探索を拒否することも
    • layout / partial も対応
  • japanese mail

    • body, subject は iso2022jp
    • subject は base64 エンコード
    • ヘッダは 76 文字 / 行である必要
    • エンコード後に折り返すと復元に失敗する場合あり
    • エンコード前に折り返し
  • emoticon

    • docomo: sjis
    • au: jis
    • sb: utf8
    • Unicode の私用領域に独自のコードでマッピング
  • Jpmobile::Mail::Base

    • メールアドレスによって文字コード切り替え
  • Testing

    • functional test
    • template
    • request.mobile?
    • assert_template (>1.0.0.7pre7)
    • charset
      • rack を通過しないので utf-8
      • integration test では変換される
    • unit test
    • mailer
      • mail オブジェクトの段階では utf-8
      • デリバリー後、@emails.first.to_s なら変換後
  • known issue

    • 文字コード変換に非可逆のケース
    • link_to に utf8 文字列を渡す場合は、そのままだと、docomo からのリクエストに utf8 文字が含まれることになってしまうためエラーや文字化け
    • メールで charset がわからない場合、iso1022jp に決めうちなどの対策をとらないとエンコーディングエラー
  • 質疑

    • rfc違反メールにも対応
    • unicode 絵文字
    • 1.8 では扱えないので、1.8 対応の必要がなくなれば対応したい。

Writing Friendly Libraries

Writing Friendly Libraries | 日本Ruby会議2011(7月16日〜18日)

参照: Friendly Ruby Objects

  • @drbrain

    • Segment 7
    • 90 unique gems
    • Serious lib (works)
    • Joke lib
  • Conventions

    • ほかのライブラリの規約に従う
    • LibraryName::Extention
    • bin/executable
  • Version

    • major.minor.revision
    • major: 非互換変更
    • minor: 新機能
    • revision: バグフィックス
  • 使いやすく

    • 実際に使う人が使いやすく
    • ruby がどうやってるか参考にする
  • Printable

    • to_s: 人間が読む用
    • inspect: デバッグ用
    • pretty_print: 巨大な構造を表現
  • Comparable

    • ==
    • <=> と Comparable
    • ==** と~ をマッチ用に
  • Hashable

    • hash と eql?
    • Array unique
    • Array deferable
    • each と Enumerable
  • Enumerator

    • enum_for と Enumerable
  • Chanable

    • enum.map.with_index ...
    • return enum_for methodunless block_given?
  • Exceptions

    • Common subclass (ArgmentError とか)を使う
    • なぜ例外が起こったのか伝える
    • 例外オブジェクトに例外に関係のあるデータをくっつける
    • (ActiveRecord::RecordInvalid なら record メソッドで原因となったオブジェクトが得られる)
  • initialize_copy

    • dup や clone から作られる
    • deep copy
    • 共有状態の管理
  • Marshal

    • compact で fast に
    • ガイドライン
    • Arrray か ハッシュで
    • marshal_dump は better
    • VERSION を必ずつける
      • 互換性
      • 新機能追加しやすい
      • 古いデータをこわさない
  • メンテしやすさ

    • 引き継ぎのためにも
    • do one thing
    • 書きやすい
    • 読みやすい
    • 再利用しやすさを最大化
  • Release note

    • important changes
    • new features
    • bug fixes
    • Change log とは異なる、機能、変更ベースで
  • テストせよ

    • testcase
    • abstract test case
    • 実装
  • bin/executable は最小限に

    • 実際の処理は lib 下に集約
  • 後方互換

    • api と実装をわける
    • api レイヤーで互換性を保持する
    • less api class better : api に関わるクラスを少なくしよう
  • C Extentsion

    • C は難しくリファクタリングしにくい
    • できるだけ ruby で書く
  • Documentation

    • API を書く
    • 内部実装は隠す
    • example をつけよう
  • Extensibility

    • Hooks
    • callback のしくみを入れる (ActiveRecord.before_save みたいな)
    • subclass を作って override method (ActiveRecord#before_save みたいな)
    • Plugins
    • hooks の登録
    • Gem.find_files を使って load する
  • Release

    • README
    • description
    • bugtracker
    • source repository
    • url
    • Release notes
    • 機能の変化、非互換姓
    • Automation
    • test
    • manifest
    • gem create / upload
    • tag release
    • update doc
    • use libraries
    • 自動化しよう
    • コピペするな
    • Hoe というライブラリ
    • https://github.com/seattlerb/hoe
    • rake release VERSION=x.y.z で全部チェック
    • プラグインもあるし設定も DRY
    • git / isolate (bundler) / minitest / email などのプラグインあり
  • 質疑

    • news と chage log が違うのになぜ news をすすめる?
    • changelog は多すぎる revert もあるし
    • news はユーザ向け、changelog は (ライブラリ自体の) 開発者むけ
  • C はどういうときに使う?

    • C library のラッパか、高速処理のため。前者をよくかく。
  • ユーザーからフィードバックを得るための tips があれば

    • prerelease 版という手もあるけど使う人すくない
    • bug tracker を使いやすくする
    • 自分が、じゃなく、ユーザーが。
    • bug tracker だけでなく ML を作るのもよい
    • rubyforge より github のが好き
    • github issues は使えるようになった
  • ライブラリが使うリソースはどこに置くべきか

    • rubygems に data_dir というメソッドがあるのでそれを使う
    • ふつう shared だけど記憶あいまい

Use rails_best_practices to refactor your rails codes

Use rails_best_practices to refactor your rails codes | 日本Ruby会議2011(7月16日〜18日)

  • @flyerhzm/ Richard Huang

  • RailsConf in Shang-hai で @ihower が Rails best practice という発表

    • チェック、実践が大変
    • それを簡単にする gem を作成、全部ではない
    • code checker が 28 人いる
  • rails-bestpractices.comでベストプラクティスを共有している

    • 70 practices
    • gem document
    • gem blog
  • 使いかた

    • gem install rails_best_practices
    • cd rails_project
    • rails_best_practices
    • plain でも html でも出力
    • html は解決法への url つき
    • 該当箇所をエディタで開ける
  • なぜ使うのか

    • 美しいコードを書くため
    • チームでの開発のため
    • コード規約
    • コードレビューの一部を自動化でき、本質だけに言及できる
  • 解析ツールについて

    • java には checkstyle
    • ruby には saikuro / flog / flay / reek / roodi などがある
    • この gem は rails 開発チームに特価している
  • How works

    • 行末の空白などの lixical チェック
    • sexp (symbol expression) に変換して、モデル名や関連のチェック
    • ベストプラクティスのチェック
    • sexp は ruby_parser で作る (rails_best_practice blog 内 play with sexp)
  • 設定

    • rails_best_practices -g
    • config/rails_vest_practices.yml がつくられるので、チェックしないプラクティスをコメントすればよい。
  • 拡張

    • github の wiki にチュートリアルつけてる
  • 質疑

    • プロジェクトの一部に対して、テストの内容を限定することはできるか
    • パターンの除外はコマンドでできるけど、特定のディレクトリとかは未実装
    • ruby のバージョンが変わったときにパーサが対応できるか
    • たぶん。ripper 使うかも。

BDD style Unit Testing

BDD style Unit Testing | 日本Ruby会議2011(7月16日〜18日)

  • @ihower

  • テストの種類

    • unit test: コードは正しいか
    • customer test (acceptance test) : 正しいソフトウェアか
  • テストの役割

    • verification
    • check regression (downgrade を防ぐ)
    • api design
    • documentation
  • BDD の印象

    • 仕様書のよう、読みやすい
  • フレームワーク

    • RSpec
    • Minitest::Spec
  • 記法

    • description Order do # クラス
    • description "#amount" do ... # インスタンスメソッド
    • description ".size" do ... # クラスメソッド
  • https://github.com/citrusbyte/context

    • test/unit で context 使う
    • matches でマッチャも使える
  • minitest/pride

    • 出力をかわいくする
  • minitest/turn

    • 出力を読みやすくする
  • BDD style caveat (注意点)

    • too magic
    • 高度な syntax で理解しづらい場合が
    • its(:status) { should == "New" } みたいな記法
    • let は流れを崩すので可読性がおちる
    • DSL
    • マッチャによっては冗長
    • 深いネスト
    • 深いネストはよくない
    • どの before が適用されるかわかりにくい
    • Mock が多すぎるとよくない
    • 遅い
    • test/unit に比べて遅い
    • とくに RSpec
    • ministest/spec は test/unit なみ
    • でもプロダクションコードの速さのほうが問題になるよね

5 years know-how of RSpec driven Rails app. development.

5 years know-how of RSpec driven Rails app. development. | 日本Ruby会議2011(7月16日〜18日)

  • @moro

    • 英和システムマネジメント
    • Rails レシピブック
    • 達人出版界
    • はじめる! Cucumber
  • コンテキストをつくるのがむつかしい

    • コンテキスト構築までのテクニック
  • モデルのテスト

    • Skinny controllers, Fat models
    • ほかは Cucumber で
  • データの用意がたいへん!

    • ex. 塾の実習参加 app
    • events has many cources, has many lessons, has many rooms and periods
    • students has many registrations
    • lessons has many registrations
    • Student#subscribe(cource) でコース全部履修
    • Student#register!(lesson_2_4) で一部別のコマに変えれる
    • これだけでもいくつもデータを用意しないといけない
  • データの種類

    • マスターデータ
    • ほとんど追加更新されない
    • 依存少ない
    • UI を scaffold で納品できるような
    • 主たるユーザ自身が変更しない
    • リソースデータ
    • 運用時、主に追加更新されるもの
    • ユーザによって更新される
    • イベントデータ
    • リレーション
    • has_many :through => に入りそうなもの
  • ストラテジー

    • fixture
    • 速い
    • メンテ性低い、柔軟性低い
    • マスターデータ向き
    • fixture_replacement
    • fabrication / factory_girl
    • ひな形からオブジェクトを作る
    • 使い方が難しい
    • 遅い
    • リソースデータ向き
    • before / setup
    • 割と速い
    • 記述が分散する
    • イベントデータ向き
    • これらを全部組み合わせて使うといい
  • DRY

    • fixture_rep や before とかでは同じようなことを何回も書くことになる。
    • context を share する
      • 適切な名前をつける
        • let(:answer) { 42 }
        • answer.should == 42
        • 名前をつけてしまえば、どこ由来 (fixture, fixture_replacement, before) だろうが OK
      • 状況に名前をつける
        • shared_context: let や context をシェアする
        • shared_context "生徒があるコースを履修している" do
          • let ...
          • before ...
        • include_context で使う
        • 「いつものあのセット」として使える。そこから状況ごとに変更できる。
      - 宣伝
    • http://bit.ly/esm-hiring-rubyists
    • rubyworldconf にでます

Efficient JavaScript integration testing with Ruby and V8 engine.

Efficient JavaScript integration testing with Ruby and V8 engine. | 日本Ruby会議2011(7月16日〜18日)

  • @nu7hatch

    • chris kowalik
  • JavaScript のテスト

    • selenium では時間がかかりすぎる。
    • ciサーバだと設定面倒
  • selenium / watir / phantom

    • 超おそい
  • ピュア javascript

    • Jasmine とか
    • おそい!
  • ヘッドレスブラウザ

    • HtmlUnit (Java)
    • Zombie (Node.js)
    • EnvJS
    • Rubyist には苦痛
  • 速いのがほしい!

    • js サポート
    • フレンドリな api
    • ポータブル
  • ruby 用 v8 拡張 + browser 実装

  • scaffold

    • Nokogiri で DOM パース
    • HTTPクライアントとして RestClient / CURB
    • js は Mustang
  • mustang : v8 in ruby

  • Mike

    • https://github.com/nu7hatch/mike
    • LibXML2 / LibCURL / LibV8 で作成 (みんな C++)
    • htmlunit / webkit / node.js, zombie に影響されてる
      • 1. 複数ウィンドウ対応
      • 2. frame サポート
      • 3. ユーザの操作 click_link など
      • 4. js 実行
      • 5. alert /confirm のモック
      • 6. api きれい!
      - 以下はまだ
    • イベントハンドリング
    • XmlHttpRequest
    • Web Socket
    • Ruby 拡張

Net::HTTP

Advancing Net::HTTP | 日本Ruby会議2011(7月16日〜18日)

  • @wycats

    • yehudakatz.com
    • Net::HTTP.start do |http| http.get do |chunk| end # レスポンス解放 # keep alive できる http.get do |chunk| end # レスポンス解放 end # ソケット解放
  • (途中から全然理解できませんでした・・・。並列化とか Reactor とか言ってた気がする。)

Method Shelters : Classboxes でも Refinements でもない別のやり方

Method Shelters : Classboxes でも Refinements でもない別のやり方 | 日本Ruby会議2011(7月16日〜18日)

  • @flexfrank
  • オープンクラスでメソッドかぶっちゃったりする問題

    • あるライブラリがメソッド追加 -> 別のライブラリがメソッド追加で上書きされちゃう
    • 別プロセスにして druby でなんとか解決するとか
    • mathn が Integer#/ をrational にしちゃうのでつらい
  • これまでの解決案

    • selector namespaces (smalltalk)
    • refinements
    • class ... のかわりに refine ... として定義し、using ... で使う
    • lexical スコープの中のみ
    • local rebinding はできない
    • classbox
    • matz 日記参照
    • import したクラスに追加などができる。
    • 同じ名前でその scope でだけ有効なサブクラスをつくる感じ。
    • A と、Aを書き換えたクラスを import する B、の両方を import すると B からみた A は改変されてないものになる。
  • method shelter

    • exposed chamber
    • public api 用
    • 呼べるし上書き
    • hidden chamber
    • private 用
    • 呼べない上書きできない

CRubyのロックデザインの解説および改善案について

CRubyのロックデザインの解説および改善案について | 日本Ruby会議2011(7月16日〜18日)

  • 小崎資広
  • (MacBook の電池が切れてしまったため、メモなし。かつ、あまり理解できてなかった。マルチコア環境では、複数スレッドのうち、1 つのスレッドがほとんど処理されない場合があり、Ruby 1.9.3 ではこの問題を解決したという話だったと思う。)

(Lightning Talk 1 は聴けませんでした)