Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

アンケートを取れるようにした #8380

Open
wants to merge 25 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
b4b406d
surveysとsurvey_questionsをmentor以下に移動
komagata Mar 2, 2025
7d6a24d
アンケートに回答できるようにした
komagata Mar 2, 2025
2e21625
アンケートの集計結果を表示できるようにした
komagata Mar 3, 2025
07a9776
自明なコメントを削除
komagata Mar 3, 2025
6a1056c
リニアスケールの集計結果に中央値と平均値を追加
komagata Mar 4, 2025
193872b
サブタブUIをコンポーネント化
komagata Mar 4, 2025
c80d674
不要なタブパーシャルを削除
komagata Mar 4, 2025
7b49a66
アンケート結果のグラフ表示
komagata Mar 4, 2025
0c89d82
SubTabComponentとSubTabsComponentのテストを追加
komagata Mar 4, 2025
185fddc
アンケートの回答詳細・集計結果・回答一覧ページのデザインを改善
komagata Mar 4, 2025
f069846
アンケートのテストを追加
komagata Mar 4, 2025
5a31b0f
開始している時だけアンケートに回答できるようにした
komagata Mar 4, 2025
e8fedad
sub_tabs helperの名前を変更
komagata Mar 4, 2025
1e1b623
sub_tabsのテストを作成
komagata Mar 4, 2025
aa3db2e
不要なtest fixtureを削除
komagata Mar 4, 2025
e65112b
メンターページのアンケートのタイトルを統一する修正をした
komagata Mar 4, 2025
bd747f4
survey_resultのクラス構造を変えた
komagata Mar 4, 2025
cca2099
prettierの指摘点を修正
komagata Mar 5, 2025
162303e
落ちているsurveyのテストを修正
komagata Mar 5, 2025
dc9f71c
.clinerulesを.gitignoreに追加
komagata Mar 5, 2025
0f28db9
メニューのアンケートのリンク先を変更
komagata Mar 5, 2025
f1cc03f
アンケートの回答から管理者ユーザーを削除
komagata Mar 5, 2025
7141a42
コメントを英語に変更
komagata Mar 5, 2025
11c8d00
既に回答済みのユーザーがアンケートページにアクセスできないように修正
komagata Mar 5, 2025
94ce078
アンケートページのデザインをメンターページと同様に修正
komagata Mar 5, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,6 @@ storage/

.envrc
/test/reports

/memory-bank
.clinerules
3 changes: 3 additions & 0 deletions app/components/sub_tab_component.html.slim
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
li.tab-nav__item
= link_to link, class: "tab-nav__item-link #{active ? 'is-active' : ''}" do
= name
13 changes: 13 additions & 0 deletions app/components/sub_tab_component.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
# frozen_string_literal: true

class SubTabComponent < ViewComponent::Base
def initialize(name:, link:, active: false)
@name = name
@link = link
@active = active
end

private

attr_reader :name, :link, :active
end
6 changes: 6 additions & 0 deletions app/components/sub_tabs_component.html.slim
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
nav.tab-nav
.container
ul.tab-nav__items
- tabs.each do |tab|
- tab[:active] = active_tab == tab[:name]
= render SubTabComponent.new(**tab)
12 changes: 12 additions & 0 deletions app/components/sub_tabs_component.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# frozen_string_literal: true

class SubTabsComponent < ViewComponent::Base
def initialize(tabs:, active_tab:)
@tabs = tabs
@active_tab = active_tab
end

private

attr_reader :tabs, :active_tab
end
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# frozen_string_literal: true

class SurveyQuestionsController < ApplicationController
class Mentor::SurveyQuestionsController < ApplicationController
before_action :set_survey_question, only: %i[edit update]
before_action :require_admin_or_mentor_login

Expand All @@ -22,7 +22,7 @@ def create
@survey_question.user_id = current_user.id

if @survey_question.save
redirect_to survey_questions_path, notice: '質問を保存しました。'
redirect_to mentor_survey_questions_path, notice: '質問を保存しました。'
else
render action: :new
end
Expand All @@ -32,7 +32,7 @@ def edit; end

def update
if @survey_question.update(survey_question_params)
redirect_to survey_questions_path, notice: '質問を保存しました。'
redirect_to mentor_survey_questions_path, notice: '質問を保存しました。'
else
render action: :edit
end
Expand Down
20 changes: 20 additions & 0 deletions app/controllers/mentor/surveys/survey_answers_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# frozen_string_literal: true

class Mentor::Surveys::SurveyAnswersController < ApplicationController
before_action :require_admin_or_mentor_login
before_action :set_survey

def index
@survey_answers = @survey.survey_answers.includes(:user, survey_question_answers: :survey_question)
end

def show
@survey_answer = @survey.survey_answers.includes(:user, survey_question_answers: :survey_question).find(params[:id])
end

private

def set_survey
@survey = Survey.find(params[:survey_id])
end
end
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
# frozen_string_literal: true

class Surveys::SurveyQuestionListingsController < ApplicationController
class Mentor::Surveys::SurveyQuestionListingsController < ApplicationController
before_action :require_admin_or_mentor_login
before_action :set_survey

def index
@survey_question_listings = @survey.survey_question_listings.includes(:survey_question).order(:position)
end

private

