cehoffman-acts_as_ferret 0.4.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (162) hide show
  1. data/LICENSE +20 -0
  2. data/README +68 -0
  3. data/bin/aaf_install +23 -0
  4. data/config/ferret_server.yml +24 -0
  5. data/doc/README.win32 +23 -0
  6. data/doc/demo/README +154 -0
  7. data/doc/demo/README_DEMO +23 -0
  8. data/doc/demo/Rakefile +10 -0
  9. data/doc/demo/app/controllers/admin/backend_controller.rb +14 -0
  10. data/doc/demo/app/controllers/admin_area_controller.rb +4 -0
  11. data/doc/demo/app/controllers/application.rb +5 -0
  12. data/doc/demo/app/controllers/contents_controller.rb +49 -0
  13. data/doc/demo/app/controllers/searches_controller.rb +8 -0
  14. data/doc/demo/app/helpers/admin/backend_helper.rb +2 -0
  15. data/doc/demo/app/helpers/application_helper.rb +3 -0
  16. data/doc/demo/app/helpers/content_helper.rb +2 -0
  17. data/doc/demo/app/helpers/search_helper.rb +2 -0
  18. data/doc/demo/app/models/comment.rb +48 -0
  19. data/doc/demo/app/models/content.rb +12 -0
  20. data/doc/demo/app/models/content_base.rb +28 -0
  21. data/doc/demo/app/models/search.rb +19 -0
  22. data/doc/demo/app/models/shared_index1.rb +3 -0
  23. data/doc/demo/app/models/shared_index2.rb +3 -0
  24. data/doc/demo/app/models/special_content.rb +3 -0
  25. data/doc/demo/app/models/stats.rb +20 -0
  26. data/doc/demo/app/views/admin/backend/search.rhtml +18 -0
  27. data/doc/demo/app/views/contents/_form.rhtml +10 -0
  28. data/doc/demo/app/views/contents/edit.rhtml +9 -0
  29. data/doc/demo/app/views/contents/index.rhtml +24 -0
  30. data/doc/demo/app/views/contents/new.rhtml +8 -0
  31. data/doc/demo/app/views/contents/show.rhtml +8 -0
  32. data/doc/demo/app/views/layouts/application.html.erb +17 -0
  33. data/doc/demo/app/views/searches/_content.html.erb +2 -0
  34. data/doc/demo/app/views/searches/search.html.erb +20 -0
  35. data/doc/demo/config/boot.rb +109 -0
  36. data/doc/demo/config/database.yml +38 -0
  37. data/doc/demo/config/environment.rb +69 -0
  38. data/doc/demo/config/environments/development.rb +16 -0
  39. data/doc/demo/config/environments/production.rb +19 -0
  40. data/doc/demo/config/environments/test.rb +21 -0
  41. data/doc/demo/config/ferret_server.yml +18 -0
  42. data/doc/demo/config/lighttpd.conf +40 -0
  43. data/doc/demo/config/routes.rb +9 -0
  44. data/doc/demo/db/development_structure.sql +15 -0
  45. data/doc/demo/db/migrate/001_initial_migration.rb +18 -0
  46. data/doc/demo/db/migrate/002_add_type_to_contents.rb +9 -0
  47. data/doc/demo/db/migrate/003_create_shared_index1s.rb +11 -0
  48. data/doc/demo/db/migrate/004_create_shared_index2s.rb +11 -0
  49. data/doc/demo/db/migrate/005_special_field.rb +9 -0
  50. data/doc/demo/db/migrate/006_create_stats.rb +15 -0
  51. data/doc/demo/db/schema.sql +18 -0
  52. data/doc/demo/doc/README_FOR_APP +2 -0
  53. data/doc/demo/doc/howto.txt +70 -0
  54. data/doc/demo/public/.htaccess +40 -0
  55. data/doc/demo/public/404.html +8 -0
  56. data/doc/demo/public/500.html +8 -0
  57. data/doc/demo/public/dispatch.cgi +10 -0
  58. data/doc/demo/public/dispatch.fcgi +24 -0
  59. data/doc/demo/public/dispatch.rb +10 -0
  60. data/doc/demo/public/favicon.ico +0 -0
  61. data/doc/demo/public/images/rails.png +0 -0
  62. data/doc/demo/public/index.html +277 -0
  63. data/doc/demo/public/robots.txt +1 -0
  64. data/doc/demo/public/stylesheets/scaffold.css +74 -0
  65. data/doc/demo/script/about +3 -0
  66. data/doc/demo/script/breakpointer +3 -0
  67. data/doc/demo/script/console +3 -0
  68. data/doc/demo/script/destroy +3 -0
  69. data/doc/demo/script/ferret_server +10 -0
  70. data/doc/demo/script/generate +3 -0
  71. data/doc/demo/script/performance/benchmarker +3 -0
  72. data/doc/demo/script/performance/profiler +3 -0
  73. data/doc/demo/script/plugin +3 -0
  74. data/doc/demo/script/process/inspector +3 -0
  75. data/doc/demo/script/process/reaper +3 -0
  76. data/doc/demo/script/process/spawner +3 -0
  77. data/doc/demo/script/process/spinner +3 -0
  78. data/doc/demo/script/runner +3 -0
  79. data/doc/demo/script/server +3 -0
  80. data/doc/demo/test/fixtures/comments.yml +12 -0
  81. data/doc/demo/test/fixtures/contents.yml +13 -0
  82. data/doc/demo/test/fixtures/remote_contents.yml +9 -0
  83. data/doc/demo/test/fixtures/shared_index1s.yml +7 -0
  84. data/doc/demo/test/fixtures/shared_index2s.yml +7 -0
  85. data/doc/demo/test/functional/admin/backend_controller_test.rb +35 -0
  86. data/doc/demo/test/functional/contents_controller_test.rb +81 -0
  87. data/doc/demo/test/functional/searches_controller_test.rb +71 -0
  88. data/doc/demo/test/smoke/drb_smoke_test.rb +321 -0
  89. data/doc/demo/test/smoke/process_stats.rb +21 -0
  90. data/doc/demo/test/test_helper.rb +30 -0
  91. data/doc/demo/test/unit/comment_test.rb +217 -0
  92. data/doc/demo/test/unit/content_test.rb +705 -0
  93. data/doc/demo/test/unit/ferret_result_test.rb +24 -0
  94. data/doc/demo/test/unit/multi_index_test.rb +329 -0
  95. data/doc/demo/test/unit/remote_index_test.rb +23 -0
  96. data/doc/demo/test/unit/shared_index1_test.rb +108 -0
  97. data/doc/demo/test/unit/shared_index2_test.rb +13 -0
  98. data/doc/demo/test/unit/sort_test.rb +21 -0
  99. data/doc/demo/test/unit/special_content_test.rb +25 -0
  100. data/doc/demo/vendor/plugins/will_paginate/LICENSE +18 -0
  101. data/doc/demo/vendor/plugins/will_paginate/README +108 -0
  102. data/doc/demo/vendor/plugins/will_paginate/Rakefile +23 -0
  103. data/doc/demo/vendor/plugins/will_paginate/init.rb +21 -0
  104. data/doc/demo/vendor/plugins/will_paginate/lib/will_paginate/collection.rb +45 -0
  105. data/doc/demo/vendor/plugins/will_paginate/lib/will_paginate/core_ext.rb +44 -0
  106. data/doc/demo/vendor/plugins/will_paginate/lib/will_paginate/finder.rb +159 -0
  107. data/doc/demo/vendor/plugins/will_paginate/lib/will_paginate/view_helpers.rb +95 -0
  108. data/doc/demo/vendor/plugins/will_paginate/test/array_pagination_test.rb +23 -0
  109. data/doc/demo/vendor/plugins/will_paginate/test/boot.rb +27 -0
  110. data/doc/demo/vendor/plugins/will_paginate/test/console +10 -0
  111. data/doc/demo/vendor/plugins/will_paginate/test/finder_test.rb +219 -0
  112. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/admin.rb +3 -0
  113. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/companies.yml +24 -0
  114. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/company.rb +23 -0
  115. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/developer.rb +11 -0
  116. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/developers_projects.yml +13 -0
  117. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/project.rb +4 -0
  118. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/projects.yml +7 -0
  119. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/replies.yml +20 -0
  120. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/reply.rb +5 -0
  121. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/schema.sql +44 -0
  122. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/topic.rb +19 -0
  123. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/topics.yml +30 -0
  124. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/user.rb +2 -0
  125. data/doc/demo/vendor/plugins/will_paginate/test/fixtures/users.yml +35 -0
  126. data/doc/demo/vendor/plugins/will_paginate/test/helper.rb +42 -0
  127. data/doc/demo/vendor/plugins/will_paginate/test/lib/activerecord_test_connector.rb +64 -0
  128. data/doc/demo/vendor/plugins/will_paginate/test/lib/load_fixtures.rb +10 -0
  129. data/doc/demo/vendor/plugins/will_paginate/test/pagination_test.rb +136 -0
  130. data/doc/monit-example +22 -0
  131. data/init.rb +24 -0
  132. data/install.rb +18 -0
  133. data/lib/act_methods.rb +147 -0
  134. data/lib/acts_as_ferret.rb +584 -0
  135. data/lib/ar_mysql_auto_reconnect_patch.rb +41 -0
  136. data/lib/blank_slate.rb +53 -0
  137. data/lib/bulk_indexer.rb +38 -0
  138. data/lib/class_methods.rb +270 -0
  139. data/lib/ferret_extensions.rb +188 -0
  140. data/lib/ferret_find_methods.rb +141 -0
  141. data/lib/ferret_result.rb +53 -0
  142. data/lib/ferret_server.rb +238 -0
  143. data/lib/index.rb +99 -0
  144. data/lib/instance_methods.rb +171 -0
  145. data/lib/local_index.rb +205 -0
  146. data/lib/more_like_this.rb +217 -0
  147. data/lib/multi_index.rb +126 -0
  148. data/lib/rdig_adapter.rb +148 -0
  149. data/lib/remote_functions.rb +23 -0
  150. data/lib/remote_index.rb +54 -0
  151. data/lib/remote_multi_index.rb +20 -0
  152. data/lib/search_results.rb +50 -0
  153. data/lib/server_manager.rb +58 -0
  154. data/lib/unix_daemon.rb +64 -0
  155. data/lib/without_ar.rb +52 -0
  156. data/rakefile +141 -0
  157. data/recipes/aaf_recipes.rb +114 -0
  158. data/script/ferret_daemon +94 -0
  159. data/script/ferret_server +10 -0
  160. data/script/ferret_service +178 -0
  161. data/tasks/ferret.rake +22 -0
  162. metadata +258 -0
