diff options
6 files changed, 96 insertions, 65 deletions
diff --git a/vendor/plugins/acts_as_xapian/README.txt b/vendor/plugins/acts_as_xapian/README.txt index 84fa14f5c..a74b30f3a 100644 --- a/vendor/plugins/acts_as_xapian/README.txt +++ b/vendor/plugins/acts_as_xapian/README.txt @@ -96,11 +96,12 @@ e.g. :texts => [ :title, :body ] * :values, things which have a range of values for sorting, or for collapsing. Specify an array quadruple of [ field, identifier, prefix, type ] where -** number is an arbitary numeric identifier for use in the Xapian database +** identifier is an arbitary numeric identifier for use in the Xapian database ** prefix is the part to use in search queries that goes before the : ** type can be any of :string, :number or :date -e.g. :values => [ [ :created_at, 0, "created_at" ], [ :size, 1, "size"] ] +e.g. :values => [ [ :created_at, 0, "created_at", :date ], +[ :size, 1, "size", :string ] ] * :terms, things which come after a : in search queries. Specify an array triple of [ field, char, prefix ] where @@ -123,23 +124,12 @@ database * :if, either an attribute or a function which if returns false means the object isn't indexed -2. Make and run this database migration to create the ActsAsXapianJob model. - - class ActsAsXapianMigration < ActiveRecord::Migration - def self.up - create_table :acts_as_xapian_jobs do |t| - t.column :model, :string, :null => false - t.column :model_id, :integer, :null => false - t.column :action, :string, :null => false - end - add_index :acts_as_xapian_jobs, [:model, :model_id], :unique => true - end - def self.down - remove_table :acts_as_xapian_jobs - end - end - -3. Call 'rake xapian::rebuild_index models="ModelName1 ModelName2"' to build the index +2. Generate a database migration to create the ActsAsXapianJob model: + + script/generate acts_as_xapian + rake db:migrate + +3. Call 'rake xapian:rebuild_index models="ModelName1 ModelName2"' to build the index the first time (you must specify all your indexed models). It's put in a development/test/production dir in acts_as_xapian/xapiandbs. diff --git a/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/USAGE b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/USAGE new file mode 100644 index 000000000..2d027c46f --- /dev/null +++ b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/USAGE @@ -0,0 +1 @@ +./script/generate acts_as_xapian diff --git a/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/acts_as_xapian_generator.rb b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/acts_as_xapian_generator.rb new file mode 100644 index 000000000..a1cd1801d --- /dev/null +++ b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/acts_as_xapian_generator.rb @@ -0,0 +1,13 @@ +class ActsAsXapianGenerator < Rails::Generator::Base + def manifest + record do |m| + m.migration_template 'migration.rb', 'db/migrate', + :migration_file_name => "create_acts_as_xapian" + end + end + + protected + def banner + "Usage: #{$0} acts_as_xapian" + end +end diff --git a/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/templates/migration.rb b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/templates/migration.rb new file mode 100644 index 000000000..84a9dd766 --- /dev/null +++ b/vendor/plugins/acts_as_xapian/generators/acts_as_xapian/templates/migration.rb @@ -0,0 +1,14 @@ +class CreateActsAsXapian < ActiveRecord::Migration + def self.up + create_table :acts_as_xapian_jobs do |t| + t.column :model, :string, :null => false + t.column :model_id, :integer, :null => false + t.column :action, :string, :null => false + end + add_index :acts_as_xapian_jobs, [:model, :model_id], :unique => true + end + def self.down + drop_table :acts_as_xapian_jobs + end +end + diff --git a/vendor/plugins/acts_as_xapian/lib/acts_as_xapian.rb b/vendor/plugins/acts_as_xapian/lib/acts_as_xapian.rb index cd4d14ba3..cfaff00cf 100644 --- a/vendor/plugins/acts_as_xapian/lib/acts_as_xapian.rb +++ b/vendor/plugins/acts_as_xapian/lib/acts_as_xapian.rb @@ -4,13 +4,13 @@ # Copyright (c) 2008 UK Citizens Online Democracy. All rights reserved. # Email: francis@mysociety.org; WWW: http://www.mysociety.org/ # -# $Id: acts_as_xapian.rb,v 1.22 2008-05-16 12:29:39 francis Exp $ +# $Id: acts_as_xapian.rb,v 1.23 2008-05-16 14:47:25 francis Exp $ # Documentation # ============= # -# See ../README.txt for documentation. Please update that file as you -# this code. +# See ../README.txt for documentation. Please update that file if you edit +# code. require 'xapian' @@ -107,40 +107,44 @@ module ActsAsXapian # and error check them - i.e. check for consistency between models @@query_parser.add_boolean_prefix("model", "M") @@query_parser.add_boolean_prefix("modelid", "I") - for term in options[:terms] - raise "Use a single capital letter for term code" if not term[1].match(/^[A-Z]$/) - raise "M and I are reserved for use as the model/id term" if term[1] == "M" or term[1] == "I" - raise "model and modelid are reserved for use as the model/id prefixes" if term[2] == "model" or term[2] == "modelid" - raise "Z is reserved for stemming terms" if term[1] == "Z" - raise "Already have code '" + term[1] + "' in another model but with different prefix '" + @@terms_by_capital[term[1]] + "'" if @@terms_by_capital.include?(term[1]) && @@terms_by_capital[term[1]] != term[2] - @@terms_by_capital[term[1]] = term[2] - @@query_parser.add_boolean_prefix(term[2], term[1]) + if options[:terms] + for term in options[:terms] + raise "Use a single capital letter for term code" if not term[1].match(/^[A-Z]$/) + raise "M and I are reserved for use as the model/id term" if term[1] == "M" or term[1] == "I" + raise "model and modelid are reserved for use as the model/id prefixes" if term[2] == "model" or term[2] == "modelid" + raise "Z is reserved for stemming terms" if term[1] == "Z" + raise "Already have code '" + term[1] + "' in another model but with different prefix '" + @@terms_by_capital[term[1]] + "'" if @@terms_by_capital.include?(term[1]) && @@terms_by_capital[term[1]] != term[2] + @@terms_by_capital[term[1]] = term[2] + @@query_parser.add_boolean_prefix(term[2], term[1]) + end end - for value in options[:values] - raise "Value index '"+value[1].to_s+"' must be an integer, is " + value[1].class.to_s if value[1].class != 1.class - raise "Already have value index '" + value[1].to_s + "' in another model but with different prefix '" + @@values_by_number[value[1]].to_s + "'" if @@values_by_number.include?(value[1]) && @@values_by_number[value[1]] != value[2] - - # date types are special, mark them so the first model they're seen for - if !@@values_by_number.include?(value[1]) - if value[3] == :date - value_range = Xapian::DateValueRangeProcessor.new(value[1]) - elsif value[3] == :string - value_range = Xapian::StringValueRangeProcessor.new(value[1]) - elsif value[3] == :number - value_range = Xapian::NumberValueRangeProcessor.new(value[1]) - else - raise "Unknown value type '" + value[3].to_s + "'" - end - - @@query_parser.add_valuerangeprocessor(value_range) - - # stop it being garbage collected, as - # add_valuerangeprocessor ref is outside Ruby's GC - @@value_ranges_store.push(value_range) - end - - @@values_by_number[value[1]] = value[2] - @@values_by_prefix[value[2]] = value[1] + if options[:values] + for value in options[:values] + raise "Value index '"+value[1].to_s+"' must be an integer, is " + value[1].class.to_s if value[1].class != 1.class + raise "Already have value index '" + value[1].to_s + "' in another model but with different prefix '" + @@values_by_number[value[1]].to_s + "'" if @@values_by_number.include?(value[1]) && @@values_by_number[value[1]] != value[2] + + # date types are special, mark them so the first model they're seen for + if !@@values_by_number.include?(value[1]) + if value[3] == :date + value_range = Xapian::DateValueRangeProcessor.new(value[1]) + elsif value[3] == :string + value_range = Xapian::StringValueRangeProcessor.new(value[1]) + elsif value[3] == :number + value_range = Xapian::NumberValueRangeProcessor.new(value[1]) + else + raise "Unknown value type '" + value[3].to_s + "'" + end + + @@query_parser.add_valuerangeprocessor(value_range) + + # stop it being garbage collected, as + # add_valuerangeprocessor ref is outside Ruby's GC + @@value_ranges_store.push(value_range) + end + + @@values_by_number[value[1]] = value[2] + @@values_by_prefix[value[2]] = value[1] + end end end end @@ -290,7 +294,8 @@ module ActsAsXapian ###################################################################### # Index - # Offline indexing job queue model, create with migration in ../README.txt + # Offline indexing job queue model, create with migration made + # using "script/generate acts_as_xapian" as described in ../README.txt class ActsAsXapianJob < ActiveRecord::Base end @@ -407,15 +412,21 @@ module ActsAsXapian doc.add_term("M" + self.class.to_s) doc.add_term("I" + doc.data) - for term in self.xapian_options[:terms] - doc.add_term(term[1] + xapian_value(term[0])) + if self.xapian_options[:terms] + for term in self.xapian_options[:terms] + doc.add_term(term[1] + xapian_value(term[0])) + end end - for value in self.xapian_options[:values] - doc.add_value(value[1], xapian_value(value[0], value[3])) + if self.xapian_options[:values] + for value in self.xapian_options[:values] + doc.add_value(value[1], xapian_value(value[0], value[3])) + end end - for text in self.xapian_options[:texts] - ActsAsXapian.term_generator.increase_termpos # stop phrases spanning different text fields - ActsAsXapian.term_generator.index_text(xapian_value(text)) + if self.xapian_options[:texts] + for text in self.xapian_options[:texts] + ActsAsXapian.term_generator.increase_termpos # stop phrases spanning different text fields + ActsAsXapian.term_generator.index_text(xapian_value(text)) + end end ActsAsXapian.writable_db.replace_document("I" + doc.data, doc) diff --git a/vendor/plugins/acts_as_xapian/tasks/xapian.rake b/vendor/plugins/acts_as_xapian/tasks/xapian.rake index 4489a0c34..3b8d0aecd 100644 --- a/vendor/plugins/acts_as_xapian/tasks/xapian.rake +++ b/vendor/plugins/acts_as_xapian/tasks/xapian.rake @@ -1,6 +1,8 @@ require 'rubygems' require 'rake' require 'rake/testtask' +require 'activerecord' +require File.dirname(__FILE__) + '/../lib/acts_as_xapian.rb' namespace :xapian do # Parameters - specify "flush=true" to save changes to the Xapian database @@ -16,7 +18,7 @@ namespace :xapian do # web server afterwards to make sure it gets the changes, rather than # still pointing to the old deleted database. desc 'Completely rebuilds Xapian search index (must specify all models)' - task :rebuild_index do + task (:rebuild_index => :environment) do raise "specify ALL your models with models=\"ModelName1 ModelName2\" as parameter" if ENV['models'].nil? ActsAsXapian.rebuild_index(ENV['models'].split(" ").map{|m| m.constantize}) end @@ -24,7 +26,7 @@ namespace :xapian do # Parameters - are models, query, offset, limit, sort_by_prefix, # collapse_by_prefix desc 'Run a query, return YAML of results' - task :query do + task (:query => :environment) do raise "specify models=\"ModelName1 ModelName2\" as parameter" if ENV['models'].nil? raise "specify query=\"your terms\" as parameter" if ENV['query'].nil? s = ActsAsXapian::Search.new(ENV['models'].split(" ").map{|m| m.constantize}, |