flying-sphinx 1.3.1 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (59) hide show
  1. checksums.yaml +5 -5
  2. data/.travis.yml +4 -6
  3. data/Appraisals +14 -10
  4. data/HISTORY +8 -0
  5. data/README.textile +4 -6
  6. data/flying-sphinx.gemspec +1 -2
  7. data/lib/flying_sphinx.rb +5 -15
  8. data/lib/flying_sphinx/cli.rb +17 -80
  9. data/lib/flying_sphinx/commands.rb +35 -0
  10. data/lib/flying_sphinx/commands/base.rb +86 -0
  11. data/lib/flying_sphinx/commands/clear.rb +7 -0
  12. data/lib/flying_sphinx/commands/configure.rb +7 -0
  13. data/lib/flying_sphinx/commands/index_sql.rb +33 -0
  14. data/lib/flying_sphinx/commands/merge.rb +17 -0
  15. data/lib/flying_sphinx/commands/prepare.rb +7 -0
  16. data/lib/flying_sphinx/commands/rebuild.rb +7 -0
  17. data/lib/flying_sphinx/commands/reset.rb +7 -0
  18. data/lib/flying_sphinx/commands/restart.rb +7 -0
  19. data/lib/flying_sphinx/commands/rotate.rb +7 -0
  20. data/lib/flying_sphinx/commands/running.rb +7 -0
  21. data/lib/flying_sphinx/commands/start.rb +7 -0
  22. data/lib/flying_sphinx/commands/start_attached.rb +10 -0
  23. data/lib/flying_sphinx/commands/stop.rb +7 -0
  24. data/lib/flying_sphinx/configuration_options.rb +11 -5
  25. data/lib/flying_sphinx/configurer.rb +7 -2
  26. data/lib/flying_sphinx/railtie.rb +7 -5
  27. data/lib/flying_sphinx/rake_interface.rb +25 -0
  28. data/lib/flying_sphinx/response/invalid.rb +1 -1
  29. data/lib/flying_sphinx/setting_files.rb +2 -2
  30. data/lib/flying_sphinx/tasks.rb +31 -24
  31. data/lib/flying_sphinx/tasks/deprecated.rb +31 -0
  32. data/lib/flying_sphinx/tasks/replaced.rb +27 -0
  33. data/lib/flying_sphinx/version.rb +1 -1
  34. data/spec/acceptance/configuring_spec.rb +7 -7
  35. data/spec/acceptance/start_or_stop_sphinx_spec.rb +7 -4
  36. data/spec/flying_sphinx/action_spec.rb +1 -1
  37. data/spec/flying_sphinx/commands/clear_spec.rb +22 -0
  38. data/spec/flying_sphinx/commands/configure_spec.rb +38 -0
  39. data/spec/flying_sphinx/commands/index_sql_spec.rb +69 -0
  40. data/spec/flying_sphinx/commands/merge_spec.rb +30 -0
  41. data/spec/flying_sphinx/commands/rebuild_spec.rb +26 -0
  42. data/spec/flying_sphinx/commands/reset_spec.rb +26 -0
  43. data/spec/flying_sphinx/commands/restart_spec.rb +23 -0
  44. data/spec/flying_sphinx/commands/rotate_spec.rb +22 -0
  45. data/spec/flying_sphinx/commands/running_spec.rb +24 -0
  46. data/spec/flying_sphinx/commands/start_attached_spec.rb +14 -0
  47. data/spec/flying_sphinx/commands/start_spec.rb +23 -0
  48. data/spec/flying_sphinx/commands/stop_spec.rb +23 -0
  49. data/spec/flying_sphinx/configurer_spec.rb +147 -0
  50. data/spec/support/command_helpers.rb +11 -0
  51. data/spec/support/multipart.rb +10 -6
  52. metadata +51 -27
  53. data/lib/flying_sphinx/binary.rb +0 -7
  54. data/lib/flying_sphinx/binary/translator.rb +0 -48
  55. data/lib/flying_sphinx/controller.rb +0 -104
  56. data/lib/flying_sphinx/rails.rb +0 -7
  57. data/lib/flying_sphinx/sphinxql.rb +0 -7
  58. data/lib/flying_sphinx/sphinxql/translator.rb +0 -26
  59. data/spec/flying_sphinx/controller_spec.rb +0 -71