@@ -0,0 +1,64 @@
1
+ ################################################################################
2
+ module ActsAsFerret
3
+ module Remote
4
+
5
+ ################################################################################
6
+ # methods for becoming a daemon on Unix-like operating systems
7
+ module UnixDaemon
8
+
9
+ ################################################################################
10
+ def platform_daemon (&block)
11
+ safefork do
12
+ write_pid_file
13
+ trap("TERM") { exit(0) }
14
+ sess_id = Process.setsid
15
+ STDIN.reopen("/dev/null")
16
+ STDOUT.reopen("#{RAILS_ROOT}/log/ferret_server.out", "a")
17
+ STDERR.reopen(STDOUT)
18
+ block.call
19
+ end
20
+ end
21
+
22
+ ################################################################################
23
+ # stop the daemon, nicely at first, and then forcefully if necessary
24
+ def stop
25
+ pid = read_pid_file
26
+ raise "ferret_server doesn't appear to be running" unless pid
27
+ $stdout.puts("stopping ferret server...")
28
+ Process.kill("TERM", pid)
29
+ 30.times { Process.kill(0, pid); sleep(0.5) }
30
+ $stdout.puts("using kill -9 #{pid}")
31
+ Process.kill(9, pid)
32
+ rescue Errno::ESRCH => e
33
+ $stdout.puts("process #{pid} has stopped")
34
+ ensure
35
+ File.unlink(@cfg.pid_file) if File.exist?(@cfg.pid_file)
36
+ end
37
+
38
+ ################################################################################
39
+ def safefork (&block)
40
+ @fork_tries ||= 0
41
+ fork(&block)
42
+ rescue Errno::EWOULDBLOCK
43
+ raise if @fork_tries >= 20
44
+ @fork_tries += 1
45
+ sleep 5
46
+ retry
47
+ end
48
+
49
+ #################################################################################
50
+ # create the PID file and install an at_exit handler
51
+ def write_pid_file
52
+ raise "ferret_server may already be running, a pid file exists: #{@cfg.pid_file}" if read_pid_file
53
+ open(@cfg.pid_file, "w") {|f| f << Process.pid << "\n"}
54
+ at_exit { File.unlink(@cfg.pid_file) if read_pid_file == Process.pid }
55
+ end
56
+
57
+ #################################################################################
58
+ def read_pid_file
59
+ File.read(@cfg.pid_file).to_i if File.exist?(@cfg.pid_file)
60
+ end
61
+
62
+ end
63
+ end
64
+ end
data/lib/without_ar.rb ADDED
@@ -0,0 +1,52 @@
1
+ module ActsAsFerret
2
+
3
+ # Include this module to use acts_as_ferret with model classes
4
+ # not based on ActiveRecord.
5
+ #
6
+ # Implement the find_for_id(id) class method in your model class in
7
+ # order to make search work.
8
+ module WithoutAR
9
+ def self.included(target)
10
+ target.extend ClassMethods
11
+ target.extend ActsAsFerret::ActMethods
12
+ target.send :include, InstanceMethods
13
+ end
14
+
15
+ module ClassMethods
16
+ def logger
17
+ RAILS_DEFAULT_LOGGER
18
+ end
19
+ def table_name
20
+ self.name.underscore
21
+ end
22
+ def primary_key
23
+ 'id'
24
+ end
25
+ def find(what, args = {})
26
+ case what
27
+ when :all
28
+ ids = args[:conditions][1]
29
+ ids.map { |id| find id }
30
+ else
31
+ find_for_id what
32
+ end
33
+ end
34
+ def find_for_id(id)
35
+ raise NotImplementedError.new("implement find_for_id in class #{self.name}")
36
+ end
37
+ def count
38
+ 0
39
+ end
40
+ end
41
+
42
+ module InstanceMethods
43
+ def logger
44
+ self.class.logger
45
+ end
46
+ def new_record?
47
+ false
48
+ end
49
+ end
50
+ end
51
+
52
+ end
data/rakefile ADDED
@@ -0,0 +1,141 @@
1
+ # rakefile for acts_as_ferret.
2
+ # use to create a gem or generate rdoc api documentation.
3
+ #
4
+ # RELEASE creation:
5
+ # rake release REL=x.y.z
6
+
7
+ require 'pathname'
8
+ require 'yaml'
9
+ require 'rake'
10
+ require 'rake/rdoctask'
11
+ require 'rake/packagetask'
12
+ require 'rake/gempackagetask'
13
+ require 'rake/testtask'
14
+ require 'rake/contrib/rubyforgepublisher'
15
+
16
+ def announce(msg='')
17
+ STDERR.puts msg
18
+ end
19
+
20
+
21
+ PKG_NAME = 'acts_as_ferret'
22
+ PKG_VERSION = ENV['REL']
23
+ PKG_FILE_NAME = "#{PKG_NAME}-#{PKG_VERSION}"
24
+ RUBYFORGE_PROJECT = 'actsasferret'
25
+ RUBYFORGE_USER = 'jkraemer'
26
+
27
+ desc 'Default: run unit tests.'
28
+ task :default => :test
29
+
30
+ desc 'Test the acts_as_ferret plugin.'
31
+ Rake::TestTask.new(:test) do |t|
32
+ t.libs << 'lib'
33
+ t.pattern = 'test/**/*_test.rb'
34
+ t.verbose = true
35
+ end
36
+
37
+ desc 'Generate documentation for the acts_as_ferret plugin.'
38
+ Rake::RDocTask.new(:rdoc) do |rdoc|
39
+ rdoc.rdoc_dir = 'html'
40
+ rdoc.title = "acts_as_ferret - Ferret based full text search for any ActiveRecord model"
41
+ rdoc.options << '--line-numbers' << '--inline-source'
42
+ rdoc.options << '--main' << 'README'
43
+ rdoc.rdoc_files.include('README', 'LICENSE')
44
+ rdoc.template = "#{ENV['template']}.rb" if ENV['template']
45
+ rdoc.rdoc_files.include('lib/**/*.rb')
46
+ end
47
+
48
+ desc "Publish the API documentation"
49
+ task :pdoc => [:rdoc] do
50
+ Rake::RubyForgePublisher.new(RUBYFORGE_PROJECT, RUBYFORGE_USER).upload
51
+ end
52
+
53
+ if PKG_VERSION
54
+ spec = Gem::Specification.new do |s|
55
+ s.name = PKG_NAME
56
+ s.version = PKG_VERSION
57
+ s.platform = Gem::Platform::RUBY
58
+ s.summary = "acts_as_ferret - Ferret based full text search for any ActiveRecord model"
59
+ s.files = Dir.glob('**/*', File::FNM_DOTMATCH).reject do |f|
60
+ [ /\.$/, /sqlite$/, /\.log$/, /^pkg/, /\.svn/, /\.git/, /\.\w+\.sw.$/,
61
+ /^html/, /\~$/, /\/\._/, /\/#/ ].any? {|regex| f =~ regex }
62
+ end
63
+ #s.files = FileList["{lib,test}/**/*"].to_a + %w(README MIT-LICENSE CHANGELOG)
64
+ # s.files.delete ...
65
+ s.require_path = 'lib'
66
+ s.bindir = "bin"
67
+ s.executables = ["aaf_install"]
68
+ s.default_executable = "aaf_install"
69
+ s.autorequire = 'acts_as_ferret'
70
+ s.has_rdoc = true
71
+ # s.test_files = Dir['test/**/*_test.rb']
72
+ s.author = "Jens Kraemer"
73
+ s.email = "jk@jkraemer.net"
74
+ s.homepage = "http://projects.jkraemer.net/acts_as_ferret"
75
+ end
76
+
77
+ desc "Update the gemspec for GitHub's gem server"
78
+ task :gemspec do
79
+ Pathname("#{spec.name}.gemspec").open('w') {|f| f << YAML.dump(spec) }
80
+ end
81
+
82
+ package_task = Rake::GemPackageTask.new(spec) do |pkg|
83
+ pkg.need_tar = true
84
+ end
85
+
86
+ # Validate that everything is ready to go for a release.
87
+ task :prerelease do
88
+ announce
89
+ announce "**************************************************************"
90
+ announce "* Making RubyGem Release #{PKG_VERSION}"
91
+ announce "**************************************************************"
92
+ announce
93
+ # Are all source files checked in?
94
+ if ENV['RELTEST']
95
+ announce "Release Task Testing, skipping checked-in file test"
96
+ else
97
+ announce "Pulling in svn..."
98
+ `svk pull .`
99
+ announce "Checking for unchecked-in files..."
100
+ data = `svk st`
101
+ unless data =~ /^$/
102
+ fail "SVK status is not clean ... do you have unchecked-in files?"
103
+ end
104
+ announce "No outstanding checkins found ... OK"
105
+ # announce "Pushing to svn..."
106
+ # `svk push .`
107
+ end
108
+ end
109
+
110
+
111
+ desc "tag the new release"
112
+ task :tag => [ :prerelease ] do
113
+ reltag = "REL_#{PKG_VERSION.gsub(/\./, '_')}"
114
+ reltag << ENV['REUSE'].gsub(/\./, '_') if ENV['REUSE']
115
+ announce "Tagging with [#{PKG_VERSION}]"
116
+ if ENV['RELTEST']
117
+ announce "Release Task Testing, skipping tagging"
118
+ else
119
+ `svn copy -m 'tagging version #{PKG_VERSION}' svn://projects.jkraemer.net/acts_as_ferret/trunk/plugin svn://projects.jkraemer.net/acts_as_ferret/tags/#{PKG_VERSION}`
120
+ `svn del -m 'remove old stable' svn://projects.jkraemer.net/acts_as_ferret/tags/stable`
121
+ `svn copy -m 'tagging version #{PKG_VERSION} as stable' svn://projects.jkraemer.net/acts_as_ferret/tags/#{PKG_VERSION} svn://projects.jkraemer.net/acts_as_ferret/tags/stable`
122
+ end
123
+ end
124
+
125
+ # Upload release to rubyforge
126
+ desc "Upload release to rubyforge"
127
+ task :prel => [ :tag, :prerelease, :package ] do
128
+ `rubyforge login`
129
+ release_command = "rubyforge add_release #{RUBYFORGE_PROJECT} #{PKG_NAME} '#{PKG_VERSION}' pkg/#{PKG_NAME}-#{PKG_VERSION}.gem"
130
+ puts release_command
131
+ system(release_command)
132
+ `rubyforge config #{RUBYFORGE_PROJECT}`
133
+ release_command = "rubyforge add_file #{RUBYFORGE_PROJECT} #{PKG_NAME} '#{PKG_VERSION}' pkg/#{PKG_NAME}-#{PKG_VERSION}.tgz"
134
+ puts release_command
135
+ system(release_command)
136
+ end
137
+
138
+ desc 'Publish the gem and API docs'
139
+ task :release => [:pdoc, :prel ]
140
+
141
+ end
@@ -0,0 +1,114 @@
1
+ # Ferret DRb server Capistrano tasks
2
+ #
3
+ # Usage:
4
+ # in your Capfile, add acts_as_ferret's recipes directory to your load path and
5
+ # load the ferret tasks:
6
+ #
7
+ # load_paths << 'vendor/plugins/acts_as_ferret/recipes'
8
+ # load 'aaf_recipes'
9
+ #
10
+ # This will hook aaf's DRb start/stop tasks into the standard
11
+ # deploy:{start|restart|stop} tasks so the server will be restarted along with
12
+ # the rest of your application.
13
+ # Also an index directory in the shared folder will be created and symlinked
14
+ # into current/ when you deploy.
15
+ #
16
+ # In order to use the ferret:index:rebuild task, declare the indexes you intend to
17
+ # rebuild remotely in config/deploy.rb:
18
+ #
19
+ # set :ferret_indexes, %w( model another_model shared )
20
+ #
21
+ # HINT: To be very sure that your DRb server and application are always using
22
+ # the same model and schema versions, and you never lose any index updates because
23
+ # of the DRb server being restarted in that moment, use the following sequence
24
+ # to update your application:
25
+ #
26
+ # cap deploy:stop deploy:update deploy:migrate deploy:start
27
+ #
28
+ # That will stop the DRb server after stopping your application, and bring it
29
+ # up before starting the application again. Plus they'll never use different
30
+ # versions of model classes (which might happen otherwise)
31
+ # Downside: Your downtime is a bit longer than with the usual deploy, so be sure to
32
+ # put up some maintenance page for the meantime. Obviously this won't work if
33
+ # your migrations need acts_as_ferret (i.e. if you update model instances which
34
+ # would lead to index updates). In this case bring up the DRb server before
35
+ # running your migrations:
36
+ #
37
+ # cap deploy:stop deploy:update ferret:start deploy:migrate ferret:stop deploy:start
38
+ #
39
+ # Chances are that you're still not safe if your migrations not only modify the index,
40
+ # but also change the structure of your models. So just don't do both things in
41
+ # one go - I can't think of an easy way to handle this case automatically.
42
+ # Suggestions and patches are of course very welcome :-)
43
+
44
+ namespace :ferret do
45
+
46
+ desc "Stop the Ferret DRb server"
47
+ task :stop, :roles => :app do
48
+ rails_env = fetch(:rails_env, 'production')
49
+ run "cd #{current_path}; script/ferret_server -e #{rails_env} stop || true"
50
+ end
51
+
52
+ desc "Start the Ferret DRb server"
53
+ task :start, :roles => :app do
54
+ rails_env = fetch(:rails_env, 'production')
55
+ run "cd #{current_path}; script/ferret_server -e #{rails_env} start"
56
+ end
57
+
58
+ desc "Restart the Ferret DRb server"
59
+ task :restart, :roles => :app do
60
+ top.ferret.stop
61
+ sleep 1
62
+ top.ferret.start
63
+ end
64
+
65
+ namespace :index do
66
+
67
+ desc "Rebuild the Ferret index. See aaf_recipes.rb for instructions."
68
+ task :rebuild, :roles => :app do
69
+ rake = fetch(:rake, 'rake')
70
+ rails_env = fetch(:rails_env, 'production')
71
+ indexes = fetch(:ferret_indexes, [])
72
+ if indexes.any?
73
+ run "cd #{current_path}; RAILS_ENV=#{rails_env} INDEXES='#{indexes.join(' ')}' #{rake} ferret:rebuild"
74
+ end
75
+ end
76
+
77
+ desc "purges all indexes for the current environment"
78
+ task :purge, :roles => :app do
79
+ run "rm -fr #{shared_path}/index/#{rails_env}"
80
+ end
81
+
82
+ desc "symlinks index folder"
83
+ task :symlink, :roles => :app do
84
+ run "mkdir -p #{shared_path}/index && rm -rf #{release_path}/index && ln -nfs #{shared_path}/index #{release_path}/index"
85
+ end
86
+
87
+ desc "Clean up old index versions"
88
+ task :cleanup, :roles => :app do
89
+ indexes = fetch(:ferret_indexes, [])
90
+ indexes.each do |index|
91
+ ferret_index_path = "#{shared_path}/index/#{rails_env}/#{index}"
92
+ releases = capture("ls -x #{ferret_index_path}").split.sort
93
+ count = 2
94
+ if count >= releases.length
95
+ logger.important "no old indexes to clean up"
96
+ else
97
+ logger.info "keeping #{count} of #{releases.length} indexes"
98
+ directories = (releases - releases.last(count)).map { |release|
99
+ File.join(ferret_index_path, release) }.join(" ")
100
+ sudo "rm -rf #{directories}"
101
+ end
102
+ end
103
+ end
104
+ end
105
+
106
+ end
107
+
108
+ after "deploy:stop", "ferret:stop"
109
+ before "deploy:start", "ferret:start"
110
+
111
+ before "deploy:restart", "ferret:stop"
112
+ after "deploy:restart", "ferret:start"
113
+ after "deploy:symlink", "ferret:index:symlink"
114
+
@@ -0,0 +1,94 @@
1
+ # Ferret Win32 Service Daemon, called by Win 32 service,
2
+ # created by Herryanto Siatono <herryanto@pluitsolutions.com>
3
+ #
4
+ # see doc/README.win32 for usage instructions
5
+ #
6
+ require 'optparse'
7
+ require 'win32/service'
8
+ include Win32
9
+
10
+ # Read options
11
+ options = {}
12
+ ARGV.options do |opts|
13
+ opts.banner = 'Usage: ferret_daemon [options]'
14
+ opts.on("-l", "--log FILE", "Daemon log file") {|file| options[:log] = file }
15
+ opts.on("-c","--console","Run Ferret server on console.") {options[:console] = true}
16
+ opts.on_tail("-h","--help", "Show this help message") {puts opts; exit}
17
+ opts.on("-e", "--environment ENV ", "Rails environment") {|env|
18
+ options[:environment] = env
19
+ ENV['RAILS_ENV'] = env
20
+ }
21
+ opts.parse!
22
+ end
23
+
24
+ require File.dirname(__FILE__) + '/../config/environment'
25
+
26
+ # Ferret Win32 Service Daemon, called by Win 32 service,
27
+ # to run on the console, use -c or --console option.
28
+ module Ferret
29
+ class FerretDaemon < Daemon
30
+ # Standard logger to redirect STDOUT and STDERR to a log file
31
+ class FerretStandardLogger
32
+ def initialize(logger)
33
+ @logger = logger
34
+ end
35
+
36
+ def write(s)
37
+ @logger.info s
38
+ end
39
+ end
40
+
41
+ def initialize(options={})
42
+ @options = options
43
+
44
+ # initialize logger
45
+ if options[:log]
46
+ @logger = Logger.new @options[:log]
47
+ else
48
+ @logger = Logger.new RAILS_ROOT + "/log/ferret_service_#{RAILS_ENV}.log"
49
+ end
50
+
51
+ # redirect stout and stderr to Ferret logger if running as windows service
52
+ $stdout = $stderr = FerretStandardLogger.new(@logger) unless @options[:console]
53
+
54
+ log "Initializing FerretDaemon..."
55
+ if @options[:console]
56
+ self.service_init
57
+ self.service_main
58
+ end
59
+ end
60
+
61
+ def service_main
62
+ log "Service main enterred..."
63
+
64
+ while running?
65
+ log "Listening..."
66
+ sleep
67
+ end
68
+
69
+ log "Service main exit..."
70
+ end
71
+
72
+ def service_init
73
+ log "Starting Ferret DRb server..."
74
+ ActsAsFerret::Remote::Server.start
75
+ log "FerretDaemon started."
76
+ end
77
+
78
+ def service_stop
79
+ log "Stopping service..."
80
+ DRb.stop_service
81
+ log "FerretDaemon stopped."
82
+ end
83
+
84
+ def log(msg)
85
+ @logger.info msg
86
+ puts msg if @options[:console]
87
+ end
88
+ end
89
+ end
90
+
91
+ if __FILE__ == $0
92
+ d = Ferret::FerretDaemon.new(options)
93
+ d.mainloop
94
+ end