Commit f0f6b810b6b4249eaa648dbf3294d2c36d12b8f4

Authored by Braulio Bhavamitra
Committed by Daniela Feitosa
1 parent 4197c870

Support multitenancy on searches

Prefix Solr unique id with schema_path to avoid colision.
Fix rake multitenancy:reindex to reindex all environments
now that we can :)
config/solr.yml.dist
... ... @@ -3,25 +3,8 @@
3 3 # If you change the host or port number here, make sure you update
4 4 # them in your Solr config file
5 5  
6   -# This file must follow a structure in order to achieve multitenancy
7   -# support. In this example, we will configure solr to support 3
8   -# different schemas: env1, env2 and env3.
9   -#
10   -# Each "hosted" environment must have an entry like this:
11   -#
12   -# production: &PRODUCTION
13   -# url: http://127.0.0.1:8983/solr
14   -# jvm_options: -server -Xmx192M -Xms64M
15   -# timeout: 0
16   -#
17   -# env1_production:
18   -# <<: *PRODUCTION
19   -#
20   -# env2_production:
21   -# <<: *PRODUCTION
22   -#
23   -# env3_production:
24   -# <<: *PRODUCTION
  6 +# No change is need to support multitenancy. Only one solr environment is need.
  7 +# Just remember to use 'rake multitenancy:reindex' for reindexation.
25 8  
26 9 production:
27 10 url: http://127.0.0.1:8983/solr
... ...
lib/acts_as_searchable.rb
... ... @@ -6,12 +6,13 @@ module ActsAsSearchable
6 6 def acts_as_searchable(options = {})
7 7 return if !ACTS_AS_SEARCHABLE_ENABLED
8 8  
9   - if (!options[:fields])
10   - options[:additional_fields] ||= []
11   - options[:additional_fields] |= [{:schema_name => :string}]
12   - else
  9 + if options[:fields]
13 10 options[:fields] << {:schema_name => :string}
  11 + else
  12 + options[:additional_fields] ||= []
  13 + options[:additional_fields] << {:schema_name => :string}
14 14 end
  15 +
15 16 acts_as_solr options
16 17 extend FindByContents
17 18 send :include, InstanceMethods
... ... @@ -19,7 +20,15 @@ module ActsAsSearchable
19 20  
20 21 module InstanceMethods
21 22 def schema_name
22   - (Noosfero::MultiTenancy.on? and ActiveRecord::Base.postgresql?) ? ActiveRecord::Base.connection.schema_search_path : ''
  23 + self.class.schema_name
  24 + end
  25 +
  26 + # replace solr_id from vendor/plugins/acts_as_solr_reloaded/lib/acts_as_solr/instance_methods.rb
  27 + # to include schema_name
  28 + def solr_id
  29 + id = "#{self.class.name}:#{record_id(self)}"
  30 + id.insert(0, "#{schema_name}:") unless schema_name.blank?
  31 + id
23 32 end
24 33 end
25 34  
... ... @@ -36,7 +45,7 @@ module ActsAsSearchable
36 45 options[:per_page] = pg_options[:per_page].to_i
37 46 options[:scores] ||= true
38 47 options[:filter_queries] ||= []
39   - options[:filter_queries] << "schema_name:\"#{schema_name}\"" unless schema_name.empty?
  48 + options[:filter_queries] << "schema_name:\"#{schema_name}\"" unless schema_name.blank?
40 49 all_facets_enabled = options.delete(:all_facets)
41 50 options[:per_page] = options.delete(:extra_limit) if options[:extra_limit]
42 51 results = []
... ...
lib/tasks/multitenancy.rake
... ... @@ -15,18 +15,17 @@ namespace :multitenancy do
15 15 end
16 16  
17 17 task :reindex => :environment do
18   - envs = ActiveRecord::Base.configurations.keys.select{ |k| k.match(/_#{RAILS_ENV}$/) }
19   - models = [ Profile, Article, Product ]
20   - envs.each do |e|
21   - puts "Rebuilding Index for #{e}" if Rake.application.options.trace
  18 + # enable output from rebuild_index
  19 + logger = ActiveRecord::Base.logger = Logger.new(STDOUT)
  20 + logger.level = ActiveSupport::BufferedLogger::INFO
  21 +
  22 + db_envs = ActiveRecord::Base.configurations.keys.select{ |k| k.match(/_#{RAILS_ENV}$/) }
  23 + db_envs.each do |e|
  24 + puts "REBUILDING INDEX FOR ENVIRONMENT #{e}"
22 25 ActiveRecord::Base.connection.schema_search_path = ActiveRecord::Base.configurations[e]['schema_search_path']
23   - models.each do |m|
24   - if e == envs[0]
25   - m.rebuild_index
26   - puts "Rebuilt index for #{m}" if Rake.application.options.trace
27   - end
28   - m.paginated_each(:per_page => 50) { |i| i.solr_save }
29   - puts "Reindexed all instances of #{m}" if Rake.application.options.trace
  26 + $solr_indexed_models.each do |m|
  27 + puts "Rebuilding index for model #{m}"
  28 + m.rebuild_index
30 29 end
31 30 end
32 31 end
... ...
vendor/plugins/acts_as_solr_reloaded/lib/acts_as_solr/parser_methods.rb
... ... @@ -30,7 +30,7 @@ module ActsAsSolr #:nodoc:
30 30 query = replace_types([*query], ':').first
31 31 end
32 32  
33   - query_options[:filter_queries] += replace_types([*options[:filter_queries]], '') if options[:filter_queries]
  33 + query_options[:filter_queries] += replace_types([*options[:filter_queries]], ':') if options[:filter_queries]
34 34  
35 35 options[:alternate_query] ||= ''
36 36 options[:alternate_query].strip!
... ... @@ -125,7 +125,7 @@ module ActsAsSolr #:nodoc:
125 125 def solr_type_condition(options = {})
126 126 classes = [self] + (self.subclasses || []) + (options[:models] || [])
127 127 classes.map do |klass|
128   - next if klass.name.empty?
  128 + next if klass.name.empty?
129 129 "#{solr_configuration[:type_field]}:\"#{klass.name}\""
130 130 end.compact.join(' OR ')
131 131 end
... ... @@ -248,7 +248,7 @@ module ActsAsSolr #:nodoc:
248 248 bad_options = options.map {|x| x.to_sym} - valid_other_options
249 249 raise "Invalid option#{'s' if bad_options.size > 1} for faceted date's other param: #{bad_options.join(', ')}. May only be one of :after, :all, :before, :between, :none" if bad_options.size > 0
250 250 end
251   -
  251 +
252 252 def sanitize_query(query)
253 253 fields = self.configuration[:solr_fields].keys
254 254 fields += DynamicAttribute.all(:select => 'name', :group => 'name').map(&:name) if DynamicAttribute.table_exists?
... ...