Home > Software design >  hide "edit" and "destroy" unless logged in as admin
hide "edit" and "destroy" unless logged in as admin

Time:05-26

I made Authentication in the rails blog project, but those who log in to the site, that is, admin can edit and destroy, guest user cannot edit destroy. I'm very new to rails and I don't know what to add. and how to make guest user login? guest user only read.

index.html

<div >
      <div >
        <% @articles.each do |article| %>
          <div >
            <div >
              <div >
                <strong ><%= article.title %></strong>
                <h3 ></h3>
                <div ><%= article.created_at.strftime("%d.%m.%Y %H:%M") %>
    
                </div>
                <p><%= article.text.truncate(110) %></p>
                <div>
                <%= link_to "Read more", article_path(article)%><br/><br/>
                <tr>
                  <%= link_to 'Show', article_path(article),class:"btn btn-outline-success btn-sm"%>
                  <%= link_to 'Edit', edit_article_path(article),class:"btn btn-outline-warning btn-sm"%>
                  <%= link_to 'Destroy', article_path(article),class:"btn btn-outline-danger btn-sm",
                          method: :delete,
                          data: { confirm: 'Are you sure?' } %>
                </tr>
                </div>
              </div>
            </div>
    
          </div>
    
        <% end %>
      </div>
      <br/><br/>
      <%= link_to 'New article', new_article_path,class:"btn btn-dark" %>
    
        <%# sayfada show, edit, destroy butonları aktive oldu %>
    </div>

application_controller.rb

class ApplicationController < ActionController::Base
  protect_from_forgery with: :exception

  before_action :authenticate_user!
end

articles_controller.rb

class ArticlesController < ApplicationController

  def index
    @articles = Article.all
  end

  def show
    @article = Article.find(params[:id])
  end

  def new
    @article = Article.new
  end

  def edit
    @article = Article.find(params[:id])
  end

  def create
    @article = Article.new(article_params)

    if @article.save
      redirect_to @article
    else
      render 'new'
    end
  end

  def update
    @article = Article.find(params[:id])

    if @article.update(article_params)
      redirect_to @article
    else
      render 'edit'
    end
  end

  def destroy
    @article = Article.find(params[:id])
    @article.destroy

    redirect_to articles_path
  end

  private
    def article_params
      params.require(:article).permit(:title, :text)
    end
end

CodePudding user response:

You haven't mentioned how you implemented authentication - I am assuming you added the gem Devise by looking at your code, but anyway you will have to somehow store each user's role. For example add an admin column to your User model

rails g migration AddsAdminColumnToUsers

def change
   add_column :users, :admin, :boolean, default: false, null: false
end

and then force this requirement in your views and controller

  <% if current_user.admin? %>
    <%= link_to 'Edit', edit_article_path(article),class:"btn btn-outline-warning btn-sm"%>
    <%= link_to 'Destroy', article_path(article),class:"btn btn-outline-danger btn-sm",
                      method: :delete,
                      data: { confirm: 'Are you sure?' } %>
<% end %>

    
class ArticlesController < ApplicationController
     def destroy
        raise "unauthorized" unless current_user.admin?
        @article = Article.find(params[:id])
        @article.destroy

        redirect_to articles_path
     end
     
     def edit
        raise "unauthorized" unless current_user.admin?
        ...
      end
 end

Many people use gems like Rolify and CanCan but for simple needs this approach can work without any gems.

  • Related