Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

string::lower() comparison with an array fails #376

Open
renatolond opened this issue May 27, 2020 · 7 comments
Open

string::lower() comparison with an array fails #376

renatolond opened this issue May 27, 2020 · 7 comments
Labels

Comments

@renatolond
Copy link

Describe the bug

When using string:lower() in a where statement, if the comparison is with an array, the comparison fails.

To Reproduce

Assuming a table "table" with a string field "field", in any repository do:

root.where { string::lower(field).is([“value1”, “value2”]) }

Fails with

Caused by PG::UndefinedFunction: ERROR: operator does not exist: text = record
LINE 1: …" FROM “table” WHERE (LOWER(“table”.“field”) = ('value1…
HINT: No operator matches the given name and argument types. You might need to add explicit type casts.

Expected behavior

The comparison is expected to generate a query with (LOWER("table"."field") in ('value1', 'value2')) and the query should work

Your environment

  • Affects my production application: NO
  • Ruby version: 2.6.6
  • OS: Linux
@renatolond renatolond added the bug label May 27, 2020
@solnic
Copy link
Member

solnic commented May 27, 2020

For the record, this is what we should support:

root.where { lower(field).in(["value1", "value2"]) }

Return types should not be required in where blocks after all.

@flash-gordon
Copy link
Member

@solnic I disagree, return type is required to determine the list of available functions/operators. It's not required for common operators such as IN or =

@solnic
Copy link
Member

solnic commented May 28, 2020

@flash-gordon not sure if I understand - do you mean that we should stop handling function building via method_missing and go the explicit route with a list of available functions?

@flash-gordon
Copy link
Member

flash-gordon commented May 28, 2020

@solnic the list of available operators is determined by the expression type: https://github.com/rom-rb/rom-sql/blob/f3ef5817462c4915f37d0523ea2a2ba95c36a9de/lib/rom/sql/type_extensions.rb For instance json_returning_function(field).json_operator(args) will be a method missing (or mb some other) error whereas json::json_returning_function(field).json_operator(args) will work just fine. It's consistent and I think we should keep it that way.

@solnic
Copy link
Member

solnic commented May 29, 2020

@flash-gordon OK fair enough 😄 so it seems like this bug is caused by the lack of in method defined on ROM::SQL::Function

@solnic solnic added this to the 3.2.1 milestone May 29, 2020
@renatolond
Copy link
Author

Just to add a little comment, the method that seems to support either = or in in some other parts seem to be is, is it intentional to split it into .is and .in ?
(see

expect(func.case(users[:id].is([1, 2]) => 'first', else: 'last').sql_literal(ds)).
to eql(%((CASE WHEN ("users"."id" IN (1, 2)) THEN 'first' ELSE 'last' END)))
)

@solnic
Copy link
Member

solnic commented May 30, 2020

@renatolond actually, it's not intentional - ROM::SQL::Attribute#is uses Sequels =~ operator which supports array arg too (just like in).

This should be unified somehow, because ROM::SQL::Function#is doesn't do the same thing 🙈

@solnic solnic removed this from the 3.2.1 milestone Jan 6, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants