Reputation: 1125
I have tried to implement a switch between a basic and advanced viewing mode on a show page, essentially switching a basic/advanced div on/off through a link. In the controller I store the viewing-mode in a session variable (using a similar approach to http://railscasts.com/episodes/199-mobile-devices). Problem: the toggling works fine changing the viewing mode, but as soon as I click on a link to a different show-page in the non-default viewing-mode it takes me back to the default-mode, why is this?
show.html.erb
<% if viewing_mode? %>
<%= link_to "Advanced", {mode: 0} %>
<% else %>
<%= link_to "Basic", {mode: 1} %>
<% end %>
<% if viewing_mode? %>
<div class="container" id="basic">
This is the basic view
</div>
<% else %>
<div class="container" id="advanced">
This is the advanced view
</div>
<% end %>
Controller
before_filter :prepare_for_viewing
def viewing_mode?
if session[:viewing_param]
session[:viewing_param] == "1"
else
session[:viewing_param] == "0"
end
end
helper_method :viewing_mode?
def prepare_for_viewing
session[:viewing_param] = params[:mode] if params[:mode]
end
Edit 1: Displaying the session parameters shows that the :viewing_params changes from:
"viewing_param"=>"1"
to
"viewing_param"=>"1.json"
after clicking on a link on a show page. This might be the problem, but why is the viewing_param modified in this way?
Edit 2: I got it to work after adding a hack, setting the "a.json" to "a", not a nice solution but it works:
def prepare_for_viewing
session[:viewing_param] = params[:mode][0] if params[:mode]
end
Upvotes: 0
Views: 1578
Reputation:
Had the same problem - session variables wasn't persisted, I've used session variable a lot so I think it's the key thing to recreate the bug
However I've overcome this issue by using cookies instead of session
Just simply instead of
session[:viewing_param] = ..
if session[:viewing_param]
use
cookies[:viewing_param] = ..
if cookies[:viewing_param]
There are advanced options available
cookies[:key] = {
:value => 'dummy value',
:expires => 1.month.from_now,
:domain => 'domainname.com'
}
Here is how to delete it:
cookies.delete(:key, :domain => 'domain.com')
After switching to cookies I wasn't able to spot any non-persisting issues.
Upvotes: 0
Reputation: 1589
This method seems to be incorrect? I made some comments
def viewing_mode?
# this is true for all values except nil and false
if session[:viewing_param]
# should it be test here? Or setting a value?
session[:viewing_param] == "1"
else
# can never be "0" here, because that value gives true in the test above
session[:viewing_param] == "0"
end
end
You are using this:
link_to "Advanced", {mode: 1}
for advanced link, and in this:
before_filter :prepare_for_viewing
def prepare_for_viewing
session[:viewing_param] = params[:mode] if params[:mode]
end
You are setting session[:viewing_param]
to "1"
(when advanced), then in
def viewing_mode?
if session[:viewing_param]
session[:viewing_param] == "1"
else
session[:viewing_param] == "0"
end
end
You are getting true, and that will give you "basic" view because of this:
<% if viewing_mode? %>
<div class="container" id="basic">
This is the basic view
</div>
Upvotes: 1
Reputation: 34166
This is what I think you're trying to do (depending on which mode is the default):
before_filter :prepare_for_viewing
helper_method :advanced_view_mode?, :basic_view_mode?
def advanced_view_mode?
session[:viewing_param] == '1'
end
def basic_view_mode?
!advanced_view_mode?
end
def prepare_for_viewing
session[:viewing_param] = params[:mode] if params[:mode]
end
Also try not to repeat markup, but if you have completely separate views, it might be worth it to render different pages all together.
<div class="container" id="<%= advanced_view_mode? ? 'advanced' : 'basic' %>">
This is common content
<%= render 'advanced/partial' if advanced_view_mode? %>
</div>
Upvotes: 1