0
votes

I want that the admin can change the boolean state of :coach with a link_to to 'true' when it 'false' and to 'false' when it 'true'. Like the delete user link_to.

view/users/index :

<%= will_paginate %>
<ul class="users">
  <%= render @users %>
</ul>
<%= will_paginate %>

views/users/_user :

<li>
<%= link_to image_tag(user.photo.url(:thumb)), user %>
<%= link_to user.fname, user %>
<%= link_to user.lname, user %>
<%= user.email %>
<%= user.coach %>

<% if current_user.admin? && !current_user?(user) %>
    <% if user.coach == false %>
| <%= link_to "Passer coach", user, coach: => :true, method: :edit, 
                              data: { confirm: "Êtes vous sûr ?" } %>
    <% else %>
| <%= link_to "Retirer des coachs", user, coach: => :false, method: :edit, 
                              data: { confirm: "Êtes vous sûr ?" } %>
    <% end %>
<% end %>



<% if current_user.admin? && !current_user?(user) %>
| <%= link_to "Supprimer", user, method: :delete,
                              data: { confirm: "Êtes vous sûr ?" } %>
<% end %> 

controllers/users_controller :

def edit
  @user = User.find(params[:id])
end

def update
  if @user.update_attributes(user_params)
    flash[:success] = "Profil mis à jour"
    redirect_to @user
  else
    render 'edit'
  end
end

def index
  @users = User.where(activated: true).paginate(page: params[:page])
end

private

def user_params
  params.require(:user).permit(:fname, :lname, :email, :password,
                               :password_confirmation, :photo,    :birthdate, :mother_tongue, :coach, spoken_language_ids:[])
end

Route.rb :

resources :users
  get 'signup' => 'users#new'
  post '/signup' => 'users#create'

resources :user do
  post :coach
end

Actual error :

No route matches [POST] "/users/1"

Don"t know how can I put the route. I tried a lot of things, but nothing works, I'm a newbie in dev and Ruby and really need your help, thanks a lot.

This is my users/edit view :

 <% provide(:title, "Paramètres") %>
  <h1>Mettre à jour votre profil</h1>

  <div class="row">
    <div class="col-md-6 col-md-offset-3">
      <%= form_for (@user), :html => { :multipart => true } do |f| %>
        <%= render 'shared/error_messages' %>

  <%= f.label :photo %>
  <%= f.file_field :photo, class: 'form-control' %>

  <%= f.label :Prénom %>
  <%= f.text_field :fname, class: 'form-control' %>

  <%= f.label :Nom %>
  <%= f.text_field :lname, class: 'form-control' %>

  <%= f.label :Date_de_naissance %>
    <%= f.date_select :birthdate, class: 'form-control' %>

  <%= f.label :Langue_maternelle %>
  <%= f.text_field :mother_tongue, class: 'form-control' %>

  <%= f.label :Autres_langues_parlées %>
  <%= f.collection_check_boxes :spoken_language_ids, SpokenLanguage.all, :id, :name do |b| %>
  <div class="collection-check-box">
  <%= b.check_box %>
  <%= b.label %>
  <% end %>

  <%= f.label :Email %>
  <%= f.email_field :email, class: 'form-control' %>

  <%= f.label :Mot_de_passe %>
  <%= f.password_field :password, class: 'form-control' %>

  <%= f.label :Confirmation_mot_de_passe, "Confirmation" %>
  <%= f.password_field :password_confirmation, class: 'form-control' %>

  <%= f.submit "Enregistrer les changements", class: "btn btn-primary" %>
<% end %>

But this part is accessible to all users while switch coach is accessible just for admin

1
Do you know which line triggers the error? Also, coach: => :false this syntax looks wrong to me, should be coach: :false or :coach => :falseivanibash
Try replacing this <%= link_to "Passer coach", user, coach: => :true, method: :edit, data: { confirm: "Êtes vous sûr ?" } %> with <%= link_to "Passer coach", edit_user_path(user), coach: :true, data: { confirm: "Êtes vous sûr ?" } %>ivanibash
I tried your solution, there is no error message. I am redirected to root and the change is not taken into accountBenjamin Richard
Do you have users/edit view?ivanibash
Look in your terminal/console window and check which controller action is being called. After clicking the link there will be a line like Processing by UsersController#update as HTML. Also your coach parameter is not in the right format to be matched by your user_params method - you probably want something like 'user[coach]': :truemikej

1 Answers

0
votes

As you define a route to post :coach you need to use it as path of your link_to
It's in this path you add the params you need (the user and the coach attribute true/false)
This path has to point to a method inside your controller.

Your custom route:

resources :users do
  post :coach
end
#=> output: user_coach POST /users/:user_id/coach(.:format)  users#coach

In your index view (inside the loop of users):

<% if current_user.admin? && !current_user?(user) %>
    <% if user.coach %>
| <%= link_to "Retirer des coachs", user_coach_path(user, coach: false), method: :post %>
    <% else %>
| <%= link_to "Passer coach", user_coach_path(user, coach: true), method: :post %>
    <% end %>
<% end %>

Note : as user.coach returns a boolean you can use it directly as a condition for your if/else statement

Then define the controller method:

  def coach
    user = User.find(params[:user_id])
    user.update(coach: params[:coach])
    redirect_to users_path
  end