create api for dashboard client portal

This commit is contained in:
Muhammad Fajar
2022-12-06 18:48:31 +07:00
parent b26ccdd0e6
commit 723c9f1895
6 changed files with 213 additions and 41 deletions

View File

@@ -0,0 +1,75 @@
<?php
namespace Modules\Client\Http\Controllers\Api;
use Illuminate\Contracts\Support\Renderable;
use Illuminate\Http\Request;
use Illuminate\Routing\Controller;
use Illuminate\Support\Facades\Auth;
class CorporateController extends Controller
{
/**
* Display a listing of the resource.
* @return Renderable
*/
public function index(Request $request)
{
$userLogin = Auth::user();
$corporate = $userLogin->managedCorporates()->select(['corporates.id', 'corporates.name'])->get();
// corporate policy, all member list, notification
return response()->json($corporate);
}
/**
* Store a newly created resource in storage.
* @param Request $request
* @return Renderable
*/
public function store(Request $request)
{
}
/**
* Show the specified resource.
* @param int $id
* @return Renderable
*/
public function show($corporate_id)
{
//
}
/**
* Show the form for editing the specified resource.
* @param int $id
* @return Renderable
*/
public function edit($id)
{
return view('client::edit');
}
/**
* Update the specified resource in storage.
* @param Request $request
* @param int $id
* @return Renderable
*/
public function update(Request $request, $id)
{
//
}
/**
* Remove the specified resource from storage.
* @param int $id
* @return Renderable
*/
public function destroy($id)
{
//
}
}

View File

