You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel Livewire按日期在表格中展示foreach循环数据问题

问题:Laravel Livewire考勤数据按日期表格展示格式错误

我尝试在Laravel Livewire中按日期将考勤数据展示为表格(预期每行对应一个学生,每列对应当月的每一天,单元格显示当天考勤状态),但当前输出的表格格式不符合预期,试过if条件和switch语句都无效。

数据库结构

id  |     name      |student_id   |  date_of_attendance |   attendance |
1   |    john       |    STD_01   |     2024-01-01      |       P      |
2   |    john       |    STD_01   |     2024-01-03      |       P      |
2   |    john       |    STD_01   |     2024-01-04      |       A      |
3   |    sean       |    STD_02   |     2024-01-01      |       P      |
4   |    sean       |    STD_02   |     2024-01-03      |       P      |
2   |    sean       |    STD_02   |     2024-01-04      |       P      |

控制器代码

public function AttendanceReport() 
{
    $this->validate(); // 从表单属性$this->ReportOfMonth获取月份请求
    
    $MonthToNumber =  Carbon::parse($this->ReportOfMonth)->month;

    $this->StudentListForAttendance = Attendance::whereMonth('date_of_attendance', '=', $MonthToNumber)->get();
    $this->dateRange = CarbonPeriod::create(now()->startOfMonth(), now()->endOfMonth())->toArray();

    $grouped =  $this->StudentListForAttendance
            ->sortBy('date_of_attendance', SORT_NATURAL)
            ->groupBy(['student_registration_id']); 
    $this->Attendance_Data = $grouped->all();
}

Blade视图代码

<table class="datatable table">
    <thead> 
        @if(!empty($this->dateRange)) 
            <tr>
                <th>NAME</th>
                <th>IDNo</th> 
                @foreach ($this->dateRange as $key=>$date) 
                    <th>{{$date->format('d')}}</th>
                @endforeach
            </tr> 
        @endif
    </thead>
    <tbody>
        @if(!empty($this->Attendance_Data))
            @foreach ($this->Attendance_Data as $key=>$Attendance_Datas)
                <tr>
                    <td>{{$Attendance_Datas[0]->student_name}}</td>
                    <td>{{$Attendance_Datas[0]->reg_id}}</td> 
                    @foreach ($Attendance_Datas as $key=>$Attendance)
                        <td>{{$Attendance->attendance}}</td>
                    @endforeach
                </tr>
            @endforeach 
        @endif 
    </tbody>
</table>  

尝试过的无效代码

@foreach ($Attendance_Datas as $key=>$Attendance) 
    @if( \Carbon\Carbon::createFromFormat('Y-m-d', $Attendance->date_of_attendance)->format('d') == 1 ) 
    // 我把这段复制了31次对应一个月的每一天
    <td>
        {\Carbon\Carbon::createFromFormat('Y-m-d', $Attendance->date_of_attendance)->format('d')}
        {{$Attendance->attendance}}
    </td> 
    @else 
        - 
    @endif 
@endforeach

解决方案

1. 优化控制器数据处理逻辑

问题出在数据分组后未按日期索引,且dateRange生成的是当前月份而非选中月份。修改控制器代码如下:

public function AttendanceReport() 
{
    $this->validate();

    $selectedMonth = Carbon::parse($this->ReportOfMonth);
    $MonthToNumber = $selectedMonth->month;

    // 获取选中月份的所有考勤数据
    $this->StudentListForAttendance = Attendance::whereMonth('date_of_attendance', '=', $MonthToNumber)->get();
    
    // 生成选中月份的日期范围(而非当前月份)
    $this->dateRange = CarbonPeriod::create(
        $selectedMonth->startOfMonth(),
        $selectedMonth->endOfMonth()
    )->toArray();

    // 按学生分组,并将每个学生的考勤数据按"日"作为键名索引
    $grouped = $this->StudentListForAttendance
        ->sortBy('date_of_attendance')
        ->groupBy('student_registration_id')
        ->map(function ($attendances) {
            return $attendances->keyBy(function ($item) {
                return Carbon::parse($item->date_of_attendance)->format('d');
            });
        });
    
    $this->Attendance_Data = $grouped->all();
}

2. 修改Blade视图渲染逻辑

之前的视图遍历学生的考勤记录,导致缺卡日期没有对应的<td>,列数和表头不匹配。现在改为遍历当月所有日期,每个日期对应一列,查找该学生当天的考勤状态:

<table class="datatable table">
    <thead> 
        @if(!empty($this->dateRange)) 
            <tr>
                <th>NAME</th>
                <th>IDNo</th> 
                @foreach ($this->dateRange as $date) 
                    <th>{{$date->format('d')}}</th>
                @endforeach
            </tr> 
        @endif
    </thead>
    <tbody>
        @if(!empty($this->Attendance_Data))
            @foreach ($this->Attendance_Data as $studentAttendances)
                <tr>
                    <td>{{ $studentAttendances->first()->student_name }}</td>
                    <td>{{ $studentAttendances->first()->reg_id }}</td>
                    @foreach ($this->dateRange as $date)
                        @php
                            $day = $date->format('d');
                            // 根据日期的"日"查找对应考勤
                            $attendance = $studentAttendances->get($day);
                        @endphp
                        <td>{{ $attendance ? $attendance->attendance : '-' }}</td>
                    @endforeach
                </tr>
            @endforeach 
        @endif 
    </tbody>
</table>  

说明

  • 控制器中通过keyBy将每个学生的考勤数据按日期的"日"作为键名,方便视图中快速查找。
  • 视图遍历当月所有日期,每个日期生成一个<td>,有考勤则显示状态,无考勤则显示-,保证表头和内容列数一致,格式符合预期。

内容的提问来源于stack exchange,提问作者p22222222

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 05:14:55