LoginSignup
44
38

More than 5 years have passed since last update.

memcachedを利用したsession管理

Last updated at Posted at 2014-07-03

今更ながら、複数台サーバーに対応させるためsession管理をmemcachedを使って外部化したいと思います。

Require

  • rails 4
  • unicorn
  • memcached
  • osx

なんでmemcached

以前はredis-storeを使ってみたのです。

レプリもできるし、複雑な型も扱えるからredisがいいなーと思っているので幸せが待っている臭いがします。

が、最近更新滞ってるし、、、っていう後ろ向きな理由でdalli + memcachedです。

Memcache vs. Redis?

Install memcached and setup launchclt

とりあえず入れる

$ brew install memcached
memcached: stable 1.4.20 (bottled)
http://memcached.org/
Conflicts with: mysql-cluster
/opt/boxen/homebrew/Cellar/memcached/1.4.20 (10 files, 184K) *
  Built from source
From: https://github.com/Homebrew/homebrew/commits/master/Library/Formula/memcached.rb
==> Dependencies
Required: libevent ✔
==> Options
--enable-sasl
        Enable SASL support -- disables ASCII protocol!
--enable-sasl-pwdb
        Enable SASL with memcached's own plain text password db support -- disables ASCII protocol!
==> Caveats
To have launchd start memcached at login:
    ln -sfv /opt/boxen/homebrew/opt/memcached/*.plist ~/Library/LaunchAgents
Then to load memcached now:
    launchctl load ~/Library/LaunchAgents/homebrew.mxc

書いてある通りlaunchdCtlで自動起動設定

$ ln -sfv /opt/boxen/homebrew/opt/memcached/*.plist ~/Library/LaunchAgents
$ launchctl load ~/Library/LaunchAgents/homebrew.mxcl.memcached.plist

確認

# プロセス
$  ps axu | ag memcached
foo      84598   0.0  0.0  2464188    380   ??  S     9:16PM   0:00.06 /opt/boxen/homebrew/opt/memcached/bin/memcached -l localhost

# 繋げる
$ telnet localhost 11211
stats
...

ok

rails側に設定

memcache clientはdalliを利用します

$ vim Gemfile
gem 'dalli'

$ bundle

とりあえずdevelopモードで動くようにします。

cacheとsession設定をdalli経由に変更

$ vim config/environment/development.rb

AppName::Application.configure do
  ...
  config.cache_store = :dalli_store
  ...

$ vim config/initialize/session_store.rb
FooRails::Application.config.session_store ActionDispatch::Session::CacheStore, key: '_foo_session', expire_after: 1.month

consoleでcacheテスト

$ rails c
pry> Rails.cache.write 'foo', 'bar'
Cache write: foo
Dalli::Server#connect 127.0.0.1:11211
=> 144115188075855872

pry> Rails.cache.read 'foo'
Cache read: foo
=> "bar"

ok

deploy後に再接続

dalli 2.0.4から再接続は不要です
https://github.com/petergoldstein/dalli/issues/208

unicornのafter fork時に、memcachedとのコネクションを張り直します。

after_fork do |server,worker|
  ...
  if defined?(ActiveSupport::Cache::DalliStore) && Rails.cache.is_a?(ActiveSupport::Cache::DalliStore)
    Rails.cache.reset
    ObjectSpace.each_object(ActionDispatch::Session::DalliStore) { |obj| obj.reset }
  end

環境変数の外だし

最終的にはElasticCacheへの接続したい物の、VM内での構築試験するためにわざわざEC2経由するとかしたくないので、dotenv gemを利用して設定を外部化します。

.evn設定

$ vim .env
# nil is connecting to local memcached
CACHE_STORE=nil

環境変数引っ張る様に変更

# developから外して
$ vim config/environment/development.rb

- AppName::Application.configure do
-   ...
-   config.cache_store = :dalli_store, ENV['CACHE_STORE']
-   ...

# productionのみ追加
$ vim config/environment/production.rb

AppName::Application.configure do
  ...
  config.cache_store = :dalli_store, ENV['CACHE_STORE']

こんな感じで。

44
38
4

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
44
38