@@ -0,0 +1,17 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Merge < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action 'merge', index_timeout, merging_options
6
+ end
7
+
8
+ private
9
+
10
+ def merging_options
11
+ {
12
+ :core_index => options[:core_index].name,
13
+ :delta_index => options[:delta_index].name,
14
+ :filters => MultiJson.dump(options[:filters])
15
+ }
16
+ end
17
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Prepare < FlyingSphinx::Commands::Base
4
+ def call
5
+ # nothing to do
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Rebuild < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action_with_path 'rebuild', index_timeout
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Reset < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action_with_path 'reset'
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Restart < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action 'restart'
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Rotate < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action 'rotate'
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Running < FlyingSphinx::Commands::Base
4
+ def call
5
+ api.get("/running")["running"]
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Start < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action 'start'
6
+ end
7
+ end
@@ -0,0 +1,10 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::StartAttached < FlyingSphinx::Commands::Base
4
+ def call
5
+ stream.puts <<-MESSAGE
6
+ It is not possible to start the Sphinx daemon as an attached process. Please
7
+ use ts:start without the NODETACH flag set.
8
+ MESSAGE
9
+ end
10
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ class FlyingSphinx::Commands::Stop < FlyingSphinx::Commands::Base
4
+ def call
5
+ run_action 'stop'
6
+ end
7
+ end
@@ -1,13 +1,14 @@
1
1
  class FlyingSphinx::ConfigurationOptions
2
- attr_reader :raw
2
+ attr_reader :raw, :engine
3
3
 
4
4
  def initialize(raw = nil, version = nil)
5
- @raw = raw || FlyingSphinx.translator.sphinx_configuration
6
- @version = version || '2.2.3'
5
+ @raw = raw || configuration.render
6
+ @version = version || '2.2.11'
7
+ @engine = configuration.settings["engine"] || "sphinx"
7
8
  end
8
9
 
9
10
  def settings
10
- @settings ||= FlyingSphinx::SettingFiles.new.to_hash
11
+ @settings ||= FlyingSphinx::SettingFiles.new(indices).to_hash
11
12
  end
12
13
 
13
14
  def version
@@ -20,7 +21,12 @@ class FlyingSphinx::ConfigurationOptions
20
21
  @configuration ||= ThinkingSphinx::Configuration.instance
21
22
  end
22
23
 
24
+ def indices
25
+ configuration.render
26
+ configuration.indices
27
+ end
28
+
23
29
  def version_defined?
24
- configuration.respond_to?(:version) && configuration.version.present?
30
+ configuration.version.present?
25
31
  end
26
32
  end
@@ -2,7 +2,11 @@ class FlyingSphinx::Configurer
2
2
  PresignatureError = Class.new FlyingSphinx::Error
3
3
  UploadError = Class.new FlyingSphinx::Error
4
4
 
5
- def initialize(api, input)
5
+ def self.call(api, input = nil)
6
+ new(api, input).call
7
+ end
8
+
9
+ def initialize(api, input = nil)
6
10
  @api = api
7
11
  @input = input
8
12
  end
@@ -47,11 +51,12 @@ class FlyingSphinx::Configurer
47
51
 
48
52
  writer.add "sphinx/raw.conf", config.raw
49
53
  writer.add "sphinx/version.txt", config.version
54
+ writer.add "sphinx/engine.txt", config.engine
50
55
  writer.add "sphinx/extra.txt", config.settings["extra"]
51
56
 
52
57
  config.settings["extra"].split(";").each do |key|
53
58
  writer.add key, config.settings[key]
54
- end unless config.settings["extra"].empty?
59
+ end unless config.settings["extra"].blank?
55
60
 
56
61
  StringIO.new writer.output
57
62
  end
@@ -4,10 +4,12 @@ class FlyingSphinx::Railtie < Rails::Railtie
4
4
  end
5
5
 
6
6
  initializer "flying_sphinx.set_sphinx_host_and_port" do |app|
7
- if ThinkingSphinx::Configuration.instance.respond_to?(:settings)
8
- FlyingSphinx::SphinxQL.load
9
- else
10
- FlyingSphinx::Binary.load
11
- end
7
+ configuration = FlyingSphinx::Configuration.new
8
+
9
+ ThinkingSphinx::Configuration.instance.settings['connection_options'] = {
10
+ :host => configuration.host,
11
+ :port => 9306,
12
+ :username => configuration.username
13
+ }
12
14
  end if ENV['FLYING_SPHINX_IDENTIFIER'] || ENV['STAGED_SPHINX_IDENTIFIER']
13
15
  end
@@ -0,0 +1,25 @@
1
+ class FlyingSphinx::RakeInterface < ThinkingSphinx::RakeInterface
2
+ def clear
3
+ command :clear
4
+ end
5
+
6
+ def rebuild
7
+ command :rebuild
8
+ end
9
+
10
+ def reset
11
+ command :reset
12
+ end
13
+
14
+ def restart
15
+ command :restart
16
+ end
17
+
18
+ private
19
+
20
+ def command(command, extra_options = {})
21
+ ThinkingSphinx::Commander.call(
22
+ command, configuration, options.merge(extra_options)
23
+ )
24
+ end
25
+ end
@@ -2,6 +2,6 @@ class FlyingSphinx::Response::Invalid < Faraday::Response::Middleware
2
2
  def on_complete(environment)
3
3
  return unless environment[:status] == 403
4
4
 
5
- raise 'Invalid Flying Sphinx credentials'
5
+ raise FlyingSphinx::Error, 'Invalid Flying Sphinx credentials'
6
6
  end
7
7
  end
@@ -2,8 +2,8 @@ class FlyingSphinx::SettingFiles
2
2
  INDEX_SETTINGS = [:stopwords, :wordforms, :exceptions]
3
3
  SOURCE_SETTINGS = [:mysql_ssl_cert, :mysql_ssl_key, :mysql_ssl_ca]
4
4
 
5
- def initialize(indices = nil)
6
- @indices = indices || FlyingSphinx.translator.sphinx_indices
5
+ def initialize(indices)
6
+ @indices = indices
7
7
  end
8
8
 
9
9
  def to_hash
@@ -1,31 +1,38 @@
1
- namespace :fs do
2
- desc "Upload Sphinx configuration and process indices"
3
- task :index => :environment do
4
- FlyingSphinx::CLI.new('setup').run
1
+ module FlyingSphinx
2
+ module Tasks
3
+ #
5
4
  end
5
+ end
6
6
 
7
- desc "Start the Sphinx daemon on Flying Sphinx servers"
8
- task :start => :environment do
9
- FlyingSphinx::CLI.new('start').run
10
- end
7
+ require_relative "tasks/replaced"
8
+ require_relative "tasks/deprecated"
11
9
 
12
- desc "Stop the Sphinx daemon on Flying Sphinx servers"
13
- task :stop => :environment do
14
- FlyingSphinx::CLI.new('stop').run
15
- end
10
+ # Replaced ts tasks
11
+ FlyingSphinx::Tasks::Replaced.call "ts:clear" do
12
+ interface.clear
13
+ end
16
14
 
17
- desc "Restart the Sphinx daemon on Flying Sphinx servers"
18
- task :restart => :environment do
19
- FlyingSphinx::CLI.new('restart').run
20
- end
15
+ FlyingSphinx::Tasks::Replaced.call "ts:rebuild",
16
+ ["ts:sql:rebuild", "ts:rt:index"]
21
17
 
