Skip to content

[課題管理]学生がレポート提出内容の修正を行えるようにしました #2162

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

Merged
merged 3 commits into from
Apr 24, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
2 changes: 2 additions & 0 deletions app/Enums/LearningtaskUseFunction.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ final class LearningtaskUseFunction extends EnumsBase
const use_report_mail = 'use_'.self::report.'_mail';
const use_report_end = 'use_'.self::report.'_end';
const report_end_at = 'report_end_at';
const use_report_revising = 'use_'.self::report.'_revising';
// [利用する評価機能]
const use_report_evaluate_file = 'use_'.self::report.'_evaluate_file';
const use_report_evaluate_comment = 'use_'.self::report.'_evaluate_comment';
Expand Down Expand Up @@ -98,6 +99,7 @@ final class LearningtaskUseFunction extends EnumsBase
self::use_report_mail => 'メール送信(教員宛)',
self::use_report_end => 'レポート提出終了日時で制御する',
self::report_end_at => 'レポート提出終了日時',
self::use_report_revising => '提出修正',
// 利用する評価機能
self::use_report_evaluate_file => 'アップロード',
self::use_report_evaluate_comment => 'コメント入力',
Expand Down
6 changes: 6 additions & 0 deletions app/Plugins/User/Learningtasks/LearningtasksPlugin.php
Original file line number Diff line number Diff line change
Expand Up @@ -1122,6 +1122,7 @@ public function show($request, $page_id, $frame_id, $post_id)
'examination_files' => $examination_files,
'examinations' => $examinations,
'tool' => $tool,
'deleted_submissions' => $tool->fetchDeletedSubmissions(),
]);
}

Expand Down Expand Up @@ -3031,6 +3032,11 @@ private function changeStatus($request, $page_id, $frame_id, $post_id, $task_sta
$this->sendMailLocal($post, $task_status, $tool, $student_user_id);
}

// 評価前の再提出は、直前の提出の進捗ステータスを削除することで、提出の修正とする。
if ($task_status == 1 && $tool->shouldReviseReportSubmission($post->id)) {
$tool->prepareRevisingReportSubmission();
}

