Texticle fuzzy search not finding anything in Ruby on Rails - ruby-on-rails

I've added the following to my gemfile:
gem 'texticle', "2.0", :require => 'texticle/rails' # search gem
I then ran bundle install and bundle installed the gem
I'm using Rails 3.1.0 and I have am using a Postgres database.
I verify that I actually have the string I am looking for in the database table:
ruby-1.9.2-p290 :004 > Hotel.first
Hotel Load (0.4ms) SELECT "hotels".* FROM "hotels" LIMIT 1
=> #<Hotel id: 1, title: "Marriot Hotel", created_at: "2012-03-01 23:53:16", updated_at: "2012-03-01 23:53:16">
When I run `Hotel.search('e')
ruby-1.9.2-p290 :005 > Hotel.search(:title => 'e')
Hotel Load (1.4ms) SELECT "hotels".*, ts_rank(to_tsvector("hotels"."title"), to_tsquery('e')) AS "rank0.4785527956789428" FROM "hotels" WHERE (to_tsvector('english', "title") ## to_tsquery('e')) ORDER BY "rank0.4785527956789428" DESC
=> []
I get nothing. I tried running Hotel.search('e') and still nothing. If I try Hotel.search(:title => 'Marriot') then it works but the reason I am using Texticle is for the fuzzy search.
Am I missing any other configurations?
Thanks

There are a couple things I would suggest checking:
Verify an extension has been created manually for each database involved. I didn't have luck with 'texticle:install_trigram'. And if you're using Heroku, there may be additional steps, especially if you haven't migrated from your shared database.
Use the fuzzy_search method. In the latest version of Texticle, there are actually 3 new methods; the original #search method has been deprecated.
To manually install the extension:
Local Dev/Test
psql -U <username>
\l
\c db_development
CREATE EXTENSION pg_trgm;
\dx
\c db_test
CREATE EXTENSION pg_trgm;
\dx
\q
Heroku Integration/Production
heroku pg:psql
\dx
CREATE EXTENSION pg_trgm;
\dx
More?
PostgreSQL Trigrams (fuzzy search)
What's new in PostgreSQL 9.1 - PostgreSQL wiki
trigram | Tumblr
Installing PostgreSQL Trigram
Install Trigram Rake Task by benhamill · Pull Request #63 · tenderlove/texticle · GitHub
texticle:install_trigram - on Heroku? · Issue #15 · tenderlove/texticle · GitHub
New Texticle search methods (source code)
texticle/lib/texticle.rb at master · texticle/texticle · GitHub

My understanding of the way Texticle works is that it's going to do full text search on your string columns but not necessarily do fuzzy search by default. If you look at the query that it's generating in Postgres, it's looking for a match on 'e' rather than any word that contains the letter 'e'.
You can read the Postgres docs here:
http://www.postgresql.org/docs/9.1/static/datatype-textsearch.html
That said, I see support for prefix matching but not postfix in the docs, although I might be missing something.
What happens if you do Hotel.search('Marr:*') ?

Related

Rails 4.2 Postgres 9.4.4 statement_timeout doesn't work

I am trying to set a statement_timeout. I tried both setting in database.yml file like this
variables:
statement_timeout: 1000
And this
ActiveRecord::Base.connection.execute("SET statement_timeout = 1000")
Tested with
ActiveRecord::Base.connection.execute("select pg_sleep(4)")
And they both don't have any effect.
I am running postgres 10 in my local and the statement_timeouts works just expected. But on my server that is running postgres 9.4.4, it simply doesn't do anything.
I've check Postgres' doc for 9.4 and statement_timeout is available. Anyone can shed some light?
I wasn't able to replicate this issue locally using: Postgresql 9.4.26. But it might be useful to share what I've tried and some thoughts around the server issue.
Here is what I've tried (a useful bit might be a query to verify the PG version from rails):
# Confirming I am executing against 9.4.x PG:
irb(main):002:0> ActiveRecord::Base.connection.execute("select version()")
(10.8ms) select version()
=> #<PG::Result:0x00007ff74782e060 status=PGRES_TUPLES_OK ntuples=1 nfields=1 cmd_tuples=1>
irb(main):003:0> _.first
=> {"version"=>"PostgreSQL 9.4.26 on x86_64-apple-darwin18.7.0, compiled by Apple clang version 11.0.0 (clang-1100.0.33.17), 64-bit"}
# Set timeout:
irb(main):004:0> ActiveRecord::Base.connection.execute("SET statement_timeout = 1000")
(0.4ms) SET statement_timeout = 1000
=> #<PG::Result:0x00007ff7720a3d88 status=PGRES_COMMAND_OK ntuples=0 nfields=0 cmd_tuples=0>
# Confirm it works - it is ~1s and also stacktrace is pretty explicit about it:
irb(main):005:0> ActiveRecord::Base.connection.execute("select pg_sleep(4)")
(1071.2ms) select pg_sleep(4)
.... (stacktrace hidden)
ActiveRecord::StatementInvalid (PG::QueryCanceled: ERROR: canceling statement due to statement timeout)
: select pg_sleep(4)
Here is what to try
Since the issue occurs on server only and since statement_timeout works on other minor version and locally, one thing that comes to mind is the lack of privileges to update statement_timeout from where it is attempted. Perhaps rails pg login used to make db connection is not allowed to update that setting.
The best would be to verify that either via rails console on a server:
irb(main):004:0> ActiveRecord::Base.connection.execute("SET statement_timeout = 1000")
irb(main):004:0> irb(main):003:0> ActiveRecord::Base.connection.execute("show statement_timeout").first
(0.2ms) show statement_timeout
=> {"statement_timeout"=>"1s"}
Or, it can be checked directly via psql console (some deployments allow this too):
psql myserveruser # if this was heroku's pg: heroku pg:psql
postgres=# set statement_timeout = 1000;
SET
postgres=# select pg_sleep(4);
ERROR: canceling statement due to statement timeout
Time: 1068.067 ms (00:01.068)
Other thing to keep in mind (taken from https://dba.stackexchange.com/a/83035/90903):
The way statement_timeout works, the time starts counting when the
server receives a new command from the client...
And if a function does SET statement_timeout = 100; it will have an effect only starting at
the next command from the client.

Why does some of the home-brew formulas show that they have conflict with another formula?

Some of the home-brew formulas such as this one show the following conflict:
This formula is in conflict with the following:
What does this conflict mean and what are its impacts?
It means that some formulas provides common files or common services and cannot be both installed in the same time.
For example the formulas Sonarqube
and SonarqubeLts conflict because they provide the same application at different version. Another example is the formulas MySQL and MariaDB that conflict because they provide both a slightly modified version of the same DBMS.
== EDIT
The formulas hive and apache-spark don't have any conflicts. You can check it with:
brew info hive apache-spark
It the past there was a conflict because both of these formulas installed the beeline binaries but this was solved with this commit:
commit b64c35859510788a31a6ffcbb18b2d10b7946d03
Author: Tim D. Smith <git#tim-smith.us>
Date: Tue May 5 15:24:12 2015 -0700
apache-spark: rename beeline to avoid hive conflict
Reference Homebrew/homebrew#39319.
diff --git a/Formula/apache-spark.rb b/Formula/apache-spark.rb
index 559ea862bb..0bec8aad9f 100644
--- a/Formula/apache-spark.rb
+++ b/Formula/apache-spark.rb
## -5,11 +5,13 ## class ApacheSpark < Formula
head "https://github.com/apache/spark.git"
url "https://d3kbcqa49mib13.cloudfront.net/spark-1.3.1-bin-hadoop2.6.tgz"
version "1.3.1"
+ revision 1
sha1 "86911b6c8964230a93691bd45589f491c10d36c0"
- conflicts_with 'hive', :because => 'both install `beeline` binaries'
-
def install
+ # Rename beeline to distinguish it from hive's beeline
+ mv "bin/beeline", "bin/spark-beeline"
+
rm_f Dir["bin/*.cmd"]
libexec.install Dir["*"]
bin.write_exec_script Dir["#{libexec}/bin/*"]
The link you provide in your question is probably not updated with the latest versions of these formulas.

PG::UnableToSend: no connection to the server in Rails

I have a production server running ubuntu 14.04, Rails 4.2.0, postgresql 9.6.1 with gem pg 0.21.0/0.20.0. In last few days, there is constantly error with accessing to a table customer_input_datax_records in psql server.
D, [2017-07-20T18:08:39.166897 #1244] DEBUG -- : CustomerInputDatax::Record Load (0.1ms) SELECT "customer_input_datax_records".* FROM "customer_input_datax_records" WHERE ("customer_input_datax_records"."status" != $1) [["status", "email_sent"]]
E, [2017-07-20T18:08:39.166990 #1244] ERROR -- : PG::UnableToSend: no connection to the server
: SELECT "customer_input_datax_records".* FROM "customer_input_datax_records" WHERE ("customer_input_datax_records"."status" != $1)
The code which call to access the db server is with Rufus scheduler 3.4.2 loop:
s = Rufus::Scheduler.singleton
s.every '2m' do
new_signups = CustomerInputDatax::Record.where.not(:status => 'email_sent').all
.......
end
After restart the server, usually there is with first request (or a few). But after some time (ex, 1 or 2 hours), the issue starts to show up. But the app seems running fine (accessing records with read/write & creating new). There are some online posts about the error. However the problem seems not the one I am having. Before I re-install the psql server, I would like to get some ideas about what causes the no connection.
UPDATE: database.yml
production:
adapter: postgresql
encoding: unicode
host: localhost
database: wb_production
pool: 5
username: postgres
password: xxxxxxx
So, the error is "RAILS: PG::UnableToSend: no connection to the server".
That reminds me of Connection pool issue with ActiveRecord objects in rufus-scheduler
You could do
s = Rufus::Scheduler.singleton
s.every '2m' do
ActiveRecord::Base.connection_pool.with_connection do
new_signups = CustomerInputDatax::Record
.where.not(status: 'email_sent')
.all
# ...
end
end
digging
It would be great to know more about the problem.
I'd suggest trying this code:
s = Rufus::Scheduler.singleton
def s.on_error(job, error)
Rails.logger.error(
"err#{error.object_id} rufus-scheduler intercepted #{error.inspect}" +
" in job #{job.inspect}")
error.backtrace.each_with_index do |line, i|
Rails.logger.error(
"err#{error.object_id} #{i}: #{line}")
end
end
s.every '2m' do
new_signups = CustomerInputDatax::Record.where.not(:status => 'email_sent').all
# .......
end
As soon as the problem manifests itself, I'd look for the on_error full output in the Rails log.
This on_error comes from https://github.com/jmettraux/rufus-scheduler#rufusscheduleron_errorjob-error
As we discuss in the comments, the problem seems related to your rufus version.
I would suggest you to check out whenever gem and to invoke a rake task instead of calling directly the activerecord model.
It could be a good idea, however, to open an issue with the traceback of your error in the rufus-scheduler repo on github (just to let then know...)

Why is YAML.safe_load failing on a YAML alias?

I've a locale file in my Rails application that works fine with Rails, but when I tried to use it with react_on_rails rake task (rake react_on_rails:locale) I'm getting this error:
Psych::BadAlias: Unknown alias: item_attributes
I found that the rake task is basically calling YAML.safe_load, so I prepared the simplest example without Rails and the error is still there. Here's the sample Ruby script:
require 'yaml'
YAML.safe_load(File.open('test.yml'))
And here's the test.yml file (shorter version of the actual locale file):
pl:
language: Polski
dictionary_name: simple
activerecord:
attributes:
line_item: &item_attributes
variant: Produkt
quantity: Ilosc
price: Cena Netto
total_price: Wartosc Netto
vat_rate: VAT
total_vat_amount: Kwota VAT
total_gross_price: Wartosc Brutto
order_item:
<<: *item_attributes
I'm still getting the error:
/usr/local/Cellar/ruby/2.3.1/lib/ruby/2.3.0/psych/visitors/to_ruby.rb:402:in `visit_Psych_Nodes_Alias': Unknown alias: item_attributes (Psych::BadAlias)
Any ideas why this works fine with Rails but fails here? Any other way to avoid duplication in the YAML file and make it work for both Rails and YAML.safe_load?
I found an answer in the Psych documentation, at https://ruby-doc.org/stdlib-2.1.0/libdoc/psych/rdoc/Psych.html.
Aliases can be explicitly allowed by changing the aliases parameter. For example:
x = []
x << x
yaml = Psych.dump x
Psych.safe_load yaml # => raises an exception
Psych.safe_load yaml, [], [], true # => loads the aliases
Whether to allow aliases or not is a boolean passed to safe_load as the fourth argument.

