In my rails project, I ran rake routes and got the following output:
Prefix Verb URI Pattern Controller#Action
obelisk_callflow_nodes GET /obelisk/callflows/:callflow_id/nodes(.:format) obelisk/nodes#index
POST /obelisk/callflows/:callflow_id/nodes(.:format) obelisk/nodes#create
new_obelisk_callflow_node GET /obelisk/callflows/:callflow_id/nodes/new(.:format) obelisk/nodes#new
edit_obelisk_callflow_node GET /obelisk/callflows/:callflow_id/nodes/:id/edit(.:format) obelisk/nodes#edit
obelisk_callflow_node GET /obelisk/callflows/:callflow_id/nodes/:id(.:format) obelisk/nodes#show
PATCH /obelisk/callflows/:callflow_id/nodes/:id(.:format) obelisk/nodes#update
PUT /obelisk/callflows/:callflow_id/nodes/:id(.:format) obelisk/nodes#update
DELETE /obelisk/callflows/:callflow_id/nodes/:id(.:format) obelisk/nodes#destroy
obelisk_callflows GET /obelisk/callflows(.:format) obelisk/callflows#index
POST /obelisk/callflows(.:format) obelisk/callflows#create
new_obelisk_callflow GET /obelisk/callflows/new(.:format) obelisk/callflows#new
edit_obelisk_callflow GET /obelisk/callflows/:id/edit(.:format) obelisk/callflows#edit
obelisk_callflow GET /obelisk/callflows/:id(.:format) obelisk/callflows#show
PATCH /obelisk/callflows/:id(.:format) obelisk/callflows#update
PUT /obelisk/callflows/:id(.:format) obelisk/callflows#update
DELETE /obelisk/callflows/:id(.:format) obelisk/callflows#destroy
I have a html.slim file for showing all the callflows (i.e.obelisk/nodes#index). In this file, I want to add a button to show the nodes of each callflow (i.e. connect that button to obelisk_callflow_nodes GET /obelisk/callflows/:callflow_id/nodes)
I've tried = link_to 'Nodes', obelisk_callflow_nodes_path(callflow_id: c.id), method: :get, class: 'btn btn-primary' where c is a callflow object. I've checked that c is what I want because I have c.name rendering properly. However, I'm getting the following error:
undefined methodobelisk_callflow_nodes_path' for #<#:0x00007fb3d5abebc8>`
I've checked that I do have an index method for my Obelisk::NodesController
I changed the routes so that I no longer user namespace obelisk so the routes don't start with /obelisk/. This fixes the problem. I know it might not be the best solution but in this case it has worked for the purpose of my project.
Related
On submit this form will call the put action on the controller:
.panel-body{style: 'background:#0E0D0D;'}
=form_for #payment, method: :put, html: {id: 'edit_bank_detail'} do |f| .row.text_white
.form-group.col-lg-12
=f.label :paypal_email_address
=f.email_field 'user_paypal_email',class: 'form-control'
.row.text-center
.form-group.col-lg-12
=f.submit 'Submit', class: 'btn btn-primary text_black',data: { disable_with: "Please wait..." }
I need it to call the put or create action based on the condition:
if #payments.new_record?
# create action
else
# put action
You don't even need to specify the HTTP method in the first place. form_for and its successor form_with are smart enough to figure out both the path for the action attribute and the method by calling #persisted? on the #payment model instance that you pass as the first argument.
= form_for #payment, html: {id: 'edit_bank_detail'} do |f|
Given conventional routes this will point the form to POST /payments or PATCH /payments/:id if the record has been persisted. Rails has used PATCH instead of PUT for updates since 2012 but resources and resource still generate additional PUT routes for backwards compatibility.
I tried something like this and it works.
=f.submit 'Submit', action_name: #return.new_record? ? 'create' : 'update'
Thanks #Sebastian Palma followed your suggestion.
When accessing the first page of our site, users are prompted to enter a "coupon code" to continue to the next page. Coupons can be used multiple times, but must exist in the "code" field of the coupon_codes table.
If the user enters a code that exists in the coupon_codes table, they should automatically be redirected to the next page. If the user enters a code that does not exist in the coupon_codes table, an error should be displayed with the option of trying again.
I'm sure I'm making this more difficult than it needs to be, as I've been working on this on and off for days. I've been able to get it to be what I feel is close, but not quite there. There have been multiple variations and trials, but this is where I'm currently at.
Model (coupon_code):
def self.code(code)
if code
self.exists?(['code = ?', "#{code}"])
##move on to /design
else
##display error
end
end
View (index):
<%= form_tag coupon_code, :method => 'get' do %>
<%= text_field_tag :code, params[:code] %>
<%= submit_tag("Check my coupon", :name => nil) %>
<% end %>
Controller:
def index
#coupon_codes = CouponCode.code(params[:code])
end
The log shows the following (after entering the correct code) before re-rendering the page I'm already on:
CouponCode Exists (0.2ms) SELECT 1 AS one FROM `coupon_codes` WHERE (code = 'correct') LIMIT 1
If I use the rails console, it seems like it should work (assuming I'm using it correctly), I'm just not sure how to go about getting it to move on or display an error.
2.1.1 :001 > code = 'correct'
=> "correct"
2.1.1 :002 > CouponCode.exists?(['code = ?', "#{code}"])
CouponCode Exists (0.2ms) SELECT 1 AS one FROM `coupon_codes` WHERE (code = 'T001') LIMIT 1
D, [2017-08-17T11:08:32.730761 #6788] DEBUG -- : CouponCode Exists (0.2ms) SELECT 1 AS one FROM `coupon_codes` WHERE (code = 'correct') LIMIT 1
=> true
2.1.1 :003 > code = 'wrong'
=> "wrong"
2.1.1 :004 > CouponCode.exists?(['code = ?', "#{code}"])
CouponCode Exists (0.2ms) SELECT 1 AS one FROM `coupon_codes` WHERE (code = 'wjorea') LIMIT 1
D, [2017-08-17T11:09:10.611964 #6788] DEBUG -- : CouponCode Exists (0.2ms) SELECT 1 AS one FROM `coupon_codes` WHERE (code = 'wrong') LIMIT 1
=> false
Again, I'm sure it's something simple and I'm just over thinking it. Sorry if I gave way too much detail... I figured too much is better than not enough. Thank you in advance for any help or direction!
My current code is based off of parts of this Stack Overflow question, if that helps any.
The problem here is the model is not and should not be concerned with controller or view issues. Redirecting to another page is explicitly a controller issue and must be handled directly in the controller.
What you want to do is reduce your model's code to an advisory position, it will advise the controller on how to handle the request. It will not take direct action.
For example:
class CouponCode
def self.code_exists?(code)
self.exists?(code: code)
end
end
Then in the controller:
if (Coupon.code_exists?(params[:code]))
redirect_to(coupon_exists_path(...))
end
Given how simple your check is, though, it's not clear if having such a method in the model is of any use since the alternative is simply:
if (Coupon.exists?(code: params[:code]))
redirect_to(coupon_exists_path(...))
end
That's one character more code on the controller and three lines less on the model.
I'm just not sure how to go about getting it to move on or display an
error.
You need to put that code in the controller. Its the controller's job to handle such things. Also you don't need a model method here. To keep the things straight forward and simple, try the below
def index
if CouponCode.exists?(code: params[:code])
#code for redirect to next page
else
flash.now[:notice] = "Your error message"
end
end
I get the error No route matches {:action=>"index", :controller=>"search"}
When using
link_to "Next Page", {:controller => 'search', :action => 'index'}
My routes.rb contains
resources :search, only: [:index]
The action works fine when I use
link_to "Next Page", '/search'
Rake routes result
Prefix Verb URI Pattern Controller#Action
errors_cookie GET /errors/cookie(.:format) errors#cookie
GET /categories(/:level1)(/:level2)(/:level3)(.:format) search#categories
GET /category/filter/:type(.:format) search#category_filter_sort
brand GET /brand(.:format) search#brand
GET /brand/filter/:type(.:format) search#brand_filter_sort
search_index GET /search(.:format) search#index
search_suggest GET /search/suggest(.:format) search#suggest
search_list GET /search/list(.:format) search#list
GET /search/filter/:type(.:format) search#filter_sort
GET /sd/:slug(.:format) search#show
GET /sd/compare/:id(.:format) search#compare
delete_favourites POST /favourites/delete(.:format) favourites#delete
usuals_favourites GET /favourites/usuals(.:format) favourites#usuals
orders_favourites GET /favourites/orders(.:format) favourites#orders
favourites GET /favourites(.:format) favourites#index
POST /favourites(.:format) favourites#create
Routes for Spree::Core::Engine:
spree_user_omniauth_authorize GET|POST /users/auth/:provider(.:format) spree/omniauth_callbacks#passthru {:provider=>/facebook|twitter|github|google_oauth2|amazon/}
spree_user_omniauth_callback GET|POST /users/auth/:action/callback(.:format) spree/omniauth_callbacks#:action
Routes for Ahoy::Engine:
visits POST /visits(.:format) ahoy/visits#create
events POST /events(.:format) ahoy/events#create
Its a spree app and the controller was inherited from Spree::BaseController.
url_for only sees routes within the spree engine and not globals
Fixed the issue by adding main_app to url_for main_app.url_for(...)
Used this monkey patch for kaminari
Thanks for your time Alexander.
I have the following line of code in a haml file
%a#mypage{:href => hub_path(#user), :class => "#{path.match('(hub)') ? 'current': ''}"}
What this does is ensure the correct item on a navigation bar is highlighted. However, I need the same item to be highlighted if any one of several paths are matched.
So, above we have the path matched to hub. I need it to return true if the path is matched to hub, or item2, or item3.
No idea where to begin. I've tried putting in "||" into the class to see if I could just list them but this didn't work. Is there a way to do "includes" when specifying the match?
continued...
So I took the advice of the posters below but still couldnt' make it work
I'm at this point to test it
- path = request.fullpath
- if path.match(/\(performance_hub|objectives|deliverables\)/)
true
- else
fail
%br
= path
Even though the path is
/users/170/hub
it is still returning false. Where am I going wrong?
Try with regex instead of string
:class => "#{path.match(/\(hub|item2|item3\)/) ? 'current': ''
This will search for (hub) or (item2) or (item3)
The answer ended up being this
%a#mylink{:href => hub_path(#user), :class => "#{%w(hub objective deliverable).any?{|w| path.match(w)} ? 'current': ''}"}
I'm trying to have a drop down list but when i try it it give me
undefined method `collect' for nil:NilClass
the controller:
def existing
#courses = Course.all
end
def duplicate
course = Course.find_by_id(permitd_up[:id])
new_course = course.dup
if new_course.save
redirect_to :action => 'show'
else
redirect_to :back
end
end
the view:
<h3>Choose a Course</h3>
<%= form_for :course , url: {:action => "duplicate" , method: "post"} do |f|%>
<%= f.select :id , #courses.collect{|c| [c.id , c.name]} %>
<br><br>
<%= f.submit%>
<%end%>
You will receive the following error
undefined method `collect' for nil:NilClass
on
<%= f.select :id , #courses.collect{|c| [c.id , c.name]} %>
Only when #courses instance variable was not set in the action that rendered this particular view.
I see that #courses variable is set in the existing method. If you are using existing as an action which renders this view then your view name must be existing.html.erb.
Or if you are rendering the view from a different action then in that case you should set #courses value in that particular action by either directly setting the value within action OR by calling existing method from there.
If you have your courses as a database table, you might want to try using rails' built in field helper collection_select. It will populate your select field with all of the data available in your model. If you want a drop-down like the one you are describing, I believe using collection select is the best way to handle it.
You can read up on it here: http://api.rubyonrails.org/classes/ActionView/Helpers/FormOptionsHelper.html
Alternatively, if you have a ton of courses, maybe try looking into using a text field with autocomplete. Jquery UI has a plugin that makes this very easy. You can check out the railscasts for it here: http://railscasts.com/episodes/102-auto-complete-association-revised.
It requires a pro account but if you do a lot of rails developing it will be the best $9 you spend every month.
If you would like to continue to do it this way, make sure that you are defining
#courses = Courses(:all) in the correct controller action, otherwise you will have nothing to render.