学生向けプログラミング入門 | 無料

学生向けにプログラミングを無料で解説。Java、C++、Ruby、PHP、データベース、Ruby on Rails, Python, Django

Rails7.1 | 動画学習アプリ作成 | 31 | 購入プロジェクト表示

↓↓クリックして頂けると励みになります。



30 | サブスクリプション】 << 【ホーム】 >> 【32 | Stripe





購入したプロジェクトを表示させるページを作成します。


「app\controllers\project_controller.rb」ファイルに以下の記述を追加します。


記述追加 app\controllers\projects_controller.rb(4,5行目)

before_action :authenticate_user!, except: [:show], only: [:list]
before_action :set_project, except: [:new, :create, :show, :index, :list]



app\controllers\projects_controller.rb

class ProjectsController < ApplicationController

  protect_from_forgery except: [:upload_photo]
  before_action :authenticate_user!, except: [:show], only: [:list]
  before_action :set_project, except: [:new, :create, :show, :index, :list]
  before_action :is_authorised, only: [:naming, :pricing, :description, :photo_upload, :update]

  def index
  	@projects = Project.all
  end

  def new
    @project = current_user.projects.build
  end

  def create
    @project = current_user.projects.build(project_params)
    if @project.save
      redirect_to naming_project_path(@project), notice: "保存しました"
    else
      redirect_to request.referrer, flash: { error: @project.errors.full_messages }
    end
  end

  def update
    new_params = project_params
    new_params = project_params.merge(active: true) if is_ready_project

    if @project.update(new_params)
      flash[:notice] = "保存しました。"
    else
      flash[:alert] = { error: @project.errors.full_messages }
    end
    redirect_back(fallback_location: request.referer)
  end

  def show
  	@project = Project.find(params[:id])
  	@tasks = @project.tasks.order(:tag)
    @i = 0
    @images = @project.images
    @joined = false
    @users = @project.users.order('created_at desc').first(10)

    if !current_user.nil? && !current_user.projects.nil?
        @joined = current_user.projects.include?(@project)
    end    
  end

  def edit
    @project = Project.find(params[:id])
  	@tasks = @project.tasks.order(:tag)
  end

  def upload_photo
    @project.images.attach(params[:file])
    render json: { success: true }
  end

  def delete_photo
    @image = ActiveStorage::Attachment.find(params[:photo_id])
    @image.purge
    redirect_to photo_upload_project_path(@project)
  end

  def list
    if !current_user.nil?
      @projects = current_user.projects
    end
  end

  private
  def set_project
    @project = Project.find(params[:id])
  end

  def project_params
    params.require(:project).permit(:name, :content, :price, :description, :images, :active)
  end

  def is_authorised
    redirect_to root_path, alert: "権限がありません。" unless current_user.id == @project.user_id
  end
  
  def is_ready_project
    !@project.active && !@project.price.blank? && !@project.name.blank? && !@project.images.blank? && !@project.description.blank?
  end

end



ルートの設定をします。


記述追加 config\routes.rb(10行目)

get '/myprojects', to: 'projects#list'



config\routes.rb

Rails.application.routes.draw do

  # ルートを app\views\pages\home.html.erb に設定
  root 'pages#home'

  # get
  get 'pages/home'
  get '/dashboard', to: 'users#dashboard'
  get '/users/:id', to: 'users#show', as: 'user'
  get '/myprojects', to: 'projects#list'

  # post
  post '/users/edit', to: 'users#update'
  post '/free', to: 'charges#free'

  # device
  devise_for :users, 
    path: '', 
    path_names: {sign_up: 'register', sign_in: 'login', edit: 'profile', sign_out: 'logout'},
    controllers: {omniauth_callbacks: 'omniauth_callbacks', registrations: 'registrations'}

  resources :projects do
    member do
      get 'naming'
      get 'pricing'
      get 'description'
      get 'photo_upload'
      delete :delete_photo
      post :upload_photo
    end
    resources :tasks, only: [:show, :index]
  end

  resources :tasks, except: [:edit] do
    member do
      get 'naming'
      get 'description'
      get 'video'
      get 'code'
    end
  end

  # Define your application routes per the DSL in https://guides.rubyonrails.org/routing.html

  # Reveal health status on /up that returns 200 if the app boots with no exceptions, otherwise 500.
  # Can be used by load balancers and uptime monitors to verify that the app is live.
  get "up" => "rails/health#show", as: :rails_health_check

  # Defines the root path route ("/")
  # root "posts#index"
end



「app\views\projects」フォルダに「list.html.erb」ファイルを新規作成します。


app\views\projects\list.html.erb(新規作成したファイル)