22
- desc "Stop, configure, index and then start Sphinx"
23
- task :rebuild => :environment do
24
- FlyingSphinx::CLI.new('rebuild').run
25
- end
18
+ FlyingSphinx::Tasks::Replaced.call "ts:restart" do
19
+ interface.restart
20
+ end
26
21
 
27
- desc "Stop, clear, configure, start then populate Sphinx"
28
- task :regenerate => :environment do
29
- FlyingSphinx::CLI.new('regenerate').run
30
- end
22
+ FlyingSphinx::Tasks::Replaced.call "ts:sql:rebuild" do
23
+ interface.rebuild
24
+ end
25
+
26
+ FlyingSphinx::Tasks::Replaced.call "ts:rt:rebuild" do
27
+ interface.reset
28
+
29
+ Rake::Task["ts:rt:index"].invoke
31
30
  end
31
+
32
+ # Deprecated tasks in the fs namespace
33
+ FlyingSphinx::Tasks::Deprecated.call :index
34
+ FlyingSphinx::Tasks::Deprecated.call :start
35
+ FlyingSphinx::Tasks::Deprecated.call :stop
36
+ FlyingSphinx::Tasks::Deprecated.call :restart
37
+ FlyingSphinx::Tasks::Deprecated.call :rebuild
38
+ FlyingSphinx::Tasks::Deprecated.call :regenerate, :rebuild
@@ -0,0 +1,31 @@
1
+ class FlyingSphinx::Tasks::Deprecated
2
+ include Rake::DSL
3
+
4
+ def self.call(old_name, new_name = nil)
5
+ new(old_name, new_name || old_name).call
6
+ end
7
+
8
+ def initialize(old_name, new_name)
9
+ @old_name = old_name
10
+ @new_name = new_name
11
+ end
12
+
13
+ def call
14
+ namespace :fs do
15
+ desc "Deprecated: Use ts:#{new_name} instead."
16
+ task old_name do
17
+ puts <<-MESSAGE
18
+ The task fs:#{old_name} is now deprecated. Please use the standard Thinking
19
+ Sphinx task instead: ts:#{new_name} (Thinking Sphinx tasks will now invoke the
20
+ appropriate behaviour for both local and Flying Sphinx environments).
21
+ MESSAGE
22
+
23
+ Rake::Task["ts:#{new_name}"].invoke
24
+ end
25
+ end
26
+ end
27
+
28
+ private
29
+
30
+ attr_reader :old_name, :new_name
31
+ end
@@ -0,0 +1,27 @@
1
+ class FlyingSphinx::Tasks::Replaced
2
+ include Rake::DSL
3
+
4
+ def self.call(name, dependencies = [:environment], &block)
5
+ new(name, dependencies, block).call
6
+ end
7
+
8
+ def initialize(name, dependencies, block)
9
+ @name = name
10
+ @dependencies = dependencies
11
+ @block = block
12
+ end
13
+
14
+ def call
15
+ return unless Rake::Task.task_defined?(name)
16
+
17
+ original = Rake::Task[name]
18
+ original.clear
19
+
20
+ desc original.comment
21
+ task name => dependencies, &block
22
+ end
23
+
24
+ private
25
+
26
+ attr_reader :name, :dependencies, :block
27
+ end
@@ -1,3 +1,3 @@
1
1
  module FlyingSphinx
2
- Version = '1.3.1'
2
+ Version = '2.0.0'
3
3
  end
@@ -2,13 +2,13 @@ require 'spec_helper'
2
2
  require 'cgi'
3
3
 
4
4
  describe 'Configuring Sphinx' do
5
- let(:cli) { FlyingSphinx::CLI.new 'configure' }
6
- let(:translator) { double 'Translator', :sphinx_indices => [index],
7
- :sphinx_configuration => 'searchd { }' }
8
- let(:index) { double 'Index' }
5
+ let(:interface) { ThinkingSphinx.rake_interface.new }
6
+ let(:configuration) { configuration_double :indices => [double('Index')],
7
+ :render => 'searchd { }', :version => '2.2.11' }
9
8
 