// ユーザーの進捗ステータス保存
LearningtasksUsersStatuses::create([
'post_id' => $post_id,
Expand Down
71 changes: 69 additions & 2 deletions app/Plugins/User/Learningtasks/LearningtasksTool.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
use Illuminate\Support\Facades\Log;

use App\Enums\DayOfWeek;
use App\Enums\LearningtaskUseFunction;
use App\Models\Common\PageRole;
use App\Models\Common\GroupUser;
use App\Models\Common\Page;
Expand Down Expand Up @@ -924,9 +925,12 @@ private function canReportUploadImpl($post_id)
if ($report_status->task_status == 2 && ($report_status->grade == 'A' || $report_status->grade == 'B' || $report_status->grade == 'C')) {
return array(false, 'すでに合格しているため、提出不要です。');
}
// 提出済みがくればfalse、D 評価がくれば再提出でtrue
if ($report_status->task_status == 1) {
// D 評価がくれば再提出でtrue
// 提出済みは締め切り前であれば修正可能
if ($report_status->task_status == 1 && !$this->checkFunction(LearningtaskUseFunction::use_report_revising)) {
$can_report_upload = array(false, '提出済みのため、現在は提出できません。');
} elseif ($report_status->task_status == 1 && $this->checkFunction(LearningtaskUseFunction::use_report_revising)) {
$can_report_upload = $this->checkReportUploadDeadline($can_report_upload);
} elseif ($report_status->task_status == 2 && $report_status->grade == 'D') {
$can_report_upload = array(true, '再提出が必要');

Expand Down Expand Up @@ -1565,4 +1569,67 @@ public function canDeletetableUserStatus($users_statuses_id)
}
return false;
}

/**
* 提出内容が修正可能かを判定する
* @return bool
*/
public function shouldReviseReportSubmission($post_id): bool
{
if ($this->isOutOfDeadlineReportUpload()) {
// 提出期限オーバーなら、修正不可
return false;
}

// 提出内容が未評価の状態であれば、提出内容の修正を可能とする
$submissions = $this->report_statuses->where('post_id', $post_id)->where('task_status', 1);
$evaluations = $this->report_statuses->where('post_id', $post_id)->where('task_status', 2);
$evaluated = $submissions->count() > 0 && $submissions->count() === $evaluations->count(); # 提出は評価済みか
if ($submissions->count() > 0 && !$evaluated) {
return true;
}

Log::debug('shouldReviseReportSubmission checked', [
'submissions_count' => $submissions->count(),
'submissions_details' => $submissions->toArray(),
'evaluations_count' => $evaluations->count(),
'evaluations_details' => $evaluations->toArray(),
'evaluated' => $evaluated,
]);

return false;
}

/**
* 提出内容の修正の前準備
*/
public function prepareRevisingReportSubmission(): void
{
$last_submission = LearningtasksUsersStatuses::where('user_id', $this->student_id)
->where('task_status', 1)
->orderBy('id', 'desc')
->first();

if ($last_submission) {
$last_submission->delete();
}
}

/**
* 削除された提出内容を取得
*/
public function fetchDeletedSubmissions(): Collection
{
$query = LearningtasksUsersStatuses::onlyTrashed()
->where('task_status', 1)
->where('user_id', $this->student_id)
->orderBy('id', 'asc');

// ログインユーザが学生の場合は自身で削除した提出内容のみ
if ($this->isStudent()) {
$query->where('user_id', $this->student_id);
}

return $query->get();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -221,7 +221,22 @@
</div>
</div>
</div>

<div class="form-group row mb-0">
<label class="{{$frame->getSettingLabelClass()}}">提出後の修正</label>
<div class="{{$frame->getSettingInputClass(true)}}">
<div class="custom-control custom-checkbox mr-3">
<input type="checkbox"
name="base_settings[{{LearningtaskUseFunction::use_report_revising}}]"
value="on"
class="custom-control-input"
id="{{LearningtaskUseFunction::use_report_revising}}"
@if(old("base_settings." . LearningtaskUseFunction::use_report_revising, $tool->getFunction(LearningtaskUseFunction::use_report_revising, true)) == 'on') checked="checked" @endif
>
<label class="custom-control-label" for="{{LearningtaskUseFunction::use_report_revising}}">提出後の修正を許可する</label>
<small class="form-text text-muted">評価前もしくは提出期限まで、学生が提出内容の修正を行えます。</small>
</div>
</div>
</div>
<div class="form-group row mb-0">
<label class="{{$frame->getSettingLabelClass()}}">提出期限</label>
<div class="{{$frame->getSettingInputClass(true)}}">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,22 @@
</div>
</div>
</div>

<div class="form-group row mb-0">
<label class="{{$frame->getSettingLabelClass()}}">提出後の修正</label>
<div class="{{$frame->getSettingInputClass(true)}}">
<div class="custom-control custom-checkbox mr-3">
<input type="checkbox"
name="post_settings[{{LearningtaskUseFunction::use_report_revising}}]"
value="on"
class="custom-control-input"
id="{{LearningtaskUseFunction::use_report_revising}}"
@if(old("post_settings." . LearningtaskUseFunction::use_report_revising, $tool->getFunction(LearningtaskUseFunction::use_report_revising, true)) == 'on') checked="checked" @endif
>
<label class="custom-control-label" for="{{LearningtaskUseFunction::use_report_revising}}">提出後の修正を許可する</label>
<small class="form-text text-muted">評価前もしくは提出期限まで、学生が提出内容の修正を行えます。</small>
</div>
</div>
</div>
<div class="form-group row mb-0">
<label class="{{$frame->getSettingLabelClass()}}">提出期限</label>
<div class="{{$frame->getSettingInputClass(true)}}">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -102,42 +102,59 @@

@if ($tool->hasReportStatuses($post->id))
<ol class="mb-3">
@php
$previous_report_submission_id = null;
@endphp
@foreach($tool->getReportStatuses($post->id) as $report_status)
@php
// $report_statusに関する修正履歴を取得する
// 直前の提出と現在の提出の間にある削除されたレコードを修正履歴とする
$submission_revisions = $deleted_submissions->where('id', '>', $previous_report_submission_id)->where('id', '<', $report_status->id);
@endphp
@if (!$loop->last)
<div class="collapse multi-collapse" id="multiCollapseReport{{$loop->iteration}}">
@endif

<li value="{{$loop->iteration}}">{{$report_status->getStstusName($tool->getStudentId())}}
<table class="table table-bordered table-sm report_table">
<tbody>
<tr>
<th>{{$report_status->getStstusPostTimeName()}}</th>
<td>{{$report_status->created_at}}</td>
</tr>
@if ($tool->isUseFunction($report_status->task_status, 'file'))
<tr>
<th>{{$report_status->getUploadFileName()}}</th>
@if (empty($report_status->upload_id))
<td>なし</td>
@else
<td><a href="{{url('/')}}/file/{{$report_status->upload_id}}" target="_blank">{{$report_status->upload->client_original_name}}</a></td>
@endif
</tr>
@endif
@if ($report_status->hasGrade())
<tr>
<th>評価</th>
<td><span class="text-danger font-weight-bold">{{$report_status->grade}}</span></td>
</tr>
@endif
@if ($tool->isUseFunction($report_status->task_status, 'comment'))
<tr>
<th>コメント</th>
<td>{!!nl2br(e($report_status->comment))!!}</td>
</tr>
@endif
</tbody>
</table>
{{-- 修正履歴 --}}
@if ($report_status->task_status == 1 && $submission_revisions->count() > 0)
<small class="text text-muted">(修正済み)</small>
@if ($tool->isTeacher())
<button type="button" class="btn btn-link p-0" data-toggle="modal" data-target="#submissionRevisionsModal{{$loop->iteration}}">
修正履歴を表示
</button>
{{-- Modal --}}
<div class="modal fade" id="submissionRevisionsModal{{$loop->iteration}}" tabindex="-1" role="dialog" aria-labelledby="submissionRevisionsModalLabel{{$loop->iteration}}" aria-hidden="true">
<div class="modal-dialog modal-lg" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="submissionRevisionsModalLabel{{$loop->iteration}}">修正履歴</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="閉じる">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<ul>
@foreach ($submission_revisions as $revision)
{{-- 履歴 --}}
@include('plugins.user.learningtasks.default.learningtasks_show_report_status', ['user_status' => $revision])
<p class="mb-2">
<span class="text-info">{{$revision->deleted_at}} {{$revision->deleted_name}}が修正</span>
</p>
@endforeach
</ul>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-dismiss="modal">閉じる</button>
</div>
</div>
</div>
</div>
@endif
@endif

{{-- 履歴 --}}
@include('plugins.user.learningtasks.default.learningtasks_show_report_status', ['user_status' => $report_status])

@if ($loop->last)
{{-- 履歴削除ボタン:課題管理者機能 --}}
Expand All @@ -147,6 +164,13 @@
@if (!$loop->last)
</div>
@endif

@php
// 修正履歴を取得するため、直前のレポート提出IDを保持
if ($report_status->task_status == 1) {
$previous_report_submission_id = $report_status->id;
}
@endphp
@endforeach
</ol>
@else
Expand All @@ -162,7 +186,12 @@
@if ($tool->checkFunction(LearningtaskUseFunction::use_report_file) || $tool->checkFunction(LearningtaskUseFunction::use_report_comment))

<h5 class="mb-1"><span class="badge badge-secondary" for="status1">提出</span></h5>

{{-- 修正可能のメッセージ --}}
@if ($tool->checkFunction(LearningtaskUseFunction::use_report_revising))
<div class="alert alert-info">
<span class="text-info submit-info-message">評価が確定するまでは提出内容を修正できます。提出済みの内容を修正する場合は、再度レポート提出を行ってください。</span>
</div>
@endif
<form action="{{url('/')}}/redirect/plugin/learningtasks/changeStatus1/{{$page->id}}/{{$frame_id}}/{{$post->id}}#frame-{{$frame_id}}" method="POST" name="form_status1" enctype="multipart/form-data">
{{ csrf_field() }}
<input type="hidden" name="redirect_path" value="{{url('/')}}/plugin/learningtasks/show/{{$page->id}}/{{$frame_id}}/{{$post->id}}#frame-{{$frame_id}}">
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
{{--
* 課題管理記事詳細のレポート履歴テンプレート。
*
* @author 永原 篤 <nagahara@opensource-workshop.jp>
* @author 石垣 佑樹 <ishigaki@opensource-workshop.co.jp>
* @copyright OpenSource-WorkShop Co.,Ltd. All Rights Reserved
* @category 課題管理プラグイン
--}}
<table class="table table-bordered table-sm report_table">
<tbody>
<tr>
<th>{{$user_status->getStstusPostTimeName()}}</th>
<td>{{$user_status->created_at}}</td>
</tr>
@if ($tool->isUseFunction($user_status->task_status, 'file'))
<tr>
<th>{{$user_status->getUploadFileName()}}</th>
@if (empty($user_status->upload_id))
<td>なし</td>
@else
<td><a href="{{url('/')}}/file/{{$user_status->upload_id}}" target="_blank">{{$user_status->upload->client_original_name}}</a></td>
@endif
</tr>
@endif
@if ($user_status->hasGrade())
<tr>
<th>評価</th>
<td><span class="text-danger font-weight-bold">{{$user_status->grade}}</span></td>
</tr>
@endif
@if ($tool->isUseFunction($user_status->task_status, 'comment'))
<tr>
<th>コメント</th>
<td>{!!nl2br(e($user_status->comment))!!}</td>
</tr>
@endif
</tbody>
</table>