<div class="container mt-4 mb-4">
    <div class="row">
        <!-- 左側 -->
        <div class="col-md-4 mb-4">
            <div class="card">
                <div class="card-body">
                    <!-- ステータス -->
                    <div>
                        <% if current_user.status %>
                            <span class="badge bg-success"><i class="fa-regular fa-bell"></i>オンライン</span>
                        <% else %>
                            <span class="btn btn-secondary"><i class="fa-regular fa-bell-slash"></i>オフライン</span>
                        <% end %>                                   
                    </div>                
                    <!-- アバター -->
                    <%= image_tag avatar_url(current_user), class: "img-fluid img-thumbnail rounded-pill" %>
                    <h4 class="text-center"><%= current_user.full_name %></h4>   
                    
                    <!-- 自己紹介 -->
                    <div class="h5 text-center"><%= current_user.about %></div>                           
                </div>
            </div>       

        </div>
        <!-- 右側 -->
        <div class="col-md-8">

            <!-- 購入したプロジェクト -->
            <div class="card mb-4">           
                <div class="card-body">
                    <h5 class="card-title"><%= current_user.full_name %>さんが購入したプロジェクト</h5>
                    <div class="row">

                    <% if @projects.count > 0 %>
                        <% @projects.each do |project| %>

                            <div class="col-md-4">
                                <div class="card mb-2">
                                    <%= link_to project_path(project), data: { turbo: false} do %>
                                        <%= image_tag project_cover(project), style: "width: 100%;", class: "card-img-top" %>
                                    <% end %>                                    
                                    <div class="card-body">    

                                        <%= link_to project_path(project), data: { turbo: false} do %>
                                            <h5 class="card-title">
                                                <span class="btn btn-light"><%= project.name %></span>
                                            </h5>
                                        <% end %>
                                        <div class="font2" style="color: black; margin: 5px;">タスク&nbsp;&nbsp;<i class="far fa-clock"></i> <%= project.tasks.count %></div>
                                        <%= link_to  "プロジェクトを開始", project_path(project), class: "btn btn-outline-success" %>                    
                                    </div>
                                </div>
                            </div>

                        <% end %>

                    <%  else %>
                        <div class="container">
                            <div class="card">
                                <div class="card-body">
                                    <div class="h4 font2">購入しているプロジェクトはありません。</div>
                                </div>
                            </div>
                        </div>

                    <% end %>
                    </div>
                </div>
            </div>
        </div>     
    </div>
</div>


ブラウザ確認
http://localhost:3000/myprojects


購入したプロジェクトが表示されます。

PCレイアウト
PCレイアウト


モバイルレイアウト
モバイルレイアウト



ナビゲーションバーにリンクを追加します。


記述追加 app\views\shared\_navbar.html.erb
39行目に以下の記述を追加します。

<li><%= link_to  "購入したプロジェクト", myprojects_path, class: "dropdown-item btn btn-light" %></li>


<nav class="navbar navbar-expand-lg bg-body-tertiary">
  <div class="container-fluid">
    <a class="navbar-brand" href="/"><span class="font1">StreamAcademe</span></a>
    <button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
      <span class="navbar-toggler-icon"></span>
    </button>
    <div class="collapse navbar-collapse" id="navbarSupportedContent">
      <ul class="navbar-nav me-auto mb-2 mb-lg-0">
        <!-- もしログインしていなかったら-->
        <% if (!user_signed_in?) %>
        <li class="nav-item" style="margin-bottom: 0.1rem;">
          <span style="margin-left: 1rem;">
          <%= link_to  "新規登録", new_user_registration_path, class: "btn btn-danger" %>
          </span>
        </li>
        <li class="nav-item">
          <span style="margin-left: 1rem;">
            <%= link_to  "ログイン", new_user_session_path, class: "btn btn-success text-light" %>
          </span>
        </li>
      </ul>
      <!-- ログインしていたら -->
      <% else %>
      <ul class="navbar-nav" style="margin-left: 2rem;">
        <li class="nav-item dropdown">
          <a class="nav-link dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">

          <figure style="position:relative; top: 0.2rem;" class="avatar <%= current_user.status ? "online" : "offline" %>"></figure>  
          <%= image_tag avatar_url(current_user), class: "bd-placeholder-img figure-img img-fluid rounded-pill", style: "width: 40px; height: 30px;" %>          
            <%= current_user.full_name %>
          </a>
          <ul class="dropdown-menu">
            <li><%= link_to  "ダッシュボード", dashboard_path, class: "dropdown-item btn btn-lightt" %></li>
            <li><%= link_to  "ユーザ登録情報編集", edit_user_registration_path, class: "dropdown-item btn btn-light" %></li>
            <li><hr class="dropdown-divider"><span class="badge bg-danger" style="margin-left: 1rem;">先生</span></li>
            <li><%= link_to  "プロジェクトを新規登録", new_project_path, class: "dropdown-item btn btn-light" %></li>
            <li><%= link_to  "タスクを新規登録", new_task_path, class: "dropdown-item btn btn-light" %></li>
            <li><hr class="dropdown-divider"><span class="badge bg-primary" style="margin-left: 1rem;">生徒</span></li>
            <li><%= link_to  "購入したプロジェクト", myprojects_path, class: "dropdown-item btn btn-light" %></li>
            <li><%= link_to  "プロジェクト一覧", projects_path, class: "dropdown-item btn btn-light" %></li>
            <li><hr class="dropdown-divider"></li>
            <li><%= button_to  "ログアウト", destroy_user_session_path, method: :delete, class: "dropdown-item btn btn-light" %></li>
          </ul>
        </li>
      </ul>
      <% end %>

    </div>
  </div>
</nav>



ブラウザを確認します。

ナビゲーションバーにリンク追加
ナビゲーションバーにリンク追加



30 | サブスクリプション】 << 【ホーム】 >> 【32 | Stripe



↓↓クリックして頂けると励みになります。