10
9
  before :each do
11
- allow(FlyingSphinx).to receive(:translator).and_return(translator)
10
+ allow(ThinkingSphinx::Configuration).to receive(:instance).
11
+ and_return(configuration)
12
12
 
13
13
  stub_hmac_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
14
14
  to_return(:body => '{"id":953, "status":"OK"}')
@@ -20,7 +20,7 @@ describe 'Configuring Sphinx' do
20
20
  end
21
21
 
22
22
  it 'sends the configuration to the server' do
23
- SuccessfulAction.new(953).matches? lambda { cli.run }
23
+ SuccessfulAction.new(953).matches? lambda { interface.configure }
24
24
 
25
25
  expect(
26
26
  a_hmac_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
@@ -29,6 +29,6 @@ describe 'Configuring Sphinx' do
29
29
  end
30
30
 
31
31
  it 'handles the full request successfully' do
32
- expect { cli.run }.to be_successful_with 953
32
+ expect { interface.configure }.to be_successful_with 953
33
33
  end
34
34
  end
@@ -1,15 +1,18 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe 'Starting Sphinx' do
4
- let(:cli) { FlyingSphinx::CLI.new 'start' }
4
+ let(:interface) { ThinkingSphinx.rake_interface.new.daemon }
5
5
 
6
6
  before :each do
7
+ stub_hmac_request(:get, 'https://flying-sphinx.com/api/my/v5/running').
8
+ to_return(:status => 200, :body => '{"running":false, "status":"OK"}')
9
+
7
10
  stub_hmac_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
8
11
  to_return(:status => 200, :body => '{"id":429, "status":"OK"}')
9
12
  end
10
13
 
11
14
  it 'makes the request to the server', :retry => 3 do
12
- expect { cli.run }.to be_successful_with 429
15
+ expect { interface.start }.to be_successful_with 429
13
16
 
14
17
  expect(
15
18
  a_hmac_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
@@ -19,7 +22,7 @@ describe 'Starting Sphinx' do
19
22
  end
20
23
 
21
24
  describe 'Stopping Sphinx', :retry => 3 do
22
- let(:cli) { FlyingSphinx::CLI.new 'stop' }
25
+ let(:interface) { ThinkingSphinx.rake_interface.new.daemon }
23
26
 
24
27
  before :each do
25
28
  stub_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
@@ -27,7 +30,7 @@ describe 'Stopping Sphinx', :retry => 3 do
27
30
  end
28
31
 
29
32
  it 'makes the request to the server', :retry => 3 do
30
- expect { cli.run }.to be_successful_with 537
33
+ expect { interface.stop }.to be_successful_with 537
31
34
 
32
35
  expect(
33
36
  a_hmac_request(:post, 'https://flying-sphinx.com/api/my/v5/perform').
@@ -72,7 +72,7 @@ describe FlyingSphinx::Action do
72
72
  calls = 0
73
73
  action = FlyingSphinx::Action.new 'abc123', 1 do
74
74
  calls += 1
75
- raise "Exception" if calls <= 5
75
+ raise StandardError, "Exception" if calls <= 5
76
76
 
77
77
  response
78
78
  end
@@ -0,0 +1,22 @@
1
+ require "spec_helper"
2
+
3
+ RSpec.describe FlyingSphinx::Commands::Clear do
4
+ let(:subject) do
5
+ FlyingSphinx::Commands::Clear.new configuration_double, :api => api
6
+ end
7
+ let(:api) do
8
+ double 'API', :identifier => 'foo', :post => {'status' => 'OK'}
9
+ end
10
+ let(:action_class) { double }
11
+
12
+ before :each do
13
+ stub_const 'FlyingSphinx::Action', action_class
14
+ action_class.stub(:perform) { |identifier, &block| block.call }
15
+ end
16
+
17
+ it "sends through action" do
18
+ expect(api).to receive(:post).with "/perform", :action => "clear"
19
+
20
+ subject.call
21
+ end
22
+ end