def set_survey
@survey = Survey.find(params[:survey_id])
@survey_question_listings = @survey.survey_question_listings.order(:position)
end
end
23 changes: 23 additions & 0 deletions app/controllers/mentor/surveys/survey_result_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# frozen_string_literal: true

class Mentor::Surveys::SurveyResultController < ApplicationController
before_action :require_admin_or_mentor_login
before_action :set_survey, only: %i[show]

def show
@survey_questions = @survey
.survey_questions
.includes(
:linear_scale,
radio_button: :radio_button_choices,
check_box: :check_box_choices
)
@survey_answers = @survey.survey_answers.includes(survey_question_answers: :survey_question)
end

private

def set_survey
@survey = Survey.find(params[:survey_id])
end
end
78 changes: 78 additions & 0 deletions app/controllers/mentor/surveys_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
# frozen_string_literal: true

class Mentor::SurveysController < ApplicationController
before_action :require_admin_or_mentor_login
before_action :set_survey, only: %i[show edit update destroy]

def index
@surveys = Survey.order(end_at: :desc)
end

def show
@survey_questions = @survey
.survey_questions
.includes(
:linear_scale,
radio_button: :radio_button_choices,
check_box: :check_box_choices
)
end

def new
@survey = Survey.new(
start_at: Time.current.beginning_of_day,
end_at: Time.current.end_of_day.strftime('%Y-%m-%dT-%H:%M')
)
@survey.survey_question_listings.build
end

def edit; end

def create
@survey = Survey.new(survey_params)
@survey.user_id = current_user.id
if @survey.save
redirect_to mentor_surveys_path, notice: notice_message(@survey)
else
render action: :new
end
end

def update
if @survey.update(survey_params)
redirect_to mentor_surveys_path, notice: notice_message(@survey)
else
render :edit
end
end

def destroy
@survey.destroy
redirect_to mentor_surveys_path, notice: 'アンケートを削除しました。'
end

private

def set_survey
@survey = Survey.find(params[:id])
end

def survey_params
params.require(:survey).permit(
:title,
:start_at,
:end_at,
:description,
survey_question_listings_attributes: %i[id survey_id survey_question_id _destroy]
)
end

def notice_message(survey)
case params[:action]
when 'create'
survey.before_start? ? 'アンケートを受付前として保存しました。' : 'アンケートを作成しました。'
when 'update'
survey.before_start? ? 'アンケートを受付前として保存しました。' : 'アンケートを更新しました。'
end
end
end
100 changes: 100 additions & 0 deletions app/controllers/surveys/survey_answers_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
# frozen_string_literal: true

class Surveys::SurveyAnswersController < ApplicationController
skip_before_action :require_active_user_login
before_action :set_survey
before_action :check_survey_period
before_action :check_already_answered

def create
@survey_answer = SurveyAnswer.new(survey: @survey, user: current_user)

if @survey_answer.save
save_question_answers
redirect_to root_path, notice: 'アンケートに回答しました。'
else
@survey_questions = @survey
.survey_questions
.includes(
:linear_scale,
radio_button: :radio_button_choices,
check_box: :check_box_choices
)
render 'surveys/show'
end
end

private

def set_survey
@survey = Survey.find(params[:survey_id])
end

def check_survey_period
if @survey.before_start?
redirect_to root_path, alert: 'このアンケートはまだ回答期間ではありません。'
elsif @survey.answer_ended?
redirect_to root_path, alert: 'このアンケートの回答期間は終了しました。'
end
end

def check_already_answered
return unless SurveyAnswer.exists?(survey: @survey, user: current_user)

redirect_to root_path, alert: 'このアンケートには既に回答済みです。'
end

def save_question_answers
params[:survey_question].each do |question_id, answer_params|
survey_question = SurveyQuestion.find(question_id)

case survey_question.format
when 'radio_button', 'linear_scale'
save_single_answer(survey_question, answer_params)
when 'check_box'
save_multiple_answers(survey_question, answer_params)
when 'text_area', 'text_field'
save_text_answer(survey_question, answer_params)
end
end
end

def save_single_answer(survey_question, answer_params)
answer = answer_params[:answer]
reason = get_reason(survey_question, answer_params)

@survey_answer.survey_question_answers.create(survey_question:, answer:, reason:)
end

def save_multiple_answers(survey_question, answer_params)
answer_params.each do |choice, value|
next if choice == 'title_of_reason_for_checkbox' || value != '1'

reason = nil
if survey_question.check_box.check_box_choices.exists?(choices: choice, reason_for_choice_required: true)
reason = answer_params[:title_of_reason_for_checkbox]
end

answer = choice
@survey_answer.survey_question_answers.create(survey_question:, answer:, reason:)
end
end

def save_text_answer(survey_question, answer_params)
@survey_answer.survey_question_answers.create(
survey_question:,
answer: answer_params
)
end

def get_reason(survey_question, answer_params)
case survey_question.format
when 'radio_button'
if survey_question.radio_button.radio_button_choices.exists?(choices: answer_params[:answer], reason_for_choice_required: true)
answer_params[:title_of_reason]
end
when 'linear_scale'
answer_params[:title_of_reason_for_linear_scale] if survey_question.linear_scale.reason_for_choice_required
end
end
end
Loading