pirosikick's diary

君のハートにunshift

Redmineのapp/models/user.rbにメソッドを追加しようとしてハマった

このページの「Redmine の本体機能の拡張」>「新しいメソッドの追加」を参考にapp/models/user.rbにメソッド追加しようとしたら、Redmine起動時に下記エラーが出た。

$ RAILS_ENV=development be rails
=> Booting WEBrick
=> Rails 3.2.8 application starting in development on http://0.0.0.0:3000
=> Call with -d to detach
=> Ctrl-C to shutdown server
Exiting
/Users/hanai/dev/redmine/vendor/bundle/ruby/1.9.1/gems/activesupport-3.2.8/lib/active_support/dependencies.rb:503:in `load_missing_constant': Expected /Users/hanai/dev/redmine/app/models/user.rb to define User (LoadError)

メソッドを追加するコードは下記で$REDMINE/plugin/$PLUGIN_NAME/lib/user_patch.rbというファイル名で保存。 $REDMINE/plugin/$PLUGIN_NAME/init.rbに「require_dependency 'user_patch'」の1行を追加し、読みこむようにする。

#
# lib/user_patch.rb
#
require_dependency 'user'

module UserPatch
  def self.included(base)
    base.extend(ClassMethods)

    base.send(:include, InstanceMethods)

    base.class_eval do
    end
  end

  module ClassMethods
  end

  module InstanceMethods
  	# 追加したいメソッド
    def hoge_method
    	"hello plugin"
    end
  end
end

User.send(:include, UserPatch)

解決方法は、user_patch.rbでprincipal, projectもrequire_dependencyすればよろし。

#
# lib/user_patch.rb
#

# 追加
require_dependency 'project'
require_dependency 'principal'

require_dependency 'user'

module UserPatch
  def self.included(base)
    base.extend(ClassMethods)

    base.send(:include, InstanceMethods)

    base.class_eval do
    end
  end

  module ClassMethods
  end

  module InstanceMethods
  	# 追加したいメソッド
    def hoge_method
    	"hello plugin"
    end
  end
end

User.send(:include, UserPatch)

なぜこうなるかは結局よくわからなかった。。issue.rbはサンプル通りでOKだったし、サンプルのissue_patch.rbを一緒に読み込むとうまくいったりと普段rubyやらrailsを触らない俺にとっては謎だった。

参考資料

Doesn't patch "User" model in a plugin