0.0
No release in over 3 years
Low commit activity in last 3 years
Simple full-text searching for Rails
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
 Dependencies
 Project Readme

pg-searchable

pg-searchable is a quick way to make Postgres columns full-text searchable in Rails models, with support for composing complex OR/AND queries.

If all you need is a straightforward search with trigram/multi-column support, pg_search is probably a better fit.

Install

gem "pg-searchable"

Setup

class Product < ActiveRecord::Base
  include PgSearchable::Model
  searchable_column :name
end

Usage

# Add test data
sour_bread = Product.create!(name: "Sour bread")
italian_pasta = Product.create!(name: "Italian pasta")
rye_bread = Product.create!(name: "Rye bread")
sushi = Product.create!(name: "Sour Sushi Itamae")

# Basic usage
bread_condition = Product.search_name("bread")
expect(Product.where(bread_condition)).to match_array [sour_bread, rye_bread]

ita_condition = Product.search_name("ita", prefix: true)
expect(Product.where(ita_condition)).to match_array [italian_pasta, sushi]

nonsour_condition = Product.search_name("!sour")
expect(Product.where(nonsour_condition)).to match_array [italian_pasta, rye_bread]

# Use Postgres built-in websearch
ws_condition = Product.search_name("sushi or pasta", websearch: true)
expect(Product.where(ws_condition)).to match_array [sushi, italian_pasta]

# Composing basic searches
non_sour_breads = Product.where(bread_condition.and(nonsour_condition))
expect(non_sour_breads).to match_array [rye_bread]

nonsour_or_ita = Product.where(nonsour_condition.or(ita_condition))
expect(nonsour_or_ita).to match_array [rye_bread, italian_pasta, sushi]

# Advanced options
raw_condition = Product.search_name("sushi | pasta", raw: true)
expect(Product.where(raw_condition)).to match_array [sushi, italian_pasta]

Usage: Scopes

pg-searchable merely builds conditions, not chainable .where scopes. However, adding a scope for your condition can be done with one line if needed:

class Product < ActiveRecord::Base
  include PgSearchable::Model
  searchable_column :name
  scope :by_name, -> (name) { where(search_name(name)) }
end

prods = Product.by_name("bread")
expect(prods.count).to be(2)

Development

Tests

Main tests for the library actually exist in the README itself. A test case scans the readme for ruby blocks and runs the code in them as a unit test.

Running tests locally:

  1. Start local Postgres: bin/local-docker-testing
  2. Run tests: bundle exec rspec

Credits

pg_search provided much of the inspiration and basis