add report page
This commit is contained in:
parent
61364b3b28
commit
44cfb2b170
@ -2,6 +2,8 @@
|
|||||||
|
|
||||||
namespace App\Http\Controllers;
|
namespace App\Http\Controllers;
|
||||||
|
|
||||||
|
use App\Models\Payment;
|
||||||
|
use Carbon\Carbon;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
|
|
||||||
class AdminController extends Controller
|
class AdminController extends Controller
|
||||||
@ -10,4 +12,45 @@ public function index()
|
|||||||
{
|
{
|
||||||
return view('home');
|
return view('home');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function groupAndSumPaymentsByYear($payments)
|
||||||
|
{
|
||||||
|
return $payments->groupBy(function($payment){
|
||||||
|
/** @var Payment $payment */
|
||||||
|
return $payment->created_at->month;
|
||||||
|
})->map(function($payments){
|
||||||
|
return $payments->sum('amount');
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public function reports()
|
||||||
|
{
|
||||||
|
$today = Carbon::today();
|
||||||
|
$paymentsInThisYear = Payment::whereBetween(
|
||||||
|
'created_at',
|
||||||
|
[$today->startOfYear()->toDateTimeString(), $today->endOfYear()->toDateTimeString()]
|
||||||
|
)->get();
|
||||||
|
$thisYearPaymentGroup = $this->groupAndSumPaymentsByYear($paymentsInThisYear);
|
||||||
|
|
||||||
|
$lastYearToday = $today->clone()->modify('-1 year');
|
||||||
|
$paymentsInLastYear = Payment::whereBetween(
|
||||||
|
'created_at',
|
||||||
|
[$lastYearToday->startOfYear()->toDateTimeString(), $lastYearToday->endOfYear()->toDateTimeString()]
|
||||||
|
)->get();
|
||||||
|
$lastYearPaymentGroup = $this->groupAndSumPaymentsByYear($paymentsInLastYear);
|
||||||
|
|
||||||
|
$data = [
|
||||||
|
'thisYearPaymentGroup' => [
|
||||||
|
'values' => $thisYearPaymentGroup->toArray(),
|
||||||
|
'year' => $today->year,
|
||||||
|
'sum' => $thisYearPaymentGroup->sum(),
|
||||||
|
],
|
||||||
|
'lastYearPaymentGroup' => [
|
||||||
|
'values' => $lastYearPaymentGroup->toArray(),
|
||||||
|
'year' => $lastYearToday->year,
|
||||||
|
'sum' => $lastYearPaymentGroup->sum(),
|
||||||
|
],
|
||||||
|
];
|
||||||
|
return view('reports', ['data' => $data]);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -22,6 +22,7 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@popperjs/core": "^2.11.5",
|
"@popperjs/core": "^2.11.5",
|
||||||
"bootstrap-icons": "^1.8.1",
|
"bootstrap-icons": "^1.8.1",
|
||||||
|
"chart.js": "^3.7.1",
|
||||||
"jquery": "^3.6.0",
|
"jquery": "^3.6.0",
|
||||||
"vue": "^3.2.33"
|
"vue": "^3.2.33"
|
||||||
}
|
}
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
@ -1,4 +1,4 @@
|
|||||||
{
|
{
|
||||||
"/js/app.js": "/js/app.js?id=3708582450858c2bd8e9b20e7002c94e",
|
"/js/app.js": "/js/app.js?id=ba48982294b1dbf988a7fa821aec293d",
|
||||||
"/css/app.css": "/css/app.css?id=4fd1d10a16883c28c2618d1eff851e13"
|
"/css/app.css": "/css/app.css?id=4fd1d10a16883c28c2618d1eff851e13"
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1 +1,56 @@
|
|||||||
require('./bootstrap');
|
require('./bootstrap');
|
||||||
|
import {
|
||||||
|
Chart,
|
||||||
|
ArcElement,
|
||||||
|
LineElement,
|
||||||
|
BarElement,
|
||||||
|
PointElement,
|
||||||
|
BarController,
|
||||||
|
BubbleController,
|
||||||
|
DoughnutController,
|
||||||
|
LineController,
|
||||||
|
PieController,
|
||||||
|
PolarAreaController,
|
||||||
|
RadarController,
|
||||||
|
ScatterController,
|
||||||
|
CategoryScale,
|
||||||
|
LinearScale,
|
||||||
|
LogarithmicScale,
|
||||||
|
RadialLinearScale,
|
||||||
|
TimeScale,
|
||||||
|
TimeSeriesScale,
|
||||||
|
Decimation,
|
||||||
|
Filler,
|
||||||
|
Legend,
|
||||||
|
Title,
|
||||||
|
Tooltip,
|
||||||
|
SubTitle
|
||||||
|
} from 'chart.js';
|
||||||
|
|
||||||
|
Chart.register(
|
||||||
|
ArcElement,
|
||||||
|
LineElement,
|
||||||
|
BarElement,
|
||||||
|
PointElement,
|
||||||
|
BarController,
|
||||||
|
BubbleController,
|
||||||
|
DoughnutController,
|
||||||
|
LineController,
|
||||||
|
PieController,
|
||||||
|
PolarAreaController,
|
||||||
|
RadarController,
|
||||||
|
ScatterController,
|
||||||
|
CategoryScale,
|
||||||
|
LinearScale,
|
||||||
|
LogarithmicScale,
|
||||||
|
RadialLinearScale,
|
||||||
|
TimeScale,
|
||||||
|
TimeSeriesScale,
|
||||||
|
Decimation,
|
||||||
|
Filler,
|
||||||
|
Legend,
|
||||||
|
Title,
|
||||||
|
Tooltip,
|
||||||
|
SubTitle
|
||||||
|
);
|
||||||
|
window.Chart = Chart
|
||||||
|
|||||||
@ -43,6 +43,9 @@
|
|||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<a class="nav-link" href="{{ route('adm.payment.index') }}">Payment</a>
|
<a class="nav-link" href="{{ route('adm.payment.index') }}">Payment</a>
|
||||||
</li>
|
</li>
|
||||||
|
<li class="nav-item">
|
||||||
|
<a class="nav-link" href="{{ route('adm.reports') }}">Reports</a>
|
||||||
|
</li>
|
||||||
@endauth
|
@endauth
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
|
|||||||
@ -10,8 +10,8 @@
|
|||||||
<th>ID</th>
|
<th>ID</th>
|
||||||
<th>專案</th>
|
<th>專案</th>
|
||||||
<th>類別</th>
|
<th>類別</th>
|
||||||
<th>狀態</th>
|
|
||||||
<th>金額</th>
|
<th>金額</th>
|
||||||
|
<th>日期</th>
|
||||||
<th></th>
|
<th></th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
@ -22,6 +22,7 @@
|
|||||||
<td>{{ $payment->project->title }}</td>
|
<td>{{ $payment->project->title }}</td>
|
||||||
<td>{{ __('enums.payment_type.' . $payment->type) }}</td>
|
<td>{{ __('enums.payment_type.' . $payment->type) }}</td>
|
||||||
<td>{{ $payment->amount }}</td>
|
<td>{{ $payment->amount }}</td>
|
||||||
|
<td>{{ $payment->created_at }}</td>
|
||||||
<td>
|
<td>
|
||||||
<a href="{{ route('adm.payment.show', [$payment->id]) }}" class="btn btn-sm btn-primary">
|
<a href="{{ route('adm.payment.show', [$payment->id]) }}" class="btn btn-sm btn-primary">
|
||||||
<i class="bi bi-eye"></i>
|
<i class="bi bi-eye"></i>
|
||||||
|
|||||||
59
resources/views/reports.blade.php
Normal file
59
resources/views/reports.blade.php
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
@extends('layouts.app')
|
||||||
|
|
||||||
|
@section('content')
|
||||||
|
<div class="container">
|
||||||
|
<div class="row justify-content-center">
|
||||||
|
<div class="col-6">
|
||||||
|
今年 ({{ $data['thisYearPaymentGroup']['year'] }}) 總收入 : {{ $data['thisYearPaymentGroup']['sum'] }}
|
||||||
|
<canvas id="myChart" width="400" height="400"></canvas>
|
||||||
|
<script>
|
||||||
|
let D = {{ Js::from( $data['thisYearPaymentGroup']['values']) }},
|
||||||
|
dataset = Array(12).fill(0)
|
||||||
|
for(let i in dataset) {
|
||||||
|
i = parseInt(i)
|
||||||
|
if(D[i + 1] !== undefined) {
|
||||||
|
dataset[i] = D[i + 1]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const ctx = document.getElementById('myChart');
|
||||||
|
const myChart = new Chart(ctx, {
|
||||||
|
type: 'bar',
|
||||||
|
data: {
|
||||||
|
labels: [1 ,2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
|
||||||
|
datasets: [{
|
||||||
|
label: '收入',
|
||||||
|
data: dataset,
|
||||||
|
backgroundColor: [
|
||||||
|
'rgba(255, 99, 132, 0.2)',
|
||||||
|
'rgba(54, 162, 235, 0.2)',
|
||||||
|
'rgba(255, 206, 86, 0.2)',
|
||||||
|
'rgba(75, 192, 192, 0.2)',
|
||||||
|
'rgba(153, 102, 255, 0.2)',
|
||||||
|
'rgba(255, 159, 64, 0.2)'
|
||||||
|
],
|
||||||
|
borderColor: [
|
||||||
|
'rgba(255, 99, 132, 1)',
|
||||||
|
'rgba(54, 162, 235, 1)',
|
||||||
|
'rgba(255, 206, 86, 1)',
|
||||||
|
'rgba(75, 192, 192, 1)',
|
||||||
|
'rgba(153, 102, 255, 1)',
|
||||||
|
'rgba(255, 159, 64, 1)'
|
||||||
|
],
|
||||||
|
borderWidth: 1
|
||||||
|
}]
|
||||||
|
},
|
||||||
|
options: {
|
||||||
|
scales: {
|
||||||
|
y: {
|
||||||
|
beginAtZero: true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
@endsection
|
||||||
@ -22,7 +22,9 @@
|
|||||||
|
|
||||||
Route::middleware('auth')->prefix('adm')->as('adm.')->group(callback: function(){
|
Route::middleware('auth')->prefix('adm')->as('adm.')->group(callback: function(){
|
||||||
|
|
||||||
Route::get('/', [AdminController::class, 'index'])->name('adm.index');
|
Route::get('/', [AdminController::class, 'index'])->name('index');
|
||||||
|
|
||||||
|
Route::get('reports', [AdminController::class, 'reports'])->name('reports');
|
||||||
|
|
||||||
Route::resource('client', \App\Http\Controllers\ClientController::class);
|
Route::resource('client', \App\Http\Controllers\ClientController::class);
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user