zakihayaメモ

RubyとRailsのことが中心

Capistranoを使う時はブランチ名をdeployにしてはいけない

アプリをデプロイしようとコマンドを打っても全くうまくいかない。 スペルミスも無いのになぜだろうと思ったら、ちゃんとエラーが出てた。

fatal: A branch named 'deploy' already exists.

どうやらCapistrano内部でdeployブランチを作って、それをサーバにデプロイしているっぽい。

街コンで成功するためにするべきたった1つの事

飯食いに外に出たら街コン参加者の大行列ができてる。まだ流行ってるんだな。
裏技をこっそりお教えするので、今後参加する方がいたらご参考に。
久しぶりのブログがこんなでいいのかわからないが。。。

街コンのシステム

男性2人または女性2人のペアで参加します。
自分が手伝った街コンでは店の前にスタッフがいて、男性と女性で4人になるように席を誘導していました。

問題点

ただ、これだと必ず自分の好みの人と話せる訳ではありません。せっかく高額の参加費を払っているのですから、彼氏/彼女候補になる方とお話したいですよね。

解決法

店内に入ってしまうとスタッフに誘導されてしまうのでしたら、店内に入らなければいいのです。具体的には、お店の入り口で待機して好みの人が来るのを待ち、キタ!と思ったら声をかけて4人グループになってしまうのです。こうすることで自分が興味ある人と話すことができました。

注意すべき事

ただし、注意しておかなければいけない事があります。店内が満席の場合です。これではせっかくゲットした人と話す場所がありません。そうならないように、あらかじめスタッフに席が空いているかどうか確認しておきましょう。スタッフが暇そうにしていたら、待っている間に何か話しておくとよいでしょう。

あとは連絡先を交換して、終了直前に「今日もう少し飲みませんか?」みたいなメールをする。これで成功率はグッと上がるはずです。

もう1つ気をつける事は、絶対に恥ずかしがってはいけません。みんな彼氏彼女を探しに来ているのですから、積極的に話しましょう。

では、ハッピー街コンライフを!

Macが来たのでイチから設定してみる(IME、キーボード)

続いてキー入力まわり。

Google日本語入力

Google日本語入力のインストール

一度使ってしまうとことえりには戻れないなあ。
ダウンロードしてインストール。
Google 日本語入力

ことえりを無効にする

ことえりは不要なので無効にする。
システム環境設定→言語とテキスト→入力ソース
下のほうにことえりがあるのでチェックを外す。
ついでにGoogle日本語入力も「ひらがな」「英数」以外はチェックを外してしまう。

KeyRemap4MacBook

インストール

USキーボードには「英数」と「かな」キーが無いので、左右のCommandキーを押したらIMEの切り替えをできるようにする。

ダウンロードはこちらから。
インストール完了後、再起動を求められる。
KeyRemap4MacBook - Software for OS X

設定

ツールバーに四角いアイコンが出るのでそれをクリック→Preferences
For Japaneseの中の「左右のコマンドキーを・・・」の中の、コマンドキーの動作を優先モードにチェック。
これで左Comanndが英数、右Comanndがかなの役割になる。
Command+何かのショートカットも普通に使える。


これでだいぶ使えるようになったー。

Macが来たのでイチから設定してみる(システム環境設定)

きましたよー新しいMacBookAir。

会社Macの設定をそのまま移行しようかとも思ったのだけど、
不要なものが多そうだったので整理しながら設定してみる。
木曜の夜までに設定完了したい、終わるかな。。。

とりあえず初日はシステム環境設定から。

Dock

Dock を自動的に隠す/表示 にチェック

カーソルを下に持っていくとDockが出たり入ったり

Mission Control

最新の使用状況に基づいて・・・のチェックをはずす

デスクトップの順番が勝手に入れ替わってしまうので自分は混乱しちゃう。

ホットコーナー

左下にLaunchpad を設定。4本指ジェスチャ苦手なので。。。

右下にスクリーンセーバーを開始する を設定。
これやっておくと地味に便利。
席立つ時はカーソルを右下に持っていくとPCがロックされるようになる。

省エネルギー

バッテリー電源使用時はディスプレイを少し・・・のチェックをはずす

いちいち変わるのが嫌。

キーボード