@@ -5,6 +5,8 @@ namespace Modules\Client\Http\Controllers\Api;
use Illuminate\Contracts\Support\Renderable; use Illuminate\Contracts\Support\Renderable;
use Illuminate\Http\Request; use Illuminate\Http\Request;
use Illuminate\Routing\Controller; use Illuminate\Routing\Controller;
use Illuminate\Support\Facades\Auth;
use Modules\Client\Transformers\DashboardResources;
class DashboardController extends Controller class DashboardController extends Controller
{ {
@@ -12,18 +14,12 @@ class DashboardController extends Controller
* Display a listing of the resource. * Display a listing of the resource.
* @return Renderable * @return Renderable
*/ */
public function index() public function index(Request $request)
{ {
$user = auth()->user(); $user = Auth::user();
$data = DashboardResources::make($user->managedCorporates()->where('active', 1)->with('currentPolicy', 'employees')->first());
$corporate = $user->managedCorporates() return response()->json($data);
->withCount('employees')
->with(['policies' => function ($policy) {
$policy->limit(1)->latest();
}])
->first();
return response()->json(compact('corporate'));
} }
/** /**

View File

@@ -5,6 +5,7 @@ namespace Modules\Client\Http\Controllers\Api;
use Illuminate\Contracts\Support\Renderable; use Illuminate\Contracts\Support\Renderable;
use Illuminate\Http\Request; use Illuminate\Http\Request;
use Illuminate\Routing\Controller; use Illuminate\Routing\Controller;
use Illuminate\Support\Facades\Auth;
class UserController extends Controller class UserController extends Controller
{ {
@@ -14,7 +15,10 @@ class UserController extends Controller
*/ */
public function index() public function index()
{ {
return response()->json(auth()->user()); $userLogin = Auth::user();
$corporateSelected = $userLogin->managedCorporates()->select('corporates.id')->where('active', 1)->first();
return response()->json(['user' => $userLogin, 'corporate' => $corporateSelected]);
} }
/** /**

View File

@@ -1,6 +1,7 @@
<?php <?php
use Modules\Client\Http\Controllers\Api\AuthController; use Modules\Client\Http\Controllers\Api\AuthController;
use Modules\Client\Http\Controllers\Api\CorporateController;
use Modules\Client\Http\Controllers\Api\DashboardController; use Modules\Client\Http\Controllers\Api\DashboardController;
use Modules\Client\Http\Controllers\Api\MemberController; use Modules\Client\Http\Controllers\Api\MemberController;
use Modules\Client\Http\Controllers\Api\UserController; use Modules\Client\Http\Controllers\Api\UserController;
@@ -29,6 +30,8 @@ Route::prefix('client')->group(function () {
Route::get('/user', [UserController::class, 'index']); Route::get('/user', [UserController::class, 'index']);
Route::get('dashboard', [DashboardController::class, 'index']); Route::get('dashboard', [DashboardController::class, 'index']);
Route::get('corporate', [CorporateController::class, 'index']);
Route::get('corporate/{corporate_id}', [CorporateController::class, 'show']);
Route::get('members', [MemberController::class, 'index']); Route::get('members', [MemberController::class, 'index']);
}); });
}); });

View File

@@ -1,5 +1,13 @@
// @mui // @mui
import { Typography, Container, Grid } from '@mui/material'; import {
Typography,
Container,
Grid,
FormControl,
InputLabel,
MenuItem,
Select,
} from '@mui/material';
// hooks // hooks
import useSettings from '../../hooks/useSettings'; import useSettings from '../../hooks/useSettings';
// components // components
@@ -8,6 +16,11 @@ import Page from '../../components/Page';
import CardNotification from '../../sections/dashboard/CardNotification'; import CardNotification from '../../sections/dashboard/CardNotification';
import CardBalance from '../../sections/dashboard/CardBalance'; import CardBalance from '../../sections/dashboard/CardBalance';
import TableList from '../../sections/dashboard/TableList'; import TableList from '../../sections/dashboard/TableList';
import { useEffect, useState } from 'react';
import axios from '../../utils/axios';
import { Stack } from '@mui/system';
import { SelectChangeEvent } from '@mui/material/Select';
import useAuth from '../../hooks/useAuth';
// ---------------------------------------------------------------------- // ----------------------------------------------------------------------
@@ -20,22 +33,93 @@ const itemList = [
// ---------------------------------------------------------------------- // ----------------------------------------------------------------------
/* ---------------------------------- types --------------------------------- */
type CorporateDataProps = {
id: number;
name: string;
};
type CardBalanceProps = {
myLimit: {
balance: number;
total: number;
percentage: number;
};
lockLimit: {
balance: number;
percentage: number;
};
};
/* -------------------------------------------------------------------------- */
export default function Dashboard() { export default function Dashboard() {
const { themeStretch } = useSettings(); const { themeStretch } = useSettings();
const { user } = useAuth();
// @ts-ignore
const [corporateValue, setCorporateValue] = useState(`${user.corporate.id}`);
const [corporateData, setCorporateData] = useState([]);
const [policyData, setPolicyData] = useState<CardBalanceProps>({
myLimit: {
balance: 0,
total: 0,
percentage: 0,
},
lockLimit: {
balance: 0,
percentage: 0,
},
});
const handleCorporateChange = (event: SelectChangeEvent) => {
setCorporateValue(event.target.value as string);
};
useEffect(() => {
(async () => {
const corporates = await axios.get('corporate');
const dashboard = await axios.get('dashboard');
setCorporateData(corporates.data);
setPolicyData(dashboard.data.policy);
})();
}, [user, corporateValue]);
return ( return (
<Page title="Dashboard"> <Page title="Dashboard">
<Container maxWidth={themeStretch ? false : 'xl'}> <Container maxWidth={themeStretch ? false : 'xl'}>
<Typography variant="h3" component="h1" paragraph> <Stack direction="row" justifyContent="space-between">
Dashboard <Typography variant="h3" component="h1" paragraph>
</Typography> Dashboard
</Typography>
<FormControl>
<InputLabel id="simple-corporate-select-lable">Corporate</InputLabel>
<Select
labelId="simple-corporate-select-lable"
id="corporate-select-lable"
value={corporateValue}
label="Corporate"
defaultValue={corporateValue}
onChange={handleCorporateChange}
>
{corporateData.map((row: CorporateDataProps, index) => (
<MenuItem key={index} value={row.id}>
{row.name}
</MenuItem>
))}
</Select>
</FormControl>
</Stack>
<Grid container spacing={2}> <Grid container spacing={2}>
<Grid item xs={12} lg={6} md={12}> <Grid item xs={12} lg={6} md={12}>
<CardNotification data={itemList} /> <CardNotification data={itemList} />
</Grid> </Grid>
<Grid item xs={12} lg={6} md={12}> <Grid item xs={12} lg={6} md={12}>
<CardBalance /> <CardBalance data={policyData} />
</Grid> </Grid>
<Grid item xs={12} lg={12} md={12}> <Grid item xs={12} lg={12} md={12}>
<TableList /> <TableList />

View File

@@ -14,23 +14,29 @@ import Iconify from '../../components/Iconify';
import { useState } from 'react'; import { useState } from 'react';
// utils // utils
import { fCurrency } from '../../utils/formatNumber'; import { fCurrency } from '../../utils/formatNumber';
// <sections></sections> /* -------------------------------- sections -------------------------------- */
import DialogTopUpLimit from './DialogTopUpLimit'; import DialogTopUpLimit from './DialogTopUpLimit';
import DialogClaimSubmitMember from './DialogClaimSubmitMember'; import DialogClaimSubmitMember from './DialogClaimSubmitMember';
// ---------------------------------------------------------------------- /* ---------------------------------- types --------------------------------- */
type DataMembers = { type CardBalanceProps = {
name: string; data: {
memberId: string; myLimit: {
saldo: string; balance: number;
total: number;
percentage: number;
};
lockLimit: {
balance: number;
percentage: number;
};
};
}; };
type NotificationProps = { /* -------------------------------------------------------------------------- */
data?: { members: DataMembers[] };
};
// ---------------------------------------------------------------------- /* --------------------------------- styled --------------------------------- */
const RootBalanceStyle = styled(Card)(({ theme }) => ({ const RootBalanceStyle = styled(Card)(({ theme }) => ({
boxShadow: 'none', boxShadow: 'none',
@@ -52,19 +58,15 @@ const BorderLinearProgress = styled(LinearProgress)(({ theme }) => ({
}, },
})); }));
// ---------------------------------------------------------------------- /* -------------------------------------------------------------------------- */
const INITIAL = '500.000.000'; export default function CardBalance(props: CardBalanceProps) {
const TOTAL = 375000000;
const PERCENT = 75;
// ----------------------------------------------------------------------
export default function CardBalance({ data }: NotificationProps) {
const [openDialog, setOpenDialog] = useState(false); const [openDialog, setOpenDialog] = useState(false);
const [dialogTitle, setDialogTitle] = useState(''); const [dialogTitle, setDialogTitle] = useState('');
const [isDialog, setIsDialog] = useState(''); const [isDialog, setIsDialog] = useState('');
const { myLimit, lockLimit } = props.data;
const clickHandler = (isDialog: string) => { const clickHandler = (isDialog: string) => {
switch (isDialog) { switch (isDialog) {
case 'submitClaim': case 'submitClaim':
@@ -91,18 +93,26 @@ export default function CardBalance({ data }: NotificationProps) {
<Typography variant="body2" component="span" sx={{ opacity: 0.72 }}> <Typography variant="body2" component="span" sx={{ opacity: 0.72 }}>
Total Limit Total Limit
</Typography> </Typography>
<Typography sx={{ typography: 'body2' }}>{fCurrency(TOTAL)}</Typography> <Typography sx={{ typography: 'body2' }}>
<Typography sx={{ typography: 'caption', color: '#919EAB' }}>/ {INITIAL}</Typography> {fCurrency(myLimit ? myLimit.balance : 0)}
</Typography>
<Typography sx={{ typography: 'caption', color: '#919EAB' }}>
/ {myLimit ? myLimit.total : 0}
</Typography>
</div> </div>
<Stack direction="row" alignItems="center" justifyContent="center"> <Stack direction="row" alignItems="center" justifyContent="center">
<Typography variant="h5" sx={{ ml: 0.5 }}> <Typography variant="h5" sx={{ ml: 0.5 }}>
{PERCENT}% {myLimit ? myLimit.percentage : 0}%
</Typography> </Typography>
</Stack> </Stack>
</Stack> </Stack>
<BorderLinearProgress variant="determinate" value={PERCENT} sx={{ mb: 1 }} /> <BorderLinearProgress
variant="determinate"
value={myLimit ? myLimit.percentage : 0}
sx={{ mb: 1 }}
/>
<Stack sx={{ backgroundColor: '#B2E8E8', paddingY: 1, paddingX: 1.5, mb: 2 }}> <Stack sx={{ backgroundColor: '#B2E8E8', paddingY: 1, paddingX: 1.5, mb: 2 }}>
<Typography sx={{ typography: 'caption', display: 'flex', alignItems: 'center' }}> <Typography sx={{ typography: 'caption', display: 'flex', alignItems: 'center' }}>
@@ -113,11 +123,11 @@ export default function CardBalance({ data }: NotificationProps) {
sx={{ color: '#424242', marginRight: '6px' }} sx={{ color: '#424242', marginRight: '6px' }}
/> />
<Typography variant="caption" component="span"> <Typography variant="caption" component="span">
Lock Fund ( 25% ) Lock Fund ( {lockLimit ? lockLimit.percentage : 0}% )
</Typography> </Typography>
</Typography> </Typography>
<Typography sx={{ typography: 'caption', color: '#637381' }}> <Typography sx={{ typography: 'caption', color: '#637381' }}>
125.000.000 / 125.000.000 {lockLimit ? lockLimit.balance : 0}
</Typography> </Typography>
</Stack> </Stack>
@@ -146,7 +156,7 @@ export default function CardBalance({ data }: NotificationProps) {
openDialog={openDialog} openDialog={openDialog}
setOpenDialog={setOpenDialog} setOpenDialog={setOpenDialog}
title={{ name: dialogTitle }} title={{ name: dialogTitle }}
data={data?.members} // data={data?.members}
/> />
)} )}