Determine mysql2 server version using mysql2 Ruby gem

I'm using Rails and the mysql2 gem. Is there a way to get the mysqld server version as running the command:
$ mysqld --version
mysqld Ver 5.5.29 for osx10.8 on i386 (Source distribution)
I do not wish to execute a shell command because the database server might be running on another server.
You can get the version info in rails via ActiveRecord::Base.connection. I'm doing it in my rails console here. I'm using an old version (2.2) of rails so the syntax might be different in yours.
irb(main):001:0> ActiveRecord::Base.connection.select_rows(
"SHOW VARIABLES LIKE '%version%'"
)
=> [
["innodb_version", "5.5.34"],
["protocol_version", "10"],
["slave_type_conversions", ""],
["version", "5.5.34-0ubuntu0.12.04.1"],
["version_comment", "(Ubuntu)"],
["version_compile_machine", "x86_64"],
["version_compile_os", "debian-linux-gnu"]
]
Once you've got this you can pull out the info you want, eg:
version = ActiveRecord::Base.connection
.select_rows("SHOW VARIABLES LIKE 'version'")
.last.last
=> "5.5.34-0ubuntu0.12.04.1"
def mysql_version
mysql_version_sql = 'SHOW VARIABLES WHERE Variable_name = "version"'
ActiveRecord::Base.connection.select_rows(mysql_version_sql)[0][1]
end
mysql_version #=> "5.5.35-0+wheezy1"

Resources