I am having trouble with my search bar function, I want it to search through my recipes model attribute "ingredients". When I put this code in it doesnt give me any results only a blank recipes page after the search. Any help would be great.
I have the ingredients as text inside the recipe table.
this is inside the recipe index.html
<%= form_for "", url: recipes_path, role: "search", method: :get do %>
<%= text_field_tag :search, #search_term, placeholder: "Seach..." %>
<% end %>
this is the recipe controller
def index
#recipes = Recipe.all
# #recipes =Recipe.search(params[:search])
if params[:search]
#search_term = params[:search]
#recipes = #recipes.search_by(#search_term)
end
end
this is the recipes model function
def self.search_by(search_term)
where("LOWER(ingredients) LIKE :search_term OR LOWER(title) LIKE :search_term",
search_term: "%{search_term.downcase}%")
end
Also this is the command line when I do the search:
Started GET "/recipes?search=chicken" for 127.0.0.1 at 2021-07-09 07:52:57 -0400
Processing by RecipesController#index as HTML
Parameters: {"search"=>"chicken"}
Rendering layout layouts/application.html.erb
Rendering recipes/index.html.erb within layouts/application
User Load (0.1ms) SELECT "users".* FROM "users" WHERE "users"."id" = ? ORDER BY "users"."id" ASC LIMIT ? [["id", 3], ["LIMIT", 1]]
↳ app/views/recipes/index.html.erb:13
Recipe Load (0.2ms) SELECT "recipes".* FROM "recipes" WHERE (LOWER(ingredients) LIKE '%{search_term.downcase}%' OR LOWER(title) LIKE '%{search_term.downcase}%')
↳ app/views/recipes/index.html.erb:70
Rendered recipes/index.html.erb within layouts/application (Duration: 5.0ms | Allocations: 2463)
[Webpacker] Everything's up-to-date. Nothing to do
Rendered layouts/_alerts.html.erb (Duration: 0.1ms | Allocations: 41)
Rendered layout layouts/application.html.erb (Duration: 11.0ms | Allocations: 7781)
Completed 200 OK in 12ms (Views: 11.1ms | ActiveRecord: 0.3ms | Allocations: 8360)
Does anyone know why its not searching through the recipes ingredients? Thank you in advance.
The interpolation in search_by method is wrong.
You wrote "%{search_term.downcase}%" when the correct is "%#{search_term.downcase}%". Missed the #!
def self.search_by(search_term)
where("LOWER(ingredients) LIKE :search_term OR LOWER(title) LIKE :search_term",
search_term: "%#{search_term.downcase}%")
end
Related
I have a strange problem with Devise that I was not able to figure out after several hours so I decided to bring it up to you to have a little help on the mater.
I have a tab panel which uses a turbo_frame_tag to render different tabs that have forms inside them. On form submission if they are errors it works perfectly, the turbo frame is rerendered with the form and its errors associated. However, on a successful form submission for the Devise form (here editing the user), it reloads the page but it does not render the content of the turbo frame whereas my rails server says it is rendering the appropriate html :sweat_smile:
I am giving you some code details below to help you understand:
– Where I display my tab content –
GET /settings (users#settings, users/settings.html.slim)
section { ... }
= render "shared/tab/navigation",
= turbo_frame_tag "tab_content", src: edit_user_registration_path
I put src: edit_user_registration_path because that it my first tab, it does not work with or without it.
I have a user edit form on my first tab, the issue is only for the Devise tab, for the other controllers/actions it works fine. Here for my user registration#edit (I curated the html for better understanding):
– The view I want to display in my turbo frame –
GET /settings/notifications (hairdressers#notifications_settings, hairdressers/notifications_settings.html.slim)
= turbo_frame_tag "tab_content"
section
= form_for(resource, as: resource_name, url: registration_path(resource_name), html: { method: :put, class: "..." }) do |f|
# some inputs
= button_tag type: "submit",
class: "...",
data: { disable_with: "Submitting..." }
– The controller responsible for handling the request and displaying the view –
My Devise user#registrations controller:
class Users::RegistrationsController < Devise::RegistrationsController
# before_action :configure_sign_up_params, only: [:create]
# before_action :configure_account_update_params, only: [:update]
layout "sign_in_up", except: %i[edit update]
# GET /resource/sign_up
# def new
# super
# end
# POST /resource
# def create
# super
# end
# GET /resource/edit
# def edit
# super
# end
# PUT /resource
# def update
# super
# end
# DELETE /resource
# def destroy
# super
# end
# GET /resource/cancel
# Forces the session data which is usually expired after sign
# in to be expired now. This is useful if the user wants to
# cancel oauth signing in/up in the middle of the process,
# removing all OAuth session data.
# def cancel
# super
# end
protected
# If you have extra params to permit, append them to the sanitizer.
# def configure_sign_up_params
# devise_parameter_sanitizer.permit(:sign_up, keys: [:attribute])
# end
# If you have extra params to permit, append them to the sanitizer.
# def configure_account_update_params
# devise_parameter_sanitizer.permit(:account_update, keys: [:attribute])
# end
# The path used after sign up.
# def after_sign_up_path_for(resource)
# super(resource)
# end
# The path used after sign up for inactive accounts (ie not activated yet accounts)
# That's our 'after_sign_up_path_for' because we ask users to activate their
# account on sign up
def after_inactive_sign_up_path_for(resource)
users_welcome_path(resource_id: resource.id)
end
# CUSTOM: The path used after successful update.
def after_update_path_for(resource)
users_settings_path
end
end
So, when I successfully update my informations as a user with this form form, it redirects me properly to the /settings routes, however it does not display the content of my turbo_frame_tag (here registrations#edit) BUT my rails server says so …
Started PUT "/users" for ::1 at 2022-08-24 19:30:45 +0200
Processing by Users::RegistrationsController#update as TURBO_STREAM
Parameters: {"authenticity_token"=>"[FILTERED]", "user"=>{"first_name"=>"Ulysse35", "last_name"=>"Benard1", "email"=>"mathieu#madeinvote.com", "phone_number"=>"06 59 86 98 64", "password"=>"[FILTERED]", "password_confirmation"=>"[FILTERED]", "current_password"=>"[FILTERED]"}}
User Load (0.5ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]]
User Load (0.3ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 LIMIT $2 [["id", 1], ["LIMIT", 1]]
TRANSACTION (0.2ms) BEGIN
User Update (7.9ms) UPDATE "users" SET "updated_at" = $1, "first_name" = $2 WHERE "users"."id" = $3 [["updated_at", "2022-08-24 17:30:45.644398"], ["first_name", "Ulysse35"], ["id", 1]]
TRANSACTION (6.7ms) COMMIT
Redirected to http://localhost:3000/settings
Completed 302 Found in 397ms (ActiveRecord: 15.7ms | Allocations: 7481)
Started GET "/settings" for ::1 at 2022-08-24 19:30:45 +0200
Processing by UsersController#settings as TURBO_STREAM
User Load (0.2ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]]
↳ app/controllers/users_controller.rb:10:in `settings'
Rendering layout layouts/application.html.slim
Rendering users/settings.html.slim within layouts/application
Rendered shared/tab/_link_item.html.slim (Duration: 23.6ms | Allocations: 786)
Rendered shared/tab/_link_item.html.slim (Duration: 1.4ms | Allocations: 781)
Rendered shared/tab/_link_item.html.slim (Duration: 3.8ms | Allocations: 781)
Rendered shared/tab/_navigation.html.slim (Duration: 62.9ms | Allocations: 2577)
Rendered users/settings.html.slim within layouts/application (Duration: 66.0ms | Allocations: 2870)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 1.1ms | Allocations: 773)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 1.1ms | Allocations: 773)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 1.0ms | Allocations: 773)
Rendered shared/buttons/_primary_compact_with_icon.html.slim (Duration: 2.4ms | Allocations: 772)
Rendered shared/buttons/_primary_large_with_icon.html.slim (Duration: 0.5ms | Allocations: 773)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_menu.html.slim (Duration: 0.3ms | Allocations: 363)
Rendered shared/_navbar.html.slim (Duration: 8.7ms | Allocations: 5647)
Rendered shared/_footer.html.slim (Duration: 1.1ms | Allocations: 21)
Rendered layout layouts/application.html.slim (Duration: 77.9ms | Allocations: 9322)
Completed 200 OK in 85ms (Views: 78.4ms | ActiveRecord: 0.2ms | Allocations: 10645)
Started GET "/users/edit" for ::1 at 2022-08-24 19:30:45 +0200
Processing by Users::RegistrationsController#edit as HTML
User Load (0.2ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]]
Rendering layout layouts/application.html.slim
Rendering devise/registrations/edit.html.slim within layouts/application
Rendered devise/shared/_password_field.html.slim (Duration: 1.0ms | Allocations: 896)
Rendered devise/shared/_password_field.html.slim (Duration: 1.0ms | Allocations: 897)
Rendered devise/shared/_password_field.html.slim (Duration: 0.5ms | Allocations: 895)
Rendered shared/buttons/_submit_primary_large.html.slim (Duration: 1.7ms | Allocations: 779)
Rendered devise/registrations/edit.html.slim within layouts/application (Duration: 7.2ms | Allocations: 5268)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 0.6ms | Allocations: 773)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 2.0ms | Allocations: 773)
Rendered shared/buttons/_flat_large_with_icon.html.slim (Duration: 0.5ms | Allocations: 773)
Rendered shared/buttons/_primary_compact_with_icon.html.slim (Duration: 0.4ms | Allocations: 772)
Rendered shared/buttons/_primary_large_with_icon.html.slim (Duration: 2.0ms | Allocations: 773)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_link_item.html.slim (Duration: 0.0ms | Allocations: 45)
Rendered shared/dropdown/_menu.html.slim (Duration: 0.2ms | Allocations: 363)
Rendered shared/_navbar.html.slim (Duration: 6.5ms | Allocations: 5647)
Rendered shared/_footer.html.slim (Duration: 0.0ms | Allocations: 21)
Rendered layout layouts/application.html.slim (Duration: 14.2ms | Allocations: 11710)
Completed 200 OK in 17ms (Views: 14.6ms | ActiveRecord: 0.2ms | Allocations: 13505)
and it seems that I receive well the turbo_frame response, just that it is not inserted properly, but probably I am missing something here
Any suggestion to solve this issue would be appreciated, do not hesitate to ask for further information …
If anyone gets the same problem someday, here is a clean solution I found to make it work ;)
Just edit your registrations#edit and registrations#update actions with something like:
def edit
render turbo_stream: turbo_stream.replace("tab_content", partial: "devise/registrations/edit", locals: { resource: resource } )
end
Do not forget to transform your devise/views/registration/edit view into a _edit partial, anyway it is what it was in my case.
By making your edit action responding with a turbo_stream you will be assured that it gets replaced accordingly.
Fairly new rails developer, and still trying to get my head around where things go and how to connect them.
I have a database of 'records', and am looking to search them. I found the ransack gem, which does this, however I don't want to put the search on the index page, I want a seperate page for the search and it's results.
I created a new action in the records controller:
def search
#q = Record.ransack(params[:q])
#found_records = #q.result(distinct: true)
end
and then the search.html.erb view, then the route:
resources :records do
match :search, to: 'records#search', on: :collection, via: [:get, :post]
end
and then the view itself
<%= search_form_for(
#q,
url: search_records_path,
html: { method: :post }
) do |f| %>
<%= f.label :brief %>
<%= f.search_field :brief %>
<%= f.submit %>
<% end %>
<div id="records">
<% #found_records.each do |record| %>
<%= render record %>
<% end %>
</div>
and this runs without errors, but when I press the search box the page just refreshes, with no search performed.
I guess this is a routing issue, but now sure how to set the route used by the search button? Any advice here much appreciated!
--edit
The log looks good to me, here is what is logged on the console.
Started POST "/records/search" for 127.0.0.1 at 2022-08-09 05:35:52 +0800
Processing by RecordsController#search as HTML
Parameters: {"authenticity_token"=>"[FILTERED]", "q"=>{"brief"=>"rain"}, "commit"=>"Search"}
Rendering layout layouts/application.html.erb
Rendering records/search.html.erb within layouts/application
Record Load (0.1ms) SELECT DISTINCT "records".* FROM "records"
↳ app/views/records/search.html.erb:20
Rendered records/_record.html.erb (Duration: 0.1ms | Allocations: 49)
Rendered records/_record.html.erb (Duration: 0.1ms | Allocations: 47)
Rendered records/_record.html.erb (Duration: 0.1ms | Allocations: 48)
Rendered records/_record.html.erb (Duration: 0.1ms | Allocations: 47)
Rendered records/_record.html.erb (Duration: 0.1ms | Allocations: 49)
Rendered records/search.html.erb within layouts/application (Duration: 4.5ms | Allocations: 1984)
Rendered layouts/_shim.html.erb (Duration: 0.1ms | Allocations: 15)
Rendered layouts/_header.html.erb (Duration: 0.1ms | Allocations: 15)
Rendered layouts/_footer.html.erb (Duration: 0.1ms | Allocations: 15)
Rendered layout layouts/application.html.erb (Duration: 24.0ms | Allocations: 7469)
Completed 200 OK in 26ms (Views: 24.7ms | ActiveRecord: 0.1ms | Allocations: 8216)
-- update --
Changing the search to a 'get' fixed the issue, and making sure to use #q and not a custom name without changing the ransack config to match.
I'm using nested fields and accept nested attributes with a 3 level nested relationship. The 3rd level (I don't think it matters that it's third level) relationship gets deleted when editing the parent.
Setup has one material, material has one rotap_analysis, rotap_analysis has many rotap_sieves. The following code is what triggers the delete ONLY WHEN EDITING AN EXISTING SETUP THAT ALREADY HAS A ROTAP ANALYSIS, creating new or editing and creating new rotap analysis works fine:
<%= f.fields_for :rotap_analysis do |ra| %>
<%= render 'materials/rotap_analysis_fields', f: ra %>
<% end %>
<div class="links float-e-margins">
<!-- this is deleting rotap analysis -->
<%= link_to_add_association '+ rotap analysis', f, :rotap_analysis, partial: 'materials/rotap_analysis_fields', class: "btn btn-info btn-xs" %>
</div>
Here is the server log with the delete transactions upon rendering with "fields_for" helper.
RotapAnalysis Load (0.3ms) SELECT "rotap_analyses".* FROM "rotap_analyses" WHERE "rotap_analyses"."material_id" = $1 LIMIT $2 [["material_id", 23], ["LIMIT", 1]]
↳ app/views/materials/_material_fields.html.erb:77
RotapSieve Load (4.2ms) SELECT "rotap_sieves".* FROM "rotap_sieves" WHERE "rotap_sieves"."rotap_analysis_id" = $1 [["rotap_analysis_id", 18]]
↳ app/views/materials/_rotap_analysis_fields.html.erb:24
Rendered materials/_rotap_sieve_fields.html.erb (Duration: 1.0ms | Allocations: 488)
Rendered materials/_rotap_sieve_fields.html.erb (Duration: 0.9ms | Allocations: 475)
Rendered materials/_rotap_analysis_fields.html.erb (Duration: 13.0ms | Allocations: 2823)
TRANSACTION (0.3ms) BEGIN
↳ app/views/materials/_material_fields.html.erb:82
RotapSieve Destroy (0.4ms) DELETE FROM "rotap_sieves" WHERE "rotap_sieves"."id" = $1 [["id", 17]]
↳ app/views/materials/_material_fields.html.erb:82
RotapAnalysis Destroy (0.5ms) DELETE FROM "rotap_analyses" WHERE "rotap_analyses"."id" = $1 [["id", 18]]
↳ app/views/materials/_material_fields.html.erb:82
TRANSACTION (1.0ms) COMMIT
↳ app/views/materials/_material_fields.html.erb:82
Rendered materials/_rotap_sieve_fields.html.erb (Duration: 0.9ms | Allocations: 475)
Rendered materials/_rotap_analysis_fields.html.erb (Duration: 4.2ms | Allocations: 1495)
Rendered materials/_material_fields.html.erb (Duration: 43.9ms | Allocations: 12427)
Rendered setups/_form.html.erb (Duration: 123.8ms | Allocations: 42184)
Rendered setups/edit.html.erb within layouts/application (Duration: 124.1ms | Allocations: 42245
I have several nested attributes throughout the application and I have never ran into this issue. What the heck is going on?
As documented this is weird but well known behaviour when using a has_one relationship. By default cocoon uses the association to create the new nested item.
But then rails assumes, if you already have one, creating a new one will replace it (which does make sense).
However: when using the link_to_add_association we pre-create an empty item to fill, so it will always delete it.
There is a simple workaround: for has_one associations you can use the force_non_association_create: true which will not create the child element using the association, and thus will not remove existing items (for has_one associations).
So in your case you would write:
<%= link_to_add_association '+ rotap analysis', f, :rotap_analysis,
partial: 'materials/rotap_analysis_fields',
force_non_association_create: true,
class: "btn btn-info btn-xs" %>
First post, so i'm a newbie in StackOverflow. I'm trying for several days to make appear a Return button on a page form but only on a specific one.
So, I was advised to use backlink to make it appears.
Here's my code from the form where I want the return button
<% if #backlink.present? %>
<div class="spacer30"></div>
<% if #backlink == 'infos' %>
path = membre_path(menu: 'infos')
<% end %>
<% end %>
<%= link_to "Retour", path, class: "btn-rounded btn-turquoise btn-small" %>
Here's my code controller
def edit
super do |user|
puts "TEST PARAMS BACKLINK #{params[:backlink]}"
#backlink = params[:backlink]
end
end
and my route's :
get 'change_password', to: 'users/registrations#edit'
put 'update' => 'users/registrations#update', :as => 'user_registration'
get 'edit_password', to: 'users/registrations#edit', :as => 'user_edit'
So i should have in my log my PUTS 'TEST PARAMS BACKLINK' but nothing appear, only :
Started GET "/change_password.1?backlink=infos" for ::1 at 2017-10-04 10:07:41 +0200
Processing by Users::RegistrationsController#edit as
Parameters: {"backlink"=>"infos"}
User Load (9.1ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]]
Rendering users/registrations/edit.html.erb within layouts/application
Rendered users/registrations/edit.html.erb within layouts/application (14.4ms)
Rendered shared/_navbar.html.erb (4.0ms)
Rendered shared/_flashes.html.erb (1.1ms)
Completed 200 OK in 231ms (Views: 217.0ms | ActiveRecord: 9.1ms)
Any ideas why it doesn't work?
Many thanks.
I just had to delete some lines, here's what i changed from my registration controller :
def edit
#backlink = params[:backlink]
super
end
This way, it appears exactly the way I wanted to.
Many thanks :)
I have a controller action that's being called three times per browser request. Any ideas? config/routes.rb and application_controller.rb are totally straightforward.
Code below,
config/routes.rb
Rails.application.routes.draw do
root 'tiles#index'
+
controllers/tiles_controller.rb
class TilesController < ApplicationController
def index
puts "this line prints three times in the console per request"
end
+
tiles/index.html.erb
<% if notice %>
<p id="notice"><%= notice %></p>
<% end %>
<div id="tiles">
<%= render "tile", tile: { type: "sam", id: "0" } %>
<%= render "tile", tile: { type: "inputs", id: "1" } %>
<%= render collection: #tiles, partial: "tile" %>
<%= render "tile", tile: { type: "social", id: "1000" } %>
</div>
+
This is the console log:
log/development.log
Started GET "/" for 127.0.0.1 at 2017-08-31 16:56:28 -0400
Processing by TilesController#index as HTML
Started GET "/" for 127.0.0.1 at 2017-08-31 16:56:28 -0400
Processing by TilesController#index as HTML
[1m[36mProject Load (0.5ms)[0m [1m[34mSELECT "projects".* FROM "projects" ORDER BY "projects"."launch_date" ASC LIMIT $1[0m [["LIMIT", 10]]
[1m[36mProject Load (9.1ms)[0m [1m[34mSELECT "projects".* FROM "projects" ORDER BY "projects"."launch_date" ASC LIMIT $1[0m [["LIMIT", 10]]
Rendering tiles/index.html.erb within layouts/application
Rendered tiles/_tile_sam.html.erb (0.3ms)
Rendered tiles/_tile.html.erb (8.0ms)
Rendering tiles/index.html.erb within layouts/application
Rendered tiles/_tile_sam.html.erb (0.0ms)
Rendered tiles/_tile.html.erb (0.9ms)
Rendered tiles/_tile_instagram.html.erb (12.6ms)
...
Rendered tiles/_tile_twitter.html.erb (0.5ms)
Rendered collection of tiles/_tile.html.erb [48 times] (125.9ms)
Rendered tiles/_tile_project.html.erb (0.1ms)
Rendered tiles/_tile_social.html.erb (0.6ms)
Rendered tiles/_tile.html.erb (2.7ms)
Rendered tiles/index.html.erb within layouts/application (166.1ms)
Rendered tiles/_tile_twitter.html.erb (0.6ms)
...
Rendered collection of tiles/_tile.html.erb [48 times] (158.5ms)
Rendered tiles/_tile_social.html.erb (0.1ms)
Rendered tiles/_tile.html.erb (1.0ms)
Rendered tiles/index.html.erb within layouts/application (165.3ms)
Completed 200 OK in 1310ms (Views: 217.1ms | ActiveRecord: 9.1ms)
Completed 200 OK in 1325ms (Views: 204.5ms | ActiveRecord: 0.5ms)
Help!
WOW
Finally figured this one out by removing code related to this action/view line by line. Basically, I was generating a few img tags with empty src fields. Apparently this causes many modern browsers to load a website several times, possibly in an attempt to find missing images or assuming the root URL is the image itself?
Found the behavior cited here:
https://forums.asp.net/t/1804472.aspx?Bizzare+safari+thing+two+page+loads+for+each+page+
page loads twice in Google chrome