F1、F2など・・・にチェック

意外と忘れがちだけど重要。

修飾キー

Caps LockをCtrlキーに変更。
US配列だとAの左にCaps Lockがあるが、ここはCtrlにしたい。
Caps Lockは使わないのでCtrlキーはそのまま。

トラックパッド

ポイントとクリック

タップでクリックにチェック。
これ設定するまで何度間違えたことか。。。

アクセシビリティ

カーソルのサイズ

1番左と左から2番目の目盛りの中間くらいがちょうど良い気がする。

Hash#mapとHash#selectのブロック引数の違いでハマる

ブロック引数が1つのmapで作っていたソースをコピーしてselectをやろうとしたら
うまくいかなくて困った。

Hash#mapはブロック引数が1つの時と2つの時で挙動が違う

  • 引数が1つの時

 keyとvalueが配列に入ってくる

{a: 1, b: 2, c: 3}.map{|val1| puts "val1=#{val1.inspect}"}
val1=[:a, 1]
val1=[:b, 2]
val1=[:c, 3]
=> [nil, nil, nil]
  • 引数が2つの時

 1つ目の引数にkey、2つ目の引数にvalueが入ってくる

{a: 1, b: 2, c: 3}.map{|val1, val2| puts "val1=#{val1.inspect} val2=#{val2.inspect}"}
val1=:a val2=1
val1=:b val2=2
val1=:c val2=3
=> [nil, nil, nil]

Hash#selectはブロック引数が1つの時も2つの時も同じ挙動

 1つ目の引数にkey、2つ目の引数にvalueが入ってくる

  • 引数が1つの時
{a: 1, b: 2, c: 3}.select{|val1| puts "val1=#{val1.inspect}"}
val1=:a
val1=:b
val1=:c
=> {}
  • 引数が2つの時
pry(main)> {a: 1, b: 2, c: 3}.select{|val1, val2| puts "val1=#{val1.inspect} val2=#{val2.inspect}"}
val1=:a val2=1
val1=:b val2=2
val1=:c val2=3
=> {}

AASMのReadmeを日本語訳してみた

AASMはRubyのクラスにステートマシンパターンを追加できるライブラリです。
業務で使うことがあったので訳してみました。

初の試みなので、おかしい点などがあればばしばし指摘してください。

元ページ
aasm/aasm · GitHub

AASM - Rubyのステートマシン

このパッケージにはRubyのクラスに有限なステートマシンを追加するライブラリであるAASMが含まれています。

AASMはacts_as_state_machineプラグインとして産声をあげましたが、ActiveRecord以外をターゲットにした汎用的なライブラリへと進化してきました。
現在はActiveRecordとMongoidへの接続を提供していますが、それらを親クラスに持たないどんなRubyのクラスへも適用することができます。

使用方法

AASMのモジュールをincludeするのと同じくらい簡単にステートマシンを追加し、stateeventおよびそれらの間のtransitionsを設定することができます。

class Job
  include AASM

  aasm do
    state :sleeping, :initial => true
    state :running
    state :cleaning

    event :run do
      transitions :from => :sleeping, :to => :running
    end

    event :clean do
      transitions :from => :running, :to => :cleaning
    end

    event :sleep do
      transitions :from => [:running, :cleaning], :to => :sleeping
    end
  end

end

このコードは Job クラスのインスタンスのpublic methodsの組を提供しています。

job = Job.new
job.sleeping? # => true
job.may_run?  # => true
job.run
job.running?  # => true
job.sleeping? # => false
job.may_run?  # => false
job.run       # => raises AASM::InvalidTransition

例外を発生させずに true と false を返り値として使用する場合は下のコードのようにwhiny_transitionsにfalseを設定したハッシュを渡します。

class Job
  ...
  aasm :whiny_transitions => false do
    ...
  end
end

job.running?  # => true
job.may_run?  # => false
job.run       # => false
コールバック

コールバックを定義すると、ある状態に遷移した時などの特定の条件を満たした場合に呼び出されます。

class Job
  include AASM

  aasm do
    state :sleeping, :initial => true, :before_enter => :do_something
    state :running

    event :run, :after => :notify_somebody do
      transitions :from => :sleeping, :to => :running, :on_transition => Proc.new {|obj, *args| obj.set_process(*args) }
    end

    event :sleep do
      after do
        ...
      end
      error do |e|
        ...
      end
      transitions :from => :running, :to => :sleeping
    end
  end

  def set_process(name)
    ...
  end

  def do_something
    ...
  end

  def notify_somebody
    ...
  end

end

このケースでは do_something は状態が sleeping になる前に呼ばれます。
一方で、notify_somebody は run イベントの遷移( sleeping から running )が終了した後に呼ばれます。

使用できるコールバックと呼び出される順序は下の通りです。

  event:before
    previous_state:before_exit
      new_state:before_enter
        ...update state...
      previous_state:after_exit
    new_state:after_enter
  event:after

下のようにしてeventにパラメータを渡すこともできます。

  job = Job.new
  job.run(:running, :defragmentation)

このケースでは、 set_process は :defagmentation を引数として呼び出されます。

イベント実行中に例外が発生した場合には、その例外は捕捉され :error コールバックに渡されます。その中で処理するか、上位のクラスに伝搬することができます。

ガード条件

ある条件のもとでのみ許可したい状態遷移を実現するために、状態遷移ごとにガード条件を設けることができます。ガード条件は、実際に遷移が発生する前に判定されます。ガード条件がfalseを返した場合は状態遷移が拒否されます。(AASM::InvalidTransition が発生するか、falseが返ります)

class Job
  include AASM

  aasm do
    state :sleeping, :initial => true
    state :running
    state :cleaning

    event :run do
      transitions :from => :sleeping, :to => :running
    end

    event :clean do
      transitions :from => :running, :to => :cleaning
    end

    event :sleep do
      transitions :from => :running, :to => :sleeping, :guard => :cleaning_needed?
    end
  end

  def cleaning_needed?
    false
  end

end

job = Job.new
job.run
job.may_sleep?  # => false
job.sleep       # => raises AASM::InvalidTransition
ActiveRecord

AASMはActiveRecordをサポートしており、データベース内のオブジェクトの状態を自動的に持続できます。

class Job < ActiveRecord::Base
  include AASM

  aasm do # default column: aasm_state
    state :sleeping, :initial => true
    state :running

    event :run do
      transitions :from => :sleeping, :to => :running
    end

    event :sleep do
      transitions :from => :running, :to => :sleeping
    end
  end

end

自動保存するか、保存しないままにしておくか選択することができます。

job = Job.new
job.run   # not saved
job.run!  # saved

保存する場合には Job クラスの全てのバリデーションが実行されます。
バリデーションを実行せずに状態を保存するのを明記したい場合は、簡単に実装できます。(それによって異常な状態が保存されてしまうかもしれません)

class Job < ActiveRecord::Base
  include AASM

  aasm :skip_validation_on_save => true do
    state :sleeping, :initial => true
    state :running

    event :run do
      transitions :from => :sleeping, :to => :running
    end

    event :sleep do
      transitions :from => :running, :to => :sleeping
    end
  end

end
スコープの自動生成

AASMはモデルの各stateに対して自動でスコープを作成します。

class Job < ActiveRecord::Base
  include AASM

  aasm do
    state :sleeping, :initial => true
    state :running
    state :cleaning
  end

  def sleeping
    "This method name is in already use"
  end
end
class JobsController < ApplicationController
  def index
    @running_jobs = jobs.running
    @recent_cleaning_jobs = jobs.cleaning.where('created_at >=  ?', 3.days.ago)

    # @sleeping_jobs = jobs.sleeping   #=> "This method name is in already use"
  end
end
トランザクションのサポート

バージョン3.0.13からActiveRecordトランザクションをサポートしています。コールバックや状態遷移が失敗するたびにデータベースへの変更内容はロールバックされます。

カラム名マイグレーション

デフォルトでは aasm_state に状態を保存します。下のように :column を使用すると、好きな列名に状態を保存できます。

class Job < ActiveRecord::Base
  include AASM

  aasm :column => 'my_state' do
    ...
  end

end

状態を保存するカラムを必ずマイグレーションに追加してください。(列の型はstringです)

class AddJobState < ActiveRecord::Migration
  def self.up
    add_column :jobs, :aasm_state, :string
  end

  def self.down
    remove_column :job, :aasm_state
  end
end