Permalink
Browse files

Import Sphincter, an ActiveRecord extension for searching with Sphinx.

[git-p4: depot-paths = "//src/Sphincter/dev/": change = 3325]
  • Loading branch information...
0 parents commit 447c639b929a18ea5605a270ae2506a642c816cf @drbrain drbrain committed Jul 30, 2007
@@ -0,0 +1,5 @@
+== 1.0.0 / 2007-07-26
+
+* 1 major enhancement
+ * Birthday!
+
@@ -0,0 +1,27 @@
+Copyright 2007 Eric Hodel. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+
+1. Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+2. Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+3. Neither the names of the authors nor the names of their contributors
+ may be used to endorse or promote products derived from this software
+ without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS
+OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE
+LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
+OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
+OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
+BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
+OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
+EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
@@ -0,0 +1,16 @@
+History.txt
+LICENSE.txt
+Manifest.txt
+README.txt
+Rakefile
+lib/sphincter.rb
+lib/sphincter/association_searcher.rb
+lib/sphincter/configure.rb
+lib/sphincter/search.rb
+lib/sphincter/search_stub.rb
+lib/sphincter/tasks.rb
+test/sphincter_test_case.rb
+test/test_sphincter_association_searcher.rb
+test/test_sphincter_configure.rb
+test/test_sphincter_search.rb
+test/test_sphincter_search_stub.rb
@@ -0,0 +1,124 @@
+Sphincter
+
+Eric Hodel <drbrain@segment7.net>
+
+http://seattlerb.org/Sphincter
+
+Sphincter was named by David Yeu.
+
+== DESCRIPTION:
+
+Sphincter is an ActiveRecord extension for full-text searching with Sphinx.
+
+Sphincter uses Dmytro Shteflyuk's sphinx Ruby API and automatic
+configuration to make totally rad ActiveRecord searching. Well, you
+still have to tell Sphincter what models you want to search. It
+doesn't read your mind.
+
+For complete documentation:
+
+ ri Sphincter
+
+== FEATURES:
+
+* Automatically configures itself.
+* Handy set of rake tasks for easy, automatic management.
+* Automatically adds has_many metadata for searching across the
+ association.
+* Stub for testing without connecting to searchd, Sphincter::SearchStub.
+* Easy pagination support.
+* Filtering by index metadata and ranges, including dates.
+
+== PROBLEMS:
+
+* Setting match mode not supported.
+* Setting sort mode not supported.
+* Setting per-field weights not supported.
+* Setting id range not supported.
+* Setting group-by not supported.
+
+== QUICK-START:
+
+Download and install Sphinx from http://www.sphinxsearch.com/downloads.html
+
+Download Sphinx Ruby API from http://rubyforge.org/frs/?group_id=2604&release_id=11049
+
+Unpack Sphinx Ruby API into vendor/plugins/.
+
+Install Sphincter:
+
+ $ gem install Sphincter
+
+Load Sphincter in config/environment.rb:
+
+ require 'sphincter'
+
+Add indexes to models:
+
+ class Post < ActiveRecord::Base
+ belongs_to :blog
+ add_index :fields => %w[title body published]
+ end
+
+Add searching UI:
+
+ class BlogController < ApplicationController
+ def search
+ @blog = Blog.find params[:id]
+
+ @results = @blog.posts.search params[:q]
+ end
+ end
+
+Start searchd:
+
+ $ rake sphincter:start_searchd
+
+Then test it out in your browser.
+
+== EXAMPLES:
+
+See Sphincter::Search#search for full documentation.
+
+Example ActiveRecord model:
+
+ class Post < ActiveRecord::Base
+ belongs_to :blog
+
+ # published is a boolean and title and body are string or text fields
+ add_index :fields => %w[title body published]
+ end
+
+Simple search:
+
+ Post.search 'words'
+
+Only search published posts:
+
+ Post.search 'words', :conditions => { :published => 1 }
+
+Only search posts created in the last week:
+
+ now = Time.now
+ ago = now - 1.weeks
+ Post.search 'words', :between => { :created_on => [ago, now] }
+
+Pagination (defaults to ten records/page):
+
+ Post.search 'words', :page => 2
+
+Pagination with custom page size:
+
+ Post.search 'words', :page => 2, :per_page => 20
+
+Pagination with custom page size (better):
+
+Add to config/sphincter.yml:
+
+ sphincter:
+ per_page: 20
+
+Then search:
+
+ Post.search 'words', :page => 2
+
@@ -0,0 +1,21 @@
+# -*- ruby -*-
+
+require 'rubygems'
+require 'hoe'
+$:.unshift 'lib'
+require 'sphincter'
+
+Hoe.new('Sphincter', Sphincter::VERSION) do |p|
+ p.rubyforge_name = 'seattelrb'
+ p.author = 'Eric Hodel'
+ p.email = 'drbrain@segment7.net'
+ p.summary = p.paragraphs_of('README.txt', 4).first
+ p.description = p.paragraphs_of('README.txt', 5).first
+ p.url = p.paragraphs_of('README.txt', 2).first
+ p.changes = p.paragraphs_of('History.txt', 0..1).join("\n\n")
+
+ p.extra_deps << ['rake', '>= 0.7.3']
+ p.extra_deps << ['rails', '>= 1.2.3']
+end
+
+# vim: syntax=Ruby
@@ -0,0 +1,102 @@
+$TESTING = defined?($TESTING) && $TESTING
+
+##
+# Sphincter is a ActiveRecord extension for full-text searching using the
+# Sphinx library.
+#
+# For the quick-start guide and some examples, see README.txt.
+#
+# == Installing
+#
+# Download and install Sphinx from http://www.sphinxsearch.com/downloads.html
+#
+# Download Sphinx Ruby API from
+# http://rubyforge.org/frs/?group_id=2604&release_id=11049
+#
+# Unpack Sphinx Ruby API into vendor/plugins/.
+#
+# Install the gem:
+#
+# gem install Sphincter
+#
+# Require Sphincter in config/environment.rb:
+#
+# require 'sphincter'
+#
+# Require the Sphincter rake tasks in Rakefile:
+#
+# require 'sphincter/tasks'
+#
+# == Setup
+#
+# At best, you don't do anything to setup Sphincter. It has sensible built-in
+# defaults.
+#
+# If you're running Sphinx's searchd for multiple environments on the same
+# machine, you'll want to add a config file to change the port that searchd
+# and the RAILS_ENV will comminicate across. Do that in a per-environment
+# configuration file.
+#
+# If you have multiple machines, you'll want to change which address searchd
+# will run on. Do that in the global configuration file.
+#
+# See Sphincter::Configure for full information on how to setup these and
+# other options for Sphincter.
+#
+# When you're done, run:
+#
+# $ rake sphincter:configure
+#
+# == Indexing
+#
+# Sphincter automatically extends ActiveRecord::Base with Sphincter::Search, so
+# you only have to call add_index in the models you want indexed:
+#
+# class Model < ActiveRecord::Base
+# belongs_to :other
+#
+# add_index :fields => %w[title body]
+# end
+#
+# class Other < ActiveRecord::Base
+# has_many :models
+# end
+#
+# add_index automatically adds a #search method to has_many associations
+# referencing this model, so you could:
+#
+# Other.find(id).models.search 'some query'
+#
+# See Sphincter::Search for details.
+#
+# When you're done, run:
+#
+# rake sphincter:index
+#
+# == Tasks
+#
+# You can get a set of Sphincter tasks by requiring 'sphincter/tasks' in your
+# Rakefile. These tasks are all in the 'sphincter' namespace:
+#
+# configure:: Creates sphinx.conf if it doesn't exist
+# reconfigure:: Creates sphinx.conf, replacing the existing one.
+# index:: Runs the sphinx indexer if the index doesn't exist.
+# reindex:: Runs the sphinx indexer. Rotates the index if searchd is running.
+# reset:: Stops searchd, reconfigures and reindexes
+# restart_searchd:: Restarts the searchd sphinx daemon
+# start_searchd:: Starts the searchd sphinx daemon
+# stop_searchd:: Stops the searchd daemon
+
+module Sphincter
+
+ ##
+ # This is the version of Sphincter you are using.
+
+ VERSION = '1.0.0'
+
+end
+
+require 'sphincter/configure'
+require 'sphincter/association_searcher'
+require 'sphincter/search'
+
@@ -0,0 +1,22 @@
+require 'sphincter'
+
+##
+# ActiveRecord::Associations::ClassMethods#has_many extension for searching
+# the items of an ActiveRecord::Associations::AssociationProxy.
+
+module Sphincter::AssociationSearcher
+
+ ##
+ # Searches for +query+ with +options+. Adds a condition so only the
+ # proxy_owner's records are matched.
+
+ def search(query, options = {})
+ pkey = proxy_reflection.primary_key_name
+ options[:conditions] ||= {}
+ options[:conditions][pkey] = proxy_owner.id
+
+ proxy_reflection.klass.search query, options
+ end
+
+end
+
Oops, something went wrong.

0 comments on commit 447c639

Please sign in to comment.