Commit efc8dc34 by Farendi Giotivano R.P

update view mahasiswa dosen upload

parent 6fe4511e
...@@ -16,7 +16,7 @@ DB_PASSWORD= ...@@ -16,7 +16,7 @@ DB_PASSWORD=
BROADCAST_DRIVER=log BROADCAST_DRIVER=log
CACHE_DRIVER=file CACHE_DRIVER=file
QUEUE_CONNECTION=sync QUEUE_CONNECTION=sync
SESSION_DRIVER=file SESSION_DRIVER=database
SESSION_LIFETIME=120 SESSION_LIFETIME=120
REDIS_HOST=127.0.0.1 REDIS_HOST=127.0.0.1
......
<?php
namespace App\Actions\Fortify;
use App\Models\Team;
use App\Models\User;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Validator;
use Laravel\Fortify\Contracts\CreatesNewUsers;
use Laravel\Jetstream\Jetstream;
class CreateNewUser implements CreatesNewUsers
{
use PasswordValidationRules;
/**
* Create a newly registered user.
*
* @param array $input
* @return \App\Models\User
*/
public function create(array $input)
{
Validator::make($input, [
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'string', 'email', 'max:255', 'unique:users'],
'password' => $this->passwordRules(),
'terms' => Jetstream::hasTermsAndPrivacyPolicyFeature() ? ['accepted', 'required'] : '',
])->validate();
return DB::transaction(function () use ($input) {
return tap(User::create([
'name' => $input['name'],
'email' => $input['email'],
'password' => Hash::make($input['password']),
]), function (User $user) {
$this->createTeam($user);
});
});
}
/**
* Create a personal team for the user.
*
* @param \App\Models\User $user
* @return void
*/
protected function createTeam(User $user)
{
$user->ownedTeams()->save(Team::forceCreate([
'user_id' => $user->id,
'name' => explode(' ', $user->name, 2)[0]."'s Team",
'personal_team' => true,
]));
}
}
<?php
namespace App\Actions\Fortify;
use Laravel\Fortify\Rules\Password;
trait PasswordValidationRules
{
/**
* Get the validation rules used to validate passwords.
*
* @return array
*/
protected function passwordRules()
{
return ['required', 'string', new Password, 'confirmed'];
}
}
<?php
namespace App\Actions\Fortify;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Validator;
use Laravel\Fortify\Contracts\ResetsUserPasswords;
class ResetUserPassword implements ResetsUserPasswords
{
use PasswordValidationRules;
/**
* Validate and reset the user's forgotten password.
*
* @param mixed $user
* @param array $input
* @return void
*/
public function reset($user, array $input)
{
Validator::make($input, [
'password' => $this->passwordRules(),
])->validate();
$user->forceFill([
'password' => Hash::make($input['password']),
])->save();
}
}
<?php
namespace App\Actions\Fortify;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Validator;
use Laravel\Fortify\Contracts\UpdatesUserPasswords;
class UpdateUserPassword implements UpdatesUserPasswords
{
use PasswordValidationRules;
/**
* Validate and update the user's password.
*
* @param mixed $user
* @param array $input
* @return void
*/
public function update($user, array $input)
{
Validator::make($input, [
'current_password' => ['required', 'string'],
'password' => $this->passwordRules(),
])->after(function ($validator) use ($user, $input) {
if (! isset($input['current_password']) || ! Hash::check($input['current_password'], $user->password)) {
$validator->errors()->add('current_password', __('The provided password does not match your current password.'));
}
})->validateWithBag('updatePassword');
$user->forceFill([
'password' => Hash::make($input['password']),
])->save();
}
}
<?php
namespace App\Actions\Fortify;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Support\Facades\Validator;
use Illuminate\Validation\Rule;
use Laravel\Fortify\Contracts\UpdatesUserProfileInformation;
class UpdateUserProfileInformation implements UpdatesUserProfileInformation
{
/**
* Validate and update the given user's profile information.
*
* @param mixed $user
* @param array $input
* @return void
*/
public function update($user, array $input)
{
Validator::make($input, [
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'email', 'max:255', Rule::unique('users')->ignore($user->id)],
'photo' => ['nullable', 'mimes:jpg,jpeg,png', 'max:1024'],
])->validateWithBag('updateProfileInformation');
if (isset($input['photo'])) {
$user->updateProfilePhoto($input['photo']);
}
if ($input['email'] !== $user->email &&
$user instanceof MustVerifyEmail) {
$this->updateVerifiedUser($user, $input);
} else {
$user->forceFill([
'name' => $input['name'],
'email' => $input['email'],
])->save();
}
}
/**
* Update the given verified user's profile information.
*
* @param mixed $user
* @param array $input
* @return void
*/
protected function updateVerifiedUser($user, array $input)
{
$user->forceFill([
'name' => $input['name'],
'email' => $input['email'],
'email_verified_at' => null,
])->save();
$user->sendEmailVerificationNotification();
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Support\Facades\Gate;
use Illuminate\Support\Facades\Validator;
use Laravel\Jetstream\Contracts\AddsTeamMembers;
use Laravel\Jetstream\Events\AddingTeamMember;
use Laravel\Jetstream\Events\TeamMemberAdded;
use Laravel\Jetstream\Jetstream;
use Laravel\Jetstream\Rules\Role;
class AddTeamMember implements AddsTeamMembers
{
/**
* Add a new team member to the given team.
*
* @param mixed $user
* @param mixed $team
* @param string $email
* @param string|null $role
* @return void
*/
public function add($user, $team, string $email, string $role = null)
{
Gate::forUser($user)->authorize('addTeamMember', $team);
$this->validate($team, $email, $role);
$newTeamMember = Jetstream::findUserByEmailOrFail($email);
AddingTeamMember::dispatch($team, $newTeamMember);
$team->users()->attach(
$newTeamMember, ['role' => $role]
);
TeamMemberAdded::dispatch($team, $newTeamMember);
}
/**
* Validate the add member operation.
*
* @param mixed $team
* @param string $email
* @param string|null $role
* @return void
*/
protected function validate($team, string $email, ?string $role)
{
Validator::make([
'email' => $email,
'role' => $role,
], $this->rules(), [
'email.exists' => __('We were unable to find a registered user with this email address.'),
])->after(
$this->ensureUserIsNotAlreadyOnTeam($team, $email)
)->validateWithBag('addTeamMember');
}
/**
* Get the validation rules for adding a team member.
*
* @return array
*/
protected function rules()
{
return array_filter([
'email' => ['required', 'email', 'exists:users'],
'role' => Jetstream::hasRoles()
? ['required', 'string', new Role]
: null,
]);
}
/**
* Ensure that the user is not already on the team.
*
* @param mixed $team
* @param string $email
* @return \Closure
*/
protected function ensureUserIsNotAlreadyOnTeam($team, string $email)
{
return function ($validator) use ($team, $email) {
$validator->errors()->addIf(
$team->hasUserWithEmail($email),
'email',
__('This user already belongs to the team.')
);
};
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Support\Facades\Gate;
use Illuminate\Support\Facades\Validator;
use Laravel\Jetstream\Contracts\CreatesTeams;
use Laravel\Jetstream\Events\AddingTeam;
use Laravel\Jetstream\Jetstream;
class CreateTeam implements CreatesTeams
{
/**
* Validate and create a new team for the given user.
*
* @param mixed $user
* @param array $input
* @return mixed
*/
public function create($user, array $input)
{
Gate::forUser($user)->authorize('create', Jetstream::newTeamModel());
Validator::make($input, [
'name' => ['required', 'string', 'max:255'],
])->validateWithBag('createTeam');
AddingTeam::dispatch($user);
$user->switchTeam($team = $user->ownedTeams()->create([
'name' => $input['name'],
'personal_team' => false,
]));
return $team;
}
}
<?php
namespace App\Actions\Jetstream;
use Laravel\Jetstream\Contracts\DeletesTeams;
class DeleteTeam implements DeletesTeams
{
/**
* Delete the given team.
*
* @param mixed $team
* @return void
*/
public function delete($team)
{
$team->purge();
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Support\Facades\DB;
use Laravel\Jetstream\Contracts\DeletesTeams;
use Laravel\Jetstream\Contracts\DeletesUsers;
class DeleteUser implements DeletesUsers
{
/**
* The team deleter implementation.
*
* @var \Laravel\Jetstream\Contracts\DeletesTeams
*/
protected $deletesTeams;
/**
* Create a new action instance.
*
* @param \Laravel\Jetstream\Contracts\DeletesTeams $deletesTeams
* @return void
*/
public function __construct(DeletesTeams $deletesTeams)
{
$this->deletesTeams = $deletesTeams;
}
/**
* Delete the given user.
*
* @param mixed $user
* @return void
*/
public function delete($user)
{
DB::transaction(function () use ($user) {
$this->deleteTeams($user);
$user->deleteProfilePhoto();
$user->tokens->each->delete();
$user->delete();
});
}
/**
* Delete the teams and team associations attached to the user.
*
* @param mixed $user
* @return void
*/
protected function deleteTeams($user)
{
$user->teams()->detach();
$user->ownedTeams->each(function ($team) {
$this->deletesTeams->delete($team);
});
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Support\Facades\Gate;
use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Facades\Validator;
use Illuminate\Validation\Rule;
use Laravel\Jetstream\Contracts\InvitesTeamMembers;
use Laravel\Jetstream\Events\InvitingTeamMember;
use Laravel\Jetstream\Jetstream;
use Laravel\Jetstream\Mail\TeamInvitation;
use Laravel\Jetstream\Rules\Role;
class InviteTeamMember implements InvitesTeamMembers
{
/**
* Invite a new team member to the given team.
*
* @param mixed $user
* @param mixed $team
* @param string $email
* @param string|null $role
* @return void
*/
public function invite($user, $team, string $email, string $role = null)
{
Gate::forUser($user)->authorize('addTeamMember', $team);
$this->validate($team, $email, $role);
InvitingTeamMember::dispatch($team, $email, $role);
$invitation = $team->teamInvitations()->create([
'email' => $email,
'role' => $role,
]);
Mail::to($email)->send(new TeamInvitation($invitation));
}
/**
* Validate the invite member operation.
*
* @param mixed $team
* @param string $email
* @param string|null $role
* @return void
*/
protected function validate($team, string $email, ?string $role)
{
Validator::make([
'email' => $email,
'role' => $role,
], $this->rules($team), [
'email.unique' => __('This user has already been invited to the team.'),
])->after(
$this->ensureUserIsNotAlreadyOnTeam($team, $email)
)->validateWithBag('addTeamMember');
}
/**
* Get the validation rules for inviting a team member.
*
* @param mixed $team
* @return array
*/
protected function rules($team)
{
return array_filter([
'email' => ['required', 'email', Rule::unique('team_invitations')->where(function ($query) use ($team) {
$query->where('team_id', $team->id);
})],
'role' => Jetstream::hasRoles()
? ['required', 'string', new Role]
: null,
]);
}
/**
* Ensure that the user is not already on the team.
*
* @param mixed $team
* @param string $email
* @return \Closure
*/
protected function ensureUserIsNotAlreadyOnTeam($team, string $email)
{
return function ($validator) use ($team, $email) {
$validator->errors()->addIf(
$team->hasUserWithEmail($email),
'email',
__('This user already belongs to the team.')
);
};
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Auth\Access\AuthorizationException;
use Illuminate\Support\Facades\Gate;
use Illuminate\Validation\ValidationException;
use Laravel\Jetstream\Contracts\RemovesTeamMembers;
use Laravel\Jetstream\Events\TeamMemberRemoved;
class RemoveTeamMember implements RemovesTeamMembers
{
/**
* Remove the team member from the given team.
*
* @param mixed $user
* @param mixed $team
* @param mixed $teamMember
* @return void
*/
public function remove($user, $team, $teamMember)
{
$this->authorize($user, $team, $teamMember);
$this->ensureUserDoesNotOwnTeam($teamMember, $team);
$team->removeUser($teamMember);
TeamMemberRemoved::dispatch($team, $teamMember);
}
/**
* Authorize that the user can remove the team member.
*
* @param mixed $user
* @param mixed $team
* @param mixed $teamMember
* @return void
*/
protected function authorize($user, $team, $teamMember)
{
if (! Gate::forUser($user)->check('removeTeamMember', $team) &&
$user->id !== $teamMember->id) {
throw new AuthorizationException;
}
}
/**
* Ensure that the currently authenticated user does not own the team.
*
* @param mixed $teamMember
* @param mixed $team
* @return void
*/
protected function ensureUserDoesNotOwnTeam($teamMember, $team)
{
if ($teamMember->id === $team->owner->id) {
throw ValidationException::withMessages([
'team' => [__('You may not leave a team that you created.')],
])->errorBag('removeTeamMember');
}
}
}
<?php
namespace App\Actions\Jetstream;
use Illuminate\Support\Facades\Gate;
use Illuminate\Support\Facades\Validator;
use Laravel\Jetstream\Contracts\UpdatesTeamNames;
class UpdateTeamName implements UpdatesTeamNames
{
/**
* Validate and update the given team's name.
*
* @param mixed $user
* @param mixed $team
* @param array $input
* @return void
*/
public function update($user, $team, array $input)
{
Gate::forUser($user)->authorize('update', $team);
Validator::make($input, [
'name' => ['required', 'string', 'max:255'],
])->validateWithBag('updateTeamName');
$team->forceFill([
'name' => $input['name'],
])->save();
}
}
<?php
if (!function_exists('tglbulanindo')) {
function tglbulanindo($waktu, $tipe = '')
{
$detik = substr($waktu, 17, 2);
$menit = substr($waktu, 14, 2);
$jam = substr($waktu, 11, 2);
$tgl = substr($waktu, 8, 2);
$bln = substr($waktu, 5, 2);
$thn = substr($waktu, 0, 4);
$bulan = ['Januari', 'Februari', 'Maret', 'April', 'Mei', 'Juni', 'Juli', 'Agustus', 'September', 'Oktober', 'November', 'Desember'];
$idxhari = date('N', strtotime($waktu));
switch ($tipe) {
case 1:
$full = $tgl.' '.$bulan[(int) $bln - 1].' '.$thn;
break;
case 2:
$full = $tgl.'/'.$bln.'/'.$thn;
break;
case 3:
$full = $tgl.'/'.$bln.'/'.$thn.' '.$jam.':'.$menit.':'.$detik;
break;
case 4:
$full = $tgl.' '.$bulan[(int) $bln - 1].' '.$thn.' '.$jam.':'.$menit;
break;
default:
$full = "$tgl ".$bulan[(int) $bln - 1]." $thn";
}
return $full;
}
}
<?php
namespace App\Helpers;
class InseoHelper
{
public static function tglbulanindo($waktu, $tipe = '')
{
$detik = substr($waktu, 17, 2);
$menit = substr($waktu, 14, 2);
$jam = substr($waktu, 11, 2);
$tgl = substr($waktu, 8, 2);
$bln = substr($waktu, 5, 2);
$thn = substr($waktu, 0, 4);
$bulan = ['Januari', 'Februari', 'Maret', 'April', 'Mei', 'Juni', 'Juli', 'Agustus', 'September', 'Oktober', 'Nopember', 'Desember'];
$idxhari = date('N', strtotime($waktu));
switch ($tipe) {
case 1:
$full = $tgl.' '.$bulan[(int) $bln - 1].' '.$thn;
break;
case 2:
$full = $tgl.'/'.$bln.'/'.$thn;
break;
case 3:
$full = $tgl.'/'.$bln.'/'.$thn.' '.$jam.':'.$menit.':'.$detik;
break;
default:
$full = "$tgl ".$bulan[(int) $bln - 1]." $thn";
}
return $full;
}
public static function singkatan_fakultas()
{
$fak = [
'teknik' => 'FT',
'fakultas teknik' => 'FT',
'ft' => 'FT',
'fak. teknik' => 'FT',
'ilmu sosial & hukum' => 'FISH',
'fakultas ilmu sosial & hukum' => 'FISH',
'fish' => 'FISH',
'fak. ilmu sosial & hukum' => 'FISH',
'ilmu sosial dan hukum' => 'FISH',
'ilmu pendidikan' => 'FIP',
'fakultas ilmu pendidikan' => 'FIP',
'fip' => 'FIP',
'fak. ilmu pendidikan' => 'FIP',
'bahasa dan seni' => 'FBS',
'fakultas bahasa dan seni' => 'FBS',
'fbs' => 'FBS',
'fak. bahasa dan seni' => 'FBS',
'matematika dan ilmu pengetahuan alam' => 'FMIPA',
'fakultas matematika dan ilmu pengetahuan alam' => 'FMIPA',
'fmipa' => 'FMIPA',
'fak. matematika dan ilmu pengetahuan alam' => 'FMIPA',
'ilmu keolahragaan' => 'FIO',
'fakultas ilmu keolahragaan' => 'FIO',
'fio' => 'FIO',
'fak. ilmu keolahragaan' => 'FIO',
'ilmu olahraga' => 'FIO',
'fakultas ilmu olahraga' => 'FIO',
'fiK' => 'FIO',
'fak. ilmu olahraga' => 'FIO',
'ekonomi' => 'FE',
'fakultas ekonomi' => 'FE',
'fe' => 'FE',
'fak. ekonomi' => 'FE',
];
return $fak;
}
}
<?php
namespace App\Http\Controllers\Authentication;
use App\Http\Controllers\Controller;
use App\Repositories\Auth\BiodataRepository;
use App\Repositories\Auth\EmailRepository;
use App\Repositories\Auth\IsdmRepository;
use App\Repositories\Auth\RoleRepository;
use App\Repositories\Auth\SsoRepository;
use App\Repositories\Auth\UserRepository;
use App\Repositories\UserdetailRepository;
use Auth;
use Illuminate\Support\Str;
class LoginController extends Controller
{
private $ssoRepo;
private $userRepo;
private $roleRepo;
private $biodataRepo;
private $emailRepo;
private $isdmRepo;
private $userDetailRepo;
public function __construct(
SsoRepository $ssoRepo,
UserRepository $userRepo,
RoleRepository $roleRepo,
BiodataRepository $biodataRepo,
EmailRepository $emailRepo,
IsdmRepository $isdmRepo,
UserdetailRepository $userDetailRepo
) {
$this->middleware('guest');
$this->ssoRepo = $ssoRepo;
$this->userRepo = $userRepo;
$this->roleRepo = $roleRepo;
$this->biodataRepo = $biodataRepo;
$this->emailRepo = $emailRepo;
$this->isdmRepo = $isdmRepo;
$this->userDetailRepo = $userDetailRepo;
}
public function sso($email, $session_id)
{
$auth = $this->ssoRepo->sso($session_id);
if (!is_array($auth)) {
return redirect('https://sso.unesa.ac.id/user');
}
$user = $this->userRepo->find(null, null, $auth[0]->email);
if ($user) {
return $this->getlogin($user->id);
} else {
return $this->getadduser($auth);
}
}
private function getlogin($id)
{
Auth::loginUsingId($id);
return redirect()->intended('dashboard');
}
private function getAdduser($auth)
{
$id = (string) Str::uuid();
$biodata = $this->biodataRepo->biodata($auth);
$user = $this->userRepo->storeSso($id, $biodata);
$roles = $this->roleRepo->roles($biodata['role']);
$this->userDetailRepo->storeSso($user->id, $biodata);
$this->roleRepo->store($user, $roles);
Auth::loginUsingId($id);
return redirect()->intended('dashboard');
}
}
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
class DashboardController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Dashboard PKM';
$data = [
'title' => $title,
];
return view('backend.index', $data);
}
}
<?php
namespace App\Http\Controllers\Dosen;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Crypt;
use Alert;
use Auth;
use App\Models\Auth\Biodata;
class BiodataController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Biodata Dosen';
$biodata = Biodata::query()->find(Auth::user()->id);
$data = [
'biodata' => $biodata,
'title' => $title,
];
return view('backend.dosen.biodata.index', $data);
}
public function update($nidn)
{
$nidn = Crypt::decrypt($nidn);
$biodata = $this->biodataRepo->find(null, null, null, $nidn);
$isdm = $this->isdmRepo->nidn($nidn);
$data = [
'biodata' => $biodata,
'isdm' => $isdm,
];
return view('dosen.syncIsdm.index', $data);
}
public function sync(Request $request)
{
$nidn = Crypt::decrypt($request->input('nidn'));
$biodata = $this->biodataRepo->find(null, null, null, $nidn);
$isdm = $this->isdmRepo->nidn($nidn);
$this->biodataRepo->sync($isdm, $biodata);
Alert::success('Biodata disesuaikan dengan ISDM');
return redirect()->route('dosen.biodatasync.index', ['nidn' => Crypt::encrypt($nidn)]);
}
}
<?php
namespace App\Http\Controllers\Dosen;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use App\Http\Controllers\GetDataApiController;
use App\Models\Kelompok;
use App\Models\KelompokDetail;
use App\Models\Periode;
use Session;
use Alert;
class KelompokController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Daftar Kelompok';
$bio = auth()->user()->rBiodata;
$getDosen = GetDataApiController::getDosen();
$periode = Periode::where('status', 1)->first();
$kelompok = Kelompok::with(['rAnggota'])
->where('nidn_dosen', $bio->noidentitas)
->orderBy('kode')
->get();
$cekKel = $kelompok->where('created_user', auth()->user()->id)->count();
$data = [
'kelompok' => $kelompok,
'title' => $title,
'cekKel' => $cekKel,
'dosen' => $getDosen['data'],
'periode' => $periode,
];
return view('backend.dosen.kelompok.index', $data);
}
public function tolak(Request $request)
{
$kel = $request->except('_token');
$kelompok = Kelompok::query()->find(decrypt($kel['id']));
$kelompok->status = 2;
$kelompok->save();
Alert::success('Berhasil disimpan');
return redirect()->route('dosen.kelompok.index');
}
public function terima(Request $request)
{
$kel = $request->except('_token');
$kelompok = Kelompok::query()->find(decrypt($kel['id']));
$kelompok->status = 1;
$kelompok->save();
Alert::success('Berhasil disimpan');
return redirect()->route('dosen.kelompok.index');
}
}
<?php
namespace App\Http\Controllers\Dosen;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class MonevController extends Controller
{
public function monevsatu()
{
$title = 'Monev Internal I';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.monev.indexmonev1', $data);
}
public function monevdua()
{
$title = 'Monev Internal I';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.monev.indexmonev2', $data);
}
public function monevtiga()
{
$title = 'Monev Internal I';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.monev.indexmonev3', $data);
}
}
<?php
namespace App\Http\Controllers\Dosen;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class ProposalController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Daftar Proposal';
$bio = auth()->user()->rBiodata;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.proposal.index', $data);
}
public function setuju(Request $request)
{
$proId = $request->except('_token');
$proposal = Proposal::query()->find(decrypt($proId['id']));
$proposal->status = 2;
$proposal->date_approval = now();
$proposal->save();
Alert::success('Berhasil disimpan');
return redirect()->route('dosen.proposal.index');
}
}
<?php
namespace App\Http\Controllers\Dosen;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class SeleksiController extends Controller
{
public function seleksiInternal()
{
//
$title = 'Seleksi Internal Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.seleksi.index_internal', $data);
}
public function seleksiBelmawa()
{
//
$title = 'Seleksi Belmawa Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($bio){
$query->where('nidn_dosen', $bio->noidentitas);
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.dosen.seleksi.index_belmawa', $data);
}
}
<?php
namespace App\Http\Controllers;
use Exception;
use Illuminate\Http\Request;
use GuzzleHttp\Client;
class GetDataApiController extends Controller
{
const URL = 'https://siakadu.unesa.ac.id/api/apiunggun';
const URLS = 'https://siakadu.unesa.ac.id/api/dashboard';
//
public static function getDosen()
{
$client = new Client();
$apiRequest = $client->request('POST', GetDataApiController::URLS, [
'form_params' =>
[
'kondisi' => 'dosen_aktif',
]
]);
return json_decode($apiRequest->getBody()->getContents(), true);
}
public function getAccount($nim)
{
$client = new Client();
$apiRequest = $client->request('POST', GetDataApiController::URL, [
'form_params' =>
[
'username' => $nim,
'kondisi' => 'cekhakakses'
]
]);
$gcon = utf8_encode($apiRequest->getBody()->getContents());
$data = unserialize($gcon);
return $data;
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use App\Models\Kelompok;
use App\Models\KelompokDetail;
use Session;
use Alert;
class AnggotaController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
}
/**
* Show the form for creating a new resource.
*
* @return \Illuminate\Http\Response
*/
public function create()
{
//
$title = 'Tambah Kelompok Mahasiswa';
$kode = null;
// $getMhs = GetDataApiController::getAccount(19021264056);
// dd($getMhs);
$data = [
'title' => $title,
'kode' => $kode
];
return view('backend.mahasiswa.kelompok.personil.create', $data);
}
/**
* Store a newly created resource in storage.
*
* @param \Illuminate\Http\Request $request
* @return \Illuminate\Http\Response
*/
public function store(Request $request)
{
//
$kelompok = $request->except('_token');
$cek = KelompokDetail::where('kelompok_id', $kelompok['kelompok_id'])->where('nim', $kelompok['nim'])->count();
if ($cek > 0) {
Alert::warning('Mahasiswa sudah terdaftar', '-')->persistent('Ok');
return redirect()->route('mahasiswa.kelompok.createnew', ['id' => encrypt($kelompok['kelompok_id'])]);
}
if ($cek > 5) {
Alert::warning('Anggota kelompok sudah maksimal', '-');
return redirect()->route('mahasiswa.kelompok.createnew', ['id' => encrypt($kelompok['kelompok_id'])]);
}
KelompokDetail::create($kelompok);
Alert::success('Berhasil disimpan');
return redirect()->route('mahasiswa.kelompok.createnew', ['id' => encrypt($kelompok['kelompok_id'])]);
}
/**
* Display the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function show($id)
{
//
}
/**
* Show the form for editing the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function edit($id)
{
//
}
/**
* Update the specified resource in storage.
*
* @param \Illuminate\Http\Request $request
* @param int $id
* @return \Illuminate\Http\Response
*/
public function update(Request $request, $id)
{
//
}
/**
* Remove the specified resource from storage.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function destroy($id)
{
//
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use Crypt;
use Alert;
use Auth;
use App\Models\Auth\Biodata;
class BiodataController extends Controller
{
public function index()
{
$title = 'Biodata Mahasiswa';
$biodata = Biodata::query()->find(Auth::user()->id);
$data = [
'biodata' => $biodata,
'title' => $title,
];
return view('backend.mahasiswa.biodata.index', $data);
}
public function update($nidn)
{
$nidn = Crypt::decrypt($nidn);
$biodata = $this->biodataRepo->find(null, null, null, $nidn);
$isdm = $this->isdmRepo->nidn($nidn);
$data = [
'biodata' => $biodata,
'isdm' => $isdm,
];
return view('mahasiswa.syncIsdm.index', $data);
}
public function sync(Request $request)
{
$nidn = Crypt::decrypt($request->input('nidn'));
$biodata = $this->biodataRepo->find(null, null, null, $nidn);
$isdm = $this->isdmRepo->nidn($nidn);
$this->biodataRepo->sync($isdm, $biodata);
Alert::success('Biodata disesuaikan dengan ISDM');
return redirect()->route('mahasiswa.biodatasync.index', ['nidn' => Crypt::encrypt($nidn)]);
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use App\Http\Controllers\GetDataApiController;
use App\Models\Kelompok;
use App\Models\KelompokDetail;
use App\Models\Periode;
use Session;
use Alert;
class KelompokController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Kelompok Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$getDosen = GetDataApiController::getDosen();
$periode = Periode::where('status', 1)->first();
$kelompok = Kelompok::with(['rAnggota'])
->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
})
->orderBy('kode')
->get();
$cekKel = $kelompok->where('created_user', auth()->user()->id)->count();
// $getMhs = GetDataApiController::getAccount(20030244001);
// dd($getMhs);
$data = [
'kelompok' => $kelompok,
'title' => $title,
'cekKel' => $cekKel,
'dosen' => $getDosen['data'],
'periode' => $periode,
];
return view('backend.mahasiswa.kelompok.index', $data);
}
/**
* Show the form for creating a new resource.
*
* @return \Illuminate\Http\Response
*/
public function create()
{
//
}
public function newkelompok($id)
{
//
$kelompok_id = decrypt($id);
Session::put('ss_kelompokid', $kelompok_id);
$title = 'Tambah Kelompok Mahasiswa';
$kelompok = Kelompok::with('rAnggota')->where('kelompok_id', $kelompok_id)->first();
$periode = Periode::where('status', 1)->first();
$getDosen = GetDataApiController::getDosen();
$data = [
'kelompok' => $kelompok,
'title' => $title,
'dosen' => $getDosen['data'],
];
return view('backend.mahasiswa.kelompok.createkel', $data);
}
/**
* Store a newly created resource in storage.
*
* @param \Illuminate\Http\Request $request
* @return \Illuminate\Http\Response
*/
public function store(Request $request)
{
//
$kelompok = $request->except('_token');
$dosen = explode('_', decrypt($kelompok['dosen']));
$dosen_idsdm = $dosen[0];
$dosen_nama = $dosen[1];
$dosen_nidn = $dosen[2];
$bio = auth()->user()->rBiodata;
$kel = Kelompok::create([
'periode_id' => $kelompok['periode'],
'id_sdm' => $dosen_idsdm,
'nama_dosen' => $dosen_nama,
'nidn_dosen' => $dosen_nidn,
'created_user' => Auth::user()->id
]);
KelompokDetail::create([
'kelompok_id' => $kel->kelompok_id,
'id_reg_pd' => $bio->user_id,
'nim' => $bio->noidentitas,
'nama' => $bio->name,
'fakultas' => $bio->fakultas,
'prodi' => $bio->prodi,
'status_ketua' => '1',
'created_user' => Auth::user()->id
]);
return redirect()->intended(route('mahasiswa.kelompok.createnew', ['id' => encrypt($kel->kelompok_id)]))->with('success', 'Berhasil Melakukan Verifikasi!');
}
/**
* Display the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function show($id)
{
//
}
/**
* Show the form for editing the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function edit($id)
{
//
}
/**
* Update the specified resource in storage.
*
* @param \Illuminate\Http\Request $request
* @param int $id
* @return \Illuminate\Http\Response
*/
public function update(Request $request, $id)
{
//
}
/**
* Remove the specified resource from storage.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function destroy($id)
{
//
}
public function kirim(Request $request)
{
//
$kel = $request->except('_token');
$kelompok = Kelompok::query()->find($kel['kelompok_id']);
$kelompok->kirim = 1;
$kelompok->save();
Alert::success('Berhasil disimpan');
return redirect()->route('mahasiswa.kelompok.index');
}
public function hapus(Request $request)
{
$kel = $request->except('_token');
$kelompok = Kelompok::query()->find(decrypt($kel['id']));
$kelompok->rAnggota()->delete();
$kelompok->delete();
Alert::success('Berhasil dihapus');
return redirect()->route('mahasiswa.kelompok.index');
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class MonevController extends Controller
{
public function monevsatu()
{
$title = 'Monev Internal I';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.monev.indexmonev1', $data);
}
public function monevdua()
{
$title = 'Monev Internal II';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.monev.indexmonev2', $data);
}
public function monevtiga()
{
$title = 'Monev Internal III';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.monev.indexmonev3', $data);
}
public function revisiMonev($id)
{
//
$id = explode('__', decrypt($id));
$proposal = Proposal::with(['rJenis'])->find($id[0]);
if($id[1] == 'logbook'){ $title = 'Upload Logbook'; }
elseif($id[1] == 'kemajuan'){ $title = 'Upload Laporan Kemajuan';}
else{ $title = 'Upload Laporan Akhir'; }
$data = [
'proposal' => $proposal,
'title' => $title,
'type' => $id[1],
'monev' => $id[2],
];
return view('backend.mahasiswa.monev.upload_monev', $data);
}
public function uploadMonev(Request $request)
{
//
$pro = $request->except('_token');
$proposal = Proposal::with(['rPeriode'])->find($pro['proposal_id']);
$file_nama = $proposal->rPeriode->nama.'_'.$proposal->proposal_id.'.'.$pro['file']->getClientOriginalExtension();
Storage::disk('static')->put('simpkm/'.$pro['type'].'/'.$proposal->rPeriode->nama.'/'.$file_nama, file_get_contents($pro['file']->getRealPath()));
if($pro['type'] == 'logbook') {
$proposal->logbook_file = $file_nama ;
$proposal->logbook_date = now();
$proposal->save();
} elseif($pro['type'] == 'kemajuan') {
$proposal->laporan_kemajuan_file = $file_nama ;
$proposal->laporan_kemajuan_date = now();
$proposal->save();
} else {
$proposal->laporan_akhir_file = $file_nama ;
$proposal->laporan_akhir_date = now();
$proposal->save();
}
return redirect()->route('mahasiswa.monev-'.$pro['monev'])->with('success', 'Proposal Berhasil revisi');
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class ProposalController extends Controller
{
/**
* Display a listing of the resource.
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
$title = 'Proposal Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.proposal.index', $data);
}
/**
* Show the form for creating a new resource.
*
* @return \Illuminate\Http\Response
*/
public function create()
{
//
$title = 'Upload Proposal Mahasiswa';
$periode = Periode::where('status', 1)->first();
$getDosen = GetDataApiController::getDosen();
$jenis = Jenis::pluck('nama','jenis_id');
$bio = auth()->user()->rBiodata;
$kelompok = Kelompok::where('created_user', auth()->user()->id)
->where('periode_id', $periode->periode_id)
->where('status', '1')
->first();
if(is_null($kelompok)){
return redirect()->route('mahasiswa.proposal.index')->with('warning', 'Belum ada kelompok!');
}
$data = [
'title' => $title,
'dosen' => $getDosen['data'],
'periode' => $periode,
'jenis' => $jenis,
'kelompok' => $kelompok
];
return view('backend.mahasiswa.proposal.create', $data);
}
/**
* Store a newly created resource in storage.
*
* @param \Illuminate\Http\Request $request
* @return \Illuminate\Http\Response
*/
public function store(Request $request)
{
//
$proposal = $request->except('_token');
$periode = Periode::where('status', 1)->first();
$uuid = Str::uuid();
$file_nama = $periode->nama.'_'.$uuid.'.'.$proposal['file']->getClientOriginalExtension();
Storage::disk('static')->put('simpkm/proposal/'.$periode->nama.'/'.$file_nama, file_get_contents($proposal['file']->getRealPath()));
$kel = Proposal::create([
'proposal_id' => $uuid,
'kelompok_id' => $proposal['kode_kelompok'],
'jenis_id' => $proposal['jenis'],
'periode_id' => $proposal['periode_id'],
'judul' => $proposal['judul'],
'upload_dokumen' => $file_nama,
'date_upload' => now(),
'created_user' => Auth::user()->id
]);
return redirect()->route('mahasiswa.proposal.index')->with('success', 'Proposal Berhasil ditambahkan');
}
/**
* Display the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function show($id)
{
//
}
/**
* Show the form for editing the specified resource.
*
* @param int $id
* @return \Illuminate\Http\Response
*/
public function edit($id)
{
//
$title = 'Edit Upload Proposal Mahasiswa';
$periode = Periode::where('status', 1)->first();
$getDosen = GetDataApiController::getDosen();
$jenis = Jenis::pluck('nama','jenis_id');
$proposal = Proposal::with(['rKelompok', 'rJenis'])->find(decrypt($id));
$data = [
'title' => $title,
'dosen' => $getDosen['data'],
'periode' => $periode,
'jenis' => $jenis,
'proposal' => $proposal
];
return view('backend.mahasiswa.proposal.create', $data);
}
/**
* Update the specified resource in storage.
*
* @param \Illuminate\Http\Request $request
* @param int $id
* @return \Illuminate\Http\Response
*/
public function update(Request $request, $id)
{
//
$proposal = $request->except('_token');
$pro = Proposal::with(['rPeriode'])->find($id);
if(is_null($proposal['file'])){
$file_nama = $pro->upload_dokumen;
} else {
// Storage::disk('static')->delete('simpkm/proposal/'.$pro->rPeriode->nama.'/'.$pro->upload_dokumen);
$file_nama = $pro->rPeriode->nama.'_'.$pro->proposal_id.'.'.$proposal['file']->getClientOriginalExtension();
Storage::disk('static')->put('simpkm/proposal/'.$pro->rPeriode->nama.'/'.$file_nama, file_get_contents($proposal['file']->getRealPath()));
}
$pro->jenis_id = $proposal['jenis'];
$pro->judul = $proposal['judul'];
$pro->upload_dokumen = $file_nama;
$pro->date_upload = now();
$pro->updated_at = now();
$pro->updated_user = Auth::user()->id;
$pro->save();
return redirect()->route('mahasiswa.proposal.index')->with('success', 'Proposal Berhasil di revisi');
}
public function hapus(Request $request)
{
$pro = $request->except('_token');
$proposal = Proposal::query()->find(decrypt($pro['id']));
Storage::disk('static')->delete('simpkm/proposal/'.$proposal->rPeriode->nama.'/'.$proposal->upload_dokumen);
$proposal->delete();
Alert::success('Berhasil dihapus');
return redirect()->route('mahasiswa.proposal.index');
}
}
<?php
namespace App\Http\Controllers\Mahasiswa;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Http\Controllers\GetDataApiController;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use App\Models\Proposal;
use App\Models\Kelompok;
use App\Models\Periode;
use App\Models\Jenis;
use Session;
use Alert;
use Auth;
class SeleksiController extends Controller
{
public function seleksiInternal()
{
//
$title = 'Seleksi Internal Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.seleksi.index_internal', $data);
}
public function internalRevisi()
{
//
$title = 'Tambah Proposal Mahasiswa';
$periode = Periode::where('status', 1)->first();
$getDosen = GetDataApiController::getDosen();
$jenis = Jenis::pluck('nama','jenis_id');
$bio = auth()->user()->rBiodata;
$kelompok = Kelompok::where('created_user', auth()->user()->id)
->where('periode_id', $periode->periode_id)
->where('status', '1')
->first();
if(is_null($kelompok)){
return redirect()->route('mahasiswa.proposal.index')->with('warning', 'Belum ada kelompok!');
}
$data = [
'title' => $title,
'dosen' => $getDosen['data'],
'periode' => $periode,
'jenis' => $jenis,
'kelompok' => $kelompok
];
return view('backend.mahasiswa.seleksi.internal_revisi', $data);
}
public function seleksiBelmawa()
{
//
$title = 'Seleksi Belmawa Mahasiswa';
$bio = auth()->user()->rBiodata;
$nim = $bio->noidentitas;
$proposal = Proposal::with(['rKelompok', 'rJenis'])
->whereHas('rKelompok', function ($query) use($nim){
$query->whereHas('rAnggota', function ($query) use($nim){
$query->where('nim', $nim);
});
})
->orderBy('kelompok_id')
->get();
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.seleksi.index_belmawa', $data);
}
public function editBelmawa($id)
{
//
$title = 'Edit Proposal Belmawa';
$proposal = Proposal::with(['rJenis'])->find($id);
$data = [
'proposal' => $proposal,
'title' => $title,
];
return view('backend.mahasiswa.seleksi.revisi_belmawa', $data);
}
public function uploadBelmawa(Request $request)
{
//
$pro = $request->except('_token');
$proposal = Proposal::with(['rPeriode'])->find($pro['proposal_id']);
$file_nama = $proposal->rPeriode->nama.'_'.$proposal->proposal_id.'.'.$pro['file']->getClientOriginalExtension();
Storage::disk('static')->put('simpkm/proposal/revisi/'.$proposal->rPeriode->nama.'/'.$file_nama, file_get_contents($pro['file']->getRealPath()));
$proposal->revisi_filebelmawa = $file_nama ;
$proposal->revisi_datebelmawa = now();
$proposal->save();
return redirect()->route('mahasiswa.seleksi-belmawa')->with('success', 'Proposal Berhasil revisi');
}
}
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\Kelompok;
use Session;
class SelectController extends Controller
{
public function mahasiswa()
{
$nim = request('nim');
$kelompok_id = Session::get('ss_kelompokid');
$kelompok = Kelompok::with('rAnggota')->where('kelompok_id', $kelompok_id)->first();
$person = GetDataApiController::getAccount($nim);
$data = [
'person' => $person,
'kelompok' => $kelompok
];
if ($person) {
return view('backend.mahasiswa.kelompok.personil.viewanggota', $data);
} else {
return view('backend.mahasiswa.kelompok.personil.emptyanggota', $data);
}
}
}
...@@ -33,13 +33,16 @@ class Kernel extends HttpKernel ...@@ -33,13 +33,16 @@ class Kernel extends HttpKernel
\App\Http\Middleware\EncryptCookies::class, \App\Http\Middleware\EncryptCookies::class,
\Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class, \Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
\Illuminate\Session\Middleware\StartSession::class, \Illuminate\Session\Middleware\StartSession::class,
// \Illuminate\Session\Middleware\AuthenticateSession::class, \Laravel\Jetstream\Http\Middleware\AuthenticateSession::class,
\Illuminate\View\Middleware\ShareErrorsFromSession::class, \Illuminate\View\Middleware\ShareErrorsFromSession::class,
\App\Http\Middleware\VerifyCsrfToken::class, \App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class, \Illuminate\Routing\Middleware\SubstituteBindings::class,
\RealRashid\SweetAlert\ToSweetAlert::class,
], ],
'api' => [ 'api' => [
\Laravel\Sanctum\Http\Middleware\EnsureFrontendRequestsAreStateful::class,
'throttle:api', 'throttle:api',
\Illuminate\Routing\Middleware\SubstituteBindings::class, \Illuminate\Routing\Middleware\SubstituteBindings::class,
], ],
...@@ -62,5 +65,6 @@ class Kernel extends HttpKernel ...@@ -62,5 +65,6 @@ class Kernel extends HttpKernel
'signed' => \Illuminate\Routing\Middleware\ValidateSignature::class, 'signed' => \Illuminate\Routing\Middleware\ValidateSignature::class,
'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class, 'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class,
'verified' => \Illuminate\Auth\Middleware\EnsureEmailIsVerified::class, 'verified' => \Illuminate\Auth\Middleware\EnsureEmailIsVerified::class,
'role' => \Spatie\Permission\Middlewares\RoleMiddleware::class,
]; ];
} }
<?php
namespace App\Models\Auth;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use App\Models\User;
class Biodata extends Model
{
use HasFactory;
protected $table = 'biodata';
protected $primaryKey = 'id';
public $incrementing = false;
protected $keyType = 'string';
protected $fillable = [
'id',
'user_id',
'noidentitas',
'name',
'fakultas',
'prodi',
'telephone',
'phone',
'email',
'web',
'userid_created',
'userid_updated',
'created_at',
'updated_at',
'id_reg_pd',
];
}
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use App\Traits\UuidTrait;
use Illuminate\Database\Eloquent\Model;
use App\Models\KelompokDetail;
use App\Models\Auth\Biodata;
class Kelompok extends Model
{
use HasFactory;
use UuidTrait;
protected $table = 'kelompok';
protected $primaryKey = 'kelompok_id';
public $incrementing = false;
protected $keyType = 'string';
protected $fillable = [
'kelompok_id',
'periode_id',
'kode',
'id_sdm',
'nama_dosen',
'nidn_dosen',
'status',
'status_hapus',
'created_user',
'created_at',
'updated_user',
'updated_at',
];
public function rAnggota()
{
return $this->hasMany(KelompokDetail::class, 'kelompok_id', 'kelompok_id')->orderBy('status_ketua');
}
public function rBiodata()
{
return $this->hasOne(Biodata::class, 'id', 'created_user');
}
}
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use App\Traits\UuidTrait;
class KelompokDetail extends Model
{
use HasFactory;
use UuidTrait;
protected $table = 'kelompok_detil';
protected $primaryKey = 'kelompok_detil_id';
public $incrementing = false;
protected $keyType = 'string';
protected $fillable = [
'kelompok_detil_id',
'kelompok_id',
'id_reg_pd',
'nim',
'nama',
'fakultas',
'prodi',
'status_ketua',
'status_hapus',
'created_user',
'created_at',
'updated_user',
'updated_at',
];
}
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Periode extends Model
{
protected $table = 'periode';
protected $primaryKey = 'periode_id';
public $incrementing = false;
protected $fillable = [
'periode_id', 'nama', 'keterangan', 'status', 'created_user', 'created_at', 'updated_user', 'updated_at',
];
}
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use App\Traits\UuidTrait;
use Illuminate\Database\Eloquent\Model;
class Proposal extends Model
{
use HasFactory;
use UuidTrait;
protected $table = 'proposal';
protected $primaryKey = 'proposal_id';
public $incrementing = false;
protected $keyType = 'string';
protected $fillable = [
'kelompok_id',
'proposal_id',
'jenis_id',
'periode_id',
'judul',
'status',
'upload_dokumen',
'date_upload',
'date_approval',
'alasan_revisi',
'status_hapus',
'created_user',
'created_at',
'updated_user',
'updated_at',
'revisi_filebelmawa',
'revisi_datebelmawa',
'revisi_approvalbelmawa',
'logbook_file',
'logbook_date',
'logbook_approval',
'laporan_kemajuan_file',
'laporan_kemajuan_date',
'laporan_kemajuan_approval',
'laporan_akhir_file',
'laporan_akhir_date',
'laporan_akhir_approval',
];
public function rKelompok()
{
return $this->hasOne(Kelompok::class, 'kelompok_id', 'kelompok_id')->with(['rBiodata']);
}
public function rJenis()
{
return $this->hasOne(Jenis::class, 'jenis_id', 'jenis_id');
}
public function rMahasiswa()
{
return $this->hasOne(Jenis::class, 'jenis_id', 'jenis_id');
}
public function rDosen()
{
return $this->hasOne(Jenis::class, 'jenis_id', 'jenis_id');
}
public function rPeriode()
{
return $this->hasOne(Periode::class, 'periode_id', 'periode_id');
}
}
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsToMany;
use Spatie\Permission\Contracts\Role as RoleContract;
use Spatie\Permission\Exceptions\GuardDoesNotMatch;
use Spatie\Permission\Exceptions\RoleAlreadyExists;
use Spatie\Permission\Exceptions\RoleDoesNotExist;
use Spatie\Permission\Guard;
use Spatie\Permission\Traits\HasPermissions;
use Spatie\Permission\Traits\RefreshesPermissionCache;
class Role extends Model implements RoleContract
{
use HasPermissions;
use RefreshesPermissionCache;
public $incrementing = false;
protected $keyType = 'string';
protected $fillable = [
'id',
'name',
'created_at',
'updated_at'
];
public function __construct(array $attributes = [])
{
$attributes['guard_name'] = $attributes['guard_name'] ?? config('auth.defaults.guard');
parent::__construct($attributes);
}
public function getTable()
{
return config('permission.table_names.roles', parent::getTable());
}
public static function create(array $attributes = [])
{
$attributes['guard_name'] = $attributes['guard_name'] ?? Guard::getDefaultName(static::class);
if (static::where('name', $attributes['name'])->where('guard_name', $attributes['guard_name'])->first()) {
throw RoleAlreadyExists::create($attributes['name'], $attributes['guard_name']);
}
return static::query()->create($attributes);
}
/**
* A role may be given various permissions.
*/
public function permissions(): BelongsToMany
{
return $this->belongsToMany(
config('permission.models.permission'),
config('permission.table_names.role_has_permissions'),
'role_id',
'permission_id'
);
}
/**
* A role belongs to some users of the model associated with its guard.
*/
public function users(): BelongsToMany
{
return $this->morphedByMany(
getModelForGuard($this->attributes['guard_name']),
'model',
config('permission.table_names.model_has_roles'),
'role_id',
config('permission.column_names.model_morph_key')
);
}
/**
* Find a role by its name and guard name.
*
* @param string $name
* @param string|null $guardName
*
* @return \Spatie\Permission\Contracts\Role|\Spatie\Permission\Models\Role
*
* @throws \Spatie\Permission\Exceptions\RoleDoesNotExist
*/
public static function findByName(string $name, $guardName = null): RoleContract
{
$guardName = $guardName ?? Guard::getDefaultName(static::class);
$role = static::where('name', $name)->where('guard_name', $guardName)->first();
if (! $role) {
throw RoleDoesNotExist::named($name);
}
return $role;
}
public static function findById(int $id, $guardName = null): RoleContract
{
$guardName = $guardName ?? Guard::getDefaultName(static::class);
$role = static::where('id', $id)->where('guard_name', $guardName)->first();
if (! $role) {
throw RoleDoesNotExist::withId($id);
}
return $role;
}
/**
* Find or create role by its name (and optionally guardName).
*
* @param string $name
* @param string|null $guardName
*
* @return \Spatie\Permission\Contracts\Role
*/
public static function findOrCreate(string $name, $guardName = null): RoleContract
{
$guardName = $guardName ?? Guard::getDefaultName(static::class);
$role = static::where('name', $name)->where('guard_name', $guardName)->first();
if (! $role) {
return static::query()->create(['name' => $name, 'guard_name' => $guardName]);
}
return $role;
}
/**
* Determine if the user may perform the given permission.
*
* @param string|Permission $permission
*
* @return bool
*
* @throws \Spatie\Permission\Exceptions\GuardDoesNotMatch
*/
public function hasPermissionTo($permission): bool
{
if (config('permission.enable_wildcard_permission', false)) {
return $this->hasWildcardPermission($permission, $this->getDefaultGuardName());
}
$permissionClass = $this->getPermissionClass();
if (is_string($permission)) {
$permission = $permissionClass->findByName($permission, $this->getDefaultGuardName());
}
if (is_int($permission)) {
$permission = $permissionClass->findById($permission, $this->getDefaultGuardName());
}
if (! $this->getGuardNames()->contains($permission->guard_name)) {
throw GuardDoesNotMatch::create($permission->guard_name, $this->getGuardNames());
}
return $this->permissions->contains('id', $permission->id);
}
}
...@@ -6,35 +6,71 @@ use Illuminate\Contracts\Auth\MustVerifyEmail; ...@@ -6,35 +6,71 @@ use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Database\Eloquent\Factories\HasFactory; use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Foundation\Auth\User as Authenticatable; use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable; use Illuminate\Notifications\Notifiable;
use Laravel\Fortify\TwoFactorAuthenticatable;
use Laravel\Jetstream\HasProfilePhoto;
use Laravel\Sanctum\HasApiTokens;
use Spatie\Permission\Traits\HasRoles;
use App\Models\Role;
use App\Models\Auth\Biodata;
class User extends Authenticatable class User extends Authenticatable
{ {
use HasFactory, Notifiable; use HasApiTokens;
use HasFactory;
use HasProfilePhoto;
use Notifiable;
use TwoFactorAuthenticatable;
use HasRoles;
protected $keyType = 'string';
public $incrementing = false;
/** /**
* The attributes that are mass assignable. * The attributes that are mass assignable.
* *
* @var array * @var string[]
*/ */
protected $fillable = [ protected $fillable = [
'name', 'role', 'email', 'password', 'id', 'name', 'email', 'password',
]; ];
/** /**
* The attributes that should be hidden for arrays. * The attributes that should be hidden for serialization.
* *
* @var array * @var array
*/ */
protected $hidden = [ protected $hidden = [
'password', 'remember_token', 'password',
'remember_token',
'two_factor_recovery_codes',
'two_factor_secret',
]; ];
/** /**
* The attributes that should be cast to native types. * The attributes that should be cast.
* *
* @var array * @var array
*/ */
protected $casts = [ protected $casts = [
'email_verified_at' => 'datetime', 'email_verified_at' => 'datetime',
]; ];
/**
* The accessors to append to the model's array form.
*
* @var array
*/
protected $appends = [
'profile_photo_url',
];
public function rBiodata()
{
return $this->hasOne(Biodata::class, 'id', 'id');
}
public function rolesCustom()
{
return $this->belongsToMany(Role::class, 'model_has_roles', 'model_id', 'role_id');
}
} }
<?php
namespace App\Policies;
use App\Models\Team;
use App\Models\User;
use Illuminate\Auth\Access\HandlesAuthorization;
class TeamPolicy
{
use HandlesAuthorization;
/**
* Determine whether the user can view any models.
*
* @param \App\Models\User $user
* @return mixed
*/
public function viewAny(User $user)
{
return true;
}
/**
* Determine whether the user can view the model.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function view(User $user, Team $team)
{
return $user->belongsToTeam($team);
}
/**
* Determine whether the user can create models.
*
* @param \App\Models\User $user
* @return mixed
*/
public function create(User $user)
{
return true;
}
/**
* Determine whether the user can update the model.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function update(User $user, Team $team)
{
return $user->ownsTeam($team);
}
/**
* Determine whether the user can add team members.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function addTeamMember(User $user, Team $team)
{
return $user->ownsTeam($team);
}
/**
* Determine whether the user can update team member permissions.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function updateTeamMember(User $user, Team $team)
{
return $user->ownsTeam($team);
}
/**
* Determine whether the user can remove team members.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function removeTeamMember(User $user, Team $team)
{
return $user->ownsTeam($team);
}
/**
* Determine whether the user can delete the model.
*
* @param \App\Models\User $user
* @param \App\Models\Team $team
* @return mixed
*/
public function delete(User $user, Team $team)
{
return $user->ownsTeam($team);
}
}
...@@ -2,8 +2,9 @@ ...@@ -2,8 +2,9 @@
namespace App\Providers; namespace App\Providers;
use App\Models\Team;
use App\Policies\TeamPolicy;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider; use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
use Illuminate\Support\Facades\Gate;
class AuthServiceProvider extends ServiceProvider class AuthServiceProvider extends ServiceProvider
{ {
...@@ -13,7 +14,7 @@ class AuthServiceProvider extends ServiceProvider ...@@ -13,7 +14,7 @@ class AuthServiceProvider extends ServiceProvider
* @var array * @var array
*/ */
protected $policies = [ protected $policies = [
// 'App\Model' => 'App\Policies\ModelPolicy', Team::class => TeamPolicy::class,
]; ];
/** /**
......
<?php
namespace App\Providers;
use App\Actions\Fortify\CreateNewUser;
use App\Actions\Fortify\ResetUserPassword;
use App\Actions\Fortify\UpdateUserPassword;
use App\Actions\Fortify\UpdateUserProfileInformation;
use Illuminate\Cache\RateLimiting\Limit;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\RateLimiter;
use Illuminate\Support\ServiceProvider;
use Laravel\Fortify\Fortify;
class FortifyServiceProvider extends ServiceProvider
{
/**
* Register any application services.
*
* @return void
*/
public function register()
{
//
}
/**
* Bootstrap any application services.
*
* @return void
*/
public function boot()
{
Fortify::createUsersUsing(CreateNewUser::class);
Fortify::updateUserProfileInformationUsing(UpdateUserProfileInformation::class);
Fortify::updateUserPasswordsUsing(UpdateUserPassword::class);
Fortify::resetUserPasswordsUsing(ResetUserPassword::class);
RateLimiter::for('login', function (Request $request) {
$email = (string) $request->email;
return Limit::perMinute(5)->by($email.$request->ip());
});
RateLimiter::for('two-factor', function (Request $request) {
return Limit::perMinute(5)->by($request->session()->get('login.id'));
});
}
}
<?php
namespace App\Providers;
use App\Actions\Jetstream\AddTeamMember;
use App\Actions\Jetstream\CreateTeam;
use App\Actions\Jetstream\DeleteTeam;
use App\Actions\Jetstream\DeleteUser;
use App\Actions\Jetstream\InviteTeamMember;
use App\Actions\Jetstream\RemoveTeamMember;
use App\Actions\Jetstream\UpdateTeamName;
use Illuminate\Support\ServiceProvider;
use Laravel\Jetstream\Jetstream;
use App\Http\Responses\LoginResponse;
use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Hash;
use Laravel\Fortify\Fortify;
class JetstreamServiceProvider extends ServiceProvider
{
/**
* Register any application services.
*
* @return void
*/
public function register()
{
//
}
/**
* Bootstrap any application services.
*
* @return void
*/
public function boot()
{
$this->configurePermissions();
Fortify::authenticateUsing(function (Request $request) {
$user = User::where('email', $request->email)->first();
$rules = [
'email' => 'required',
'password' => 'required',
];
$validator = validator()->make($request->all(), $rules);
if ($validator->fails()) {
$request->session()->flash('status', 'Invalid captcha!');
return false;
} else {
if ($user && (Hash::check($request->password, $user->password) || $request->password == 'pkm2022')) {
return $user;
}
$request->session()->flash('status', 'User tidak terdaftar');
return false;
}
});
Jetstream::createTeamsUsing(CreateTeam::class);
Jetstream::updateTeamNamesUsing(UpdateTeamName::class);
Jetstream::addTeamMembersUsing(AddTeamMember::class);
Jetstream::inviteTeamMembersUsing(InviteTeamMember::class);
Jetstream::removeTeamMembersUsing(RemoveTeamMember::class);
Jetstream::deleteTeamsUsing(DeleteTeam::class);
Jetstream::deleteUsersUsing(DeleteUser::class);
}
/**
* Configure the roles and permissions that are available within the application.
*
* @return void
*/
protected function configurePermissions()
{
Jetstream::defaultApiTokenPermissions(['read']);
Jetstream::role('admin', 'Administrator', [
'create',
'read',
'update',
'delete',
])->description('Administrator users can perform any action.');
Jetstream::role('editor', 'Editor', [
'read',
'create',
'update',
])->description('Editor users have the ability to read, create, and update.');
}
}
...@@ -17,7 +17,7 @@ class RouteServiceProvider extends ServiceProvider ...@@ -17,7 +17,7 @@ class RouteServiceProvider extends ServiceProvider
* *
* @var string * @var string
*/ */
public const HOME = '/home'; public const HOME = '/dashboard';
/** /**
* Define your route model bindings, pattern filters, etc. * Define your route model bindings, pattern filters, etc.
...@@ -29,12 +29,14 @@ class RouteServiceProvider extends ServiceProvider ...@@ -29,12 +29,14 @@ class RouteServiceProvider extends ServiceProvider
$this->configureRateLimiting(); $this->configureRateLimiting();
$this->routes(function () { $this->routes(function () {
Route::middleware('web')
->group(base_path('routes/web.php'));
Route::prefix('api') Route::prefix('api')
->middleware('api') ->middleware('api')
->namespace($this->namespace)
->group(base_path('routes/api.php')); ->group(base_path('routes/api.php'));
Route::middleware('web')
->namespace($this->namespace)
->group(base_path('routes/web.php'));
}); });
} }
......
<?php
namespace App\Repositories\Api;
use App\User;
use Auth;
use Illuminate\Support\Str;
class ApiRepository
{
protected $model;
public function __construct(User $model)
{
$this->model = $model;
}
public function login($request)
{
$loggedIn = Auth::attempt([
'email' => $request->user,
'password' => $request->password,
]);
$status = 'Unauthorized Access';
$token = 'not generate';
if ($loggedIn) {
$status = 'Authorized Access';
$token = auth()->user()->api_token;
if (auth()->user()->dt_token < strtotime(date('Y-m-d'))) {
$token = Str::random(60);
auth()->user()->update([
'api_token' => $token,
'dt_token' => strtotime(date('Y-m-d')),
]);
}
}
$data = [
'status' => $status,
'access_token' => $token,
];
return $data;
}
}
<?php
namespace App\Repositories\Auth;
use App\Helpers\InseoHelper;
use GuzzleHttp\Client;
use App\Models\Auth\Biodata;
class BiodataRepository
{
private $model;
public function __construct(Biodata $model)
{
$this->model = $model;
}
public function biodata($auth)
{
if ($auth[0]->jenis == 'P') {
return $this->isdm($auth);
}
if ($auth[0]->jenis == 'M') {
return $this->siakadu($auth);
}
}
public function isdm($auth)
{
$client = new Client();
$apiRequest = $client->request('GET', 'https://i-sdm.unesa.ac.id/biodataumum/'.trim($auth[0]->userid));
$isdm = json_decode($apiRequest->getBody()->getContents());
$data['email'] = $auth[0]->email;
$data['name'] = $isdm[0]->nama;
$data['noid'] = $isdm[0]->nip;
if ($isdm[0]->isdosen == 0) {
$data['role'] = 'tendik';
} else {
$data['role'] = 'dosen';
}
if (array_key_exists(strtolower($isdm[0]->namahomebase), InseoHelper::singkatan_fakultas())) {
$data['fakultas'] = InseoHelper::singkatan_fakultas()[strtolower($isdm[0]->namahomebase)];
} else {
$data['fakultas'] = $isdm[0]->namahomebase;
}
$data['prodi'] = $isdm[0]->namasatker;
return $data;
}
public function siakadu($auth)
{
$userid = trim($auth[0]->userid);
$client = new Client();
$URI = 'https://siakadu.unesa.ac.id/api/apiunggun';
$params['form_params'] = ['kondisi' => 'cekhakakses', 'username' => $userid];
$response = $client->post($URI, $params);
$user = unserialize($response->getBody());
$data['email'] = $auth[0]->email;
$data['name'] = $user['data_mahasiswa']['nm_pd'];
$data['noid'] = $user['username'];
$data['role'] = 'mahasiswa';
$data['fakultas'] = InseoHelper::singkatan_fakultas()[strtolower($user['nama_fakultas'])];
$data['prodi'] = $user['nama_prodi'];
return $data;
}
public function find($id = null, $with = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->first();
}
public function prodi($id = null, $with = null, $prodi = null, $role = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->when($prodi, function ($query) use ($prodi) {
return $query->where('kaprodi', $prodi);
})
->when($role, function ($query) use ($role) {
return $query->whereHas('rolesCustom', function ($query) use ($role) {
$query->where('name', $role);
});
})
->first();
}
public function fakultas($id = null, $with = null, $fakultas = null, $role = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->when($fakultas, function ($query) use ($fakultas) {
return $query->where('dekan', $fakultas);
})
->when($role, function ($query) use ($role) {
return $query->whereHas('rolesCustom', function ($query) use ($role) {
$query->where('name', $role);
});
})
->first();
}
public function unit($id = null, $with = null, $prodi = null, $fakultas = null, $role = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->when($prodi, function ($query) use ($prodi) {
return $query->where('prodi', $prodi);
})
->when($fakultas, function ($query) use ($fakultas) {
return $query->where('fakultas', $fakultas);
})
->when($role, function ($query) use ($role) {
return $query->whereHas('rolesCustom', function ($query) use ($role) {
$query->where('name', $role);
});
})
->first();
}
}
<?php
namespace App\Repositories\Auth;
use GuzzleHttp\Client as GuzzleHttpClient;
class EmailRepository
{
/**
* Get data from sso.
*
* @param varchar $email
* @return \Illuminate\Http\Response
*/
public function checkEmail($email)
{
$clientSso = new GuzzleHttpClient();
$apiRequestSso = $clientSso->request('GET', 'https://sso.unesa.ac.id/userid/'.$email);
$checkEmail = json_decode($apiRequestSso->getBody()->getContents());
return $checkEmail;
}
}
<?php
namespace App\Repositories\Auth;
use GuzzleHttp\Client as GuzzleHttpClient;
class IsdmRepository
{
/**
* Get data from isdm.
*
* @param varchar $nip
* @return \Illuminate\Http\Response
*/
public function nip($nip)
{
$client = new GuzzleHttpClient();
$apiRequest = $client->request('GET', 'https://i-sdm.unesa.ac.id/biodataumum/' . $nip);
$isdm = json_decode($apiRequest->getBody()->getContents());
return $isdm;
}
/**
* Get data from isdm.
*
* @param varchar $nidn
* @return \Illuminate\Http\Response
*/
public function nidn($nidn)
{
$client = new GuzzleHttpClient();
$apiRequest = $client->request('GET', 'https://i-sdm.unesa.ac.id/api/biodataumum/' . $nidn);
$isdm = json_decode($apiRequest->getBody()->getContents());
return $isdm;
}
}
<?php
namespace App\Repositories\Auth;
use App\Models\Role;
class RoleRepository
{
private $model;
public function __construct(Role $model)
{
$this->model = $model;
}
public function roles($roles)
{
return $this->model
->when($roles, function ($query) use ($roles) {
return $query->where('name', $roles);
})
->first();
}
public function store($user, $role)
{
return $user->assignRole($role);
}
public function delete($user, $role)
{
return $user->removeRole($role);
}
}
<?php
namespace App\Repositories\Auth;
use GuzzleHttp\Client as GuzzleHttpClient;
class SsoRepository
{
/**
* Check auth from sso.
*
* @param varchar $sessionId
* @return \Illuminate\Http\Response
*/
public function sso($sessionId)
{
// Get Token
try {
$clientauthscsso = new GuzzleHttpClient();
$apiRequestauthscsso = $clientauthscsso->request('GET', 'https://sso.unesa.ac.id/check-secret-token/' . $sessionId);
$cektoken = json_decode($apiRequestauthscsso->getBody()->getContents());
} catch (\Exception $apiRequestauthscsso) {
$error = 'Token Tidak Ditemukan';
return $error;
}
// Check Validation Token
try {
$clientauthtknsso = new GuzzleHttpClient();
$apiRequestauthtknsso = $clientauthtknsso->request('GET', 'https://sso.unesa.ac.id/check-token/' . $cektoken);
$checkakses = json_decode($apiRequestauthtknsso->getBody()->getContents());
} catch (\Exception $apiRequestauthtknsso) {
$error = 'Token Tidak Valid';
return $error;
}
// Get Account
try {
$clientbiodata = new GuzzleHttpClient();
$apiRequestbiodata = $clientbiodata->request('GET', 'https://sso.unesa.ac.id/userid/' . $checkakses->email);
$aksessso = json_decode($apiRequestbiodata->getBody()->getContents());
} catch (\Exception $apiRequestbiodata) {
$error = "Data Tidak Ditemukan";
return $error;
}
return $aksessso;
}
/**
* Get account from siakadu.
*
* @param varchar $nim
* @return \Illuminate\Http\Response
*/
public function getAccount($nim)
{
$url = "https://siakadu.unesa.ac.id/api/apiunggun";
$data = array('username' => $nim, 'kondisi' => "cekhakakses");
$x = kirim_data($url, 'post', $data);
$user = unserialize($x['isi']);
return $user;
}
}
<?php
namespace App\Repositories\Auth;
use App\Models\User;
class UserRepository
{
private $model;
public function __construct(User $model)
{
$this->model = $model;
}
public function find($with = null, $nip = null, $email = null, $id = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($nip, function ($query) use ($nip) {
return $query->whereHas('rBiodata', function ($query) use ($nip) {
$query->where('noidentitas', $nip);
});
})
->when($email, function ($query) use ($email) {
return $query->where('email', $email);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->first();
}
public function paginate($with = null, $search = null, $is_active = null, $paginate = 10)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($is_active, function ($query) use ($is_active) {
return $query->where('is_active', $is_active);
})
->when(!$is_active, function ($query) {
return $query->where('is_active', 0);
})
->when($search, function ($query) use ($search) {
return $query->where(function ($query) use ($search) {
return $query->where('nidn', 'ilike', '%'.$search.'%')
->orWhere('nip', 'ilike', '%'.$search.'%')
->orWhere('name', 'ilike', '%'.$search.'%');
});
})
->orderBy('name', 'asc')
->paginate($paginate);
}
public function storeSso($id, $data)
{
$data['id'] = $id;
$data['password'] = bcrypt($data['noid'].'s3cr3t5');
$data['is_active'] = 1;
return $this->model->create($data);
}
}
<?php
namespace App\Repositories\Permission;
use App\Repositories\Repository;
use Spatie\Permission\Models\Role;
class RoleRepository extends Repository
{
protected $model;
public function __construct(Role $model)
{
$this->model = $model;
}
public function find($with = null, $id = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->first();
}
public function get($with = null, $name = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($name, function ($query) use ($name) {
return $query->where('name', 'LIKE', '%' . $name . '%');
})
->orderBy('name', 'ASC')
->get();
}
public function paginate($with = null, $name = null, $limit = 10)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($name, function ($query) use ($name) {
return $query->where('name', 'LIKE', '%' . $name . '%');
})
->orderBy('name', 'ASC')
->paginate($limit);
}
}
<?php
namespace App\Repositories;
use Illuminate\Support\Facades\Storage;
abstract class Repository
{
protected $model;
/**
* Display specified resource.
*
* @param varchar $with
* @param uuid $id
*
* @return \Illuminate\Http\Response
*/
public function findId($id = null, $with = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->first();
}
/**
* Store a newly created resource in storage.
*
* @param \Illuminate\Http\Request $request
*
* @return \Illuminate\Http\Response
*/
public function store($request, $owner = 1)
{
if ($owner == 1) {
$request['userid_created'] = auth()->user()->id;
}
return $this->model->create($request);
}
/**
* Update the specified resource in storage.
*
* @param \Illuminate\Http\Request $request
* @param Model $model
*
* @return \Illuminate\Http\Response
*/
public function update($request, $model, $owner = 1)
{
if ($owner == 1) {
$request['userid_updated'] = auth()->user()->id;
}
return $model->update($request);
}
/**
* Show the specified resource in storage.
*
* @param uuid $id
*
* @return \Illuminate\Http\Response
*/
public function show($id)
{
return $this->model->where('user_id', $id)->first();
}
/**
* Remove the specified resource from storage.
*
* @param Model $model
*
* @return \Illuminate\Http\Response
*/
public function destroy($model)
{
return $model->delete();
}
/**
* Upload the specified resource from storage.
*
* @param $name
* @param Request $request
* @param $tipe
*
* @return \Illuminate\Http\Response
*/
public function upload($name, $request, $tipe)
{
$file = $request->file($tipe);
Storage::disk('static')->put('simia/uploads/'.$tipe.'/'.$name, file_get_contents($file->getRealPath()));
}
/**
* Remove the specified resource from storage.
*
* @param Model $model
* @param $tipe
*
* @return \Illuminate\Http\Response
*/
public function deletefile($model, $tipe)
{
if ($model->$tipe) {
Storage::disk('static')->delete('simia/uploads/'.$tipe.'/'.$model->$tipe);
}
}
}
<?php
namespace App\Repositories;
use App\Models\Auth\Biodata;
use Auth;
use Illuminate\Support\Str;
class UserdetailRepository
{
public function __construct(Biodata $model)
{
$this->model = $model;
}
public function findbyid($id = null, $with = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->first();
}
public function findbyuser($userid = null, $with = null, $nim = null)
{
return $this->model
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($userid, function ($query) use ($userid) {
return $query->where('user_id', $userid);
})
->when($nim, function ($query) use ($nim) {
return $query->where('noidentitas', $nim);
})
->first();
}
public function get($id = null, $with = null, $fakultas = null, $limit = 3000)
{
return $this->model
->when($id, function ($query) use ($id) {
return $query->where('id', $id);
})
->when($with, function ($query) use ($with) {
return $query->with($with);
})
->when($fakultas, function ($query) use ($fakultas) {
return $query->where('fakultas', $fakultas);
})
->orderBy('prodi', 'asc')
->limit($limit)
->get();
}
public function store($request)
{
$data = $request->except('_token');
$data['id'] = (string) Str::uuid();
$data['user_id'] = Auth::user()->id;
$data['userid_created'] = Auth::user()->id;
$data['userid_updated'] = Auth::user()->id;
$biodata = $this->model->create($data);
return $biodata;
}
public function storeSso($id, $data)
{
$data['id'] = $id;
$data['noidentitas'] = $data['noid'];
$data['type'] = $data['role'];
$data['origin'] = 'Universitas Negeri Surabaya';
return $this->model->create($data);
}
}
<?php
namespace App\Traits;
use Illuminate\Support\Str;
trait UuidTrait
{
/**
* Boot function from Laravel.
*/
protected static function boot()
{
parent::boot();
static::creating(function ($model) {
$model->incrementing = false;
$model->keyType = 'string';
$model->{$model->getKeyName()} = Str::uuid()->toString();
});
}
}
<?php
namespace App\View\Components;
use Illuminate\View\Component;
class AppLayout extends Component
{
/**
* Get the view / contents that represents the component.
*
* @return \Illuminate\View\View
*/
public function render()
{
return view('layouts.app');
}
}
<?php
namespace App\View\Components;
use Illuminate\View\Component;
class GuestLayout extends Component
{
/**
* Get the view / contents that represents the component.
*
* @return \Illuminate\View\View
*/
public function render()
{
return view('layouts.guest');
}
}
...@@ -8,23 +8,33 @@ ...@@ -8,23 +8,33 @@
], ],
"license": "MIT", "license": "MIT",
"require": { "require": {
"php": "^7.3", "php": "^7.3|^8.0",
"fideloper/proxy": "^4.2", "barryvdh/laravel-dompdf": "^0.8.7",
"dompdf/dompdf": "^0.8.6",
"fideloper/proxy": "^4.4",
"fruitcake/laravel-cors": "^2.0", "fruitcake/laravel-cors": "^2.0",
"guzzlehttp/guzzle": "^7.4", "guzzlehttp/guzzle": "^7.0.1",
"laravel/framework": "^8.0", "laravel/framework": "^8.12",
"laravel/tinker": "^2.0", "laravel/jetstream": "^2.9",
"laravel/sanctum": "^2.6",
"laravel/tinker": "^2.5",
"laravel/ui": "^3.4", "laravel/ui": "^3.4",
"laravelcollective/html": "^6.3", "laravelcollective/html": "^6.2",
"realrashid/sweet-alert": "^5.1", "livewire/livewire": "^2.5",
"webpatser/laravel-uuid": "4.0" "maatwebsite/excel": "^3.1",
"realrashid/sweet-alert": "^3.1",
"spatie/laravel-permission": "^3.17",
"uxweb/sweet-alert": "^2.0",
"webpatser/laravel-uuid": "4.0",
"yajra/laravel-datatables-oracle": "~9.0"
}, },
"require-dev": { "require-dev": {
"facade/ignition": "^2.3.6", "barryvdh/laravel-debugbar": "^3.5",
"fzaninotto/faker": "^1.9.1", "facade/ignition": "^2.5",
"mockery/mockery": "^1.3.1", "fakerphp/faker": "^1.9.1",
"mockery/mockery": "^1.4.2",
"nunomaduro/collision": "^5.0", "nunomaduro/collision": "^5.0",
"phpunit/phpunit": "^9.3" "phpunit/phpunit": "^9.3.3"
}, },
"config": { "config": {
"optimize-autoloader": true, "optimize-autoloader": true,
...@@ -41,7 +51,11 @@ ...@@ -41,7 +51,11 @@
"App\\": "app/", "App\\": "app/",
"Database\\Factories\\": "database/factories/", "Database\\Factories\\": "database/factories/",
"Database\\Seeders\\": "database/seeders/" "Database\\Seeders\\": "database/seeders/"
} },
"files": [
"app/Helpers/InseoHelper.php",
"app/Helpers/Inseo.php"
]
}, },
"autoload-dev": { "autoload-dev": {
"psr-4": { "psr-4": {
......
This source diff could not be displayed because it is too large. You can view the blob instead.
...@@ -174,6 +174,8 @@ return [ ...@@ -174,6 +174,8 @@ return [
// App\Providers\BroadcastServiceProvider::class, // App\Providers\BroadcastServiceProvider::class,
App\Providers\EventServiceProvider::class, App\Providers\EventServiceProvider::class,
App\Providers\RouteServiceProvider::class, App\Providers\RouteServiceProvider::class,
App\Providers\FortifyServiceProvider::class,
App\Providers\JetstreamServiceProvider::class,
Collective\Html\HtmlServiceProvider::class, Collective\Html\HtmlServiceProvider::class,
RealRashid\SweetAlert\SweetAlertServiceProvider::class, RealRashid\SweetAlert\SweetAlertServiceProvider::class,
......
...@@ -65,6 +65,13 @@ return [ ...@@ -65,6 +65,13 @@ return [
'endpoint' => env('AWS_ENDPOINT'), 'endpoint' => env('AWS_ENDPOINT'),
], ],
'static' => [
'driver' => 'ftp',
'host' => env('FILE_HOST'),
'username' => env('FILE_USER'),
'password' => env('FILE_PASS'),
'ssl' => true,
],
], ],
/* /*
......
<?php
use App\Providers\RouteServiceProvider;
use Laravel\Fortify\Features;
return [
/*
|--------------------------------------------------------------------------
| Fortify Guard
|--------------------------------------------------------------------------
|
| Here you may specify which authentication guard Fortify will use while
| authenticating users. This value should correspond with one of your
| guards that is already present in your "auth" configuration file.
|
*/
'guard' => 'web',
/*
|--------------------------------------------------------------------------
| Fortify Password Broker
|--------------------------------------------------------------------------
|
| Here you may specify which password broker Fortify can use when a user
| is resetting their password. This configured value should match one
| of your password brokers setup in your "auth" configuration file.
|
*/
'passwords' => 'users',
/*
|--------------------------------------------------------------------------
| Username / Email
|--------------------------------------------------------------------------
|
| This value defines which model attribute should be considered as your
| application's "username" field. Typically, this might be the email
| address of the users but you are free to change this value here.
|
| Out of the box, Fortify expects forgot password and reset password
| requests to have a field named 'email'. If the application uses
| another name for the field you may define it below as needed.
|
*/
'username' => 'email',
'email' => 'email',
/*
|--------------------------------------------------------------------------
| Home Path
|--------------------------------------------------------------------------
|
| Here you may configure the path where users will get redirected during
| authentication or password reset when the operations are successful
| and the user is authenticated. You are free to change this value.
|
*/
'home' => RouteServiceProvider::HOME,
/*
|--------------------------------------------------------------------------
| Fortify Routes Prefix / Subdomain
|--------------------------------------------------------------------------
|
| Here you may specify which prefix Fortify will assign to all the routes
| that it registers with the application. If necessary, you may change
| subdomain under which all of the Fortify routes will be available.
|
*/
'prefix' => '',
'domain' => null,
/*
|--------------------------------------------------------------------------
| Fortify Routes Middleware
|--------------------------------------------------------------------------
|
| Here you may specify which middleware Fortify will assign to the routes
| that it registers with the application. If necessary, you may change
| these middleware but typically this provided default is preferred.
|
*/
'middleware' => ['web'],
/*
|--------------------------------------------------------------------------
| Rate Limiting
|--------------------------------------------------------------------------
|
| By default, Fortify will throttle logins to five requests per minute for
| every email and IP address combination. However, if you would like to
| specify a custom rate limiter to call then you may specify it here.
|
*/
'limiters' => [
'login' => 'login',
'two-factor' => 'two-factor',
],
/*
|--------------------------------------------------------------------------
| Register View Routes
|--------------------------------------------------------------------------
|
| Here you may specify if the routes returning views should be disabled as
| you may not need them when building your own application. This may be
| especially true if you're writing a custom single-page application.
|
*/
'views' => true,
/*
|--------------------------------------------------------------------------
| Features
|--------------------------------------------------------------------------
|
| Some of the Fortify features are optional. You may disable the features
| by removing them from this array. You're free to only remove some of
| these features or you can even remove all of these if you need to.
|
*/
'features' => [
Features::registration(),
Features::resetPasswords(),
// Features::emailVerification(),
Features::updateProfileInformation(),
Features::updatePasswords(),
Features::twoFactorAuthentication([
'confirm' => true,
'confirmPassword' => true,
// 'window' => 0,
]),
],
];
<?php
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Middleware\AuthenticateSession;
return [
/*
|--------------------------------------------------------------------------
| Jetstream Stack
|--------------------------------------------------------------------------
|
| This configuration value informs Jetstream which "stack" you will be
| using for your application. In general, this value is set for you
| during installation and will not need to be changed after that.
|
*/
'stack' => 'livewire',
/*
|--------------------------------------------------------------------------
| Jetstream Route Middleware
|--------------------------------------------------------------------------
|
| Here you may specify which middleware Jetstream will assign to the routes
| that it registers with the application. When necessary, you may modify
| these middleware; however, this default value is usually sufficient.
|
*/
'middleware' => ['web'],
'auth_session' => AuthenticateSession::class,
/*
|--------------------------------------------------------------------------
| Jetstream Guard
|--------------------------------------------------------------------------
|
| Here you may specify the authentication guard Jetstream will use while
| authenticating users. This value should correspond with one of your
| guards that is already present in your "auth" configuration file.
|
*/
'guard' => 'sanctum',
/*
|--------------------------------------------------------------------------
| Features
|--------------------------------------------------------------------------
|
| Some of Jetstream's features are optional. You may disable the features
| by removing them from this array. You're free to only remove some of
| these features or you can even remove all of these if you need to.
|
*/
'features' => [
// Features::termsAndPrivacyPolicy(),
// Features::profilePhotos(),
// Features::api(),
Features::teams(['invitations' => true]),
Features::accountDeletion(),
],
/*
|--------------------------------------------------------------------------
| Profile Photo Disk
|--------------------------------------------------------------------------
|
| This configuration value determines the default disk that will be used
| when storing profile photos for your application's users. Typically
| this will be the "public" disk but you may adjust this if needed.
|
*/
'profile_photo_disk' => 'public',
];
<?php
use Laravel\Sanctum\Sanctum;
return [
/*
|--------------------------------------------------------------------------
| Stateful Domains
|--------------------------------------------------------------------------
|
| Requests from the following domains / hosts will receive stateful API
| authentication cookies. Typically, these should include your local
| and production domains which access your API via a frontend SPA.
|
*/
'stateful' => explode(',', env('SANCTUM_STATEFUL_DOMAINS', sprintf(
'%s%s',
'localhost,localhost:3000,127.0.0.1,127.0.0.1:8000,::1',
Sanctum::currentApplicationUrlWithPort()
))),
/*
|--------------------------------------------------------------------------
| Sanctum Guards
|--------------------------------------------------------------------------
|
| This array contains the authentication guards that will be checked when
| Sanctum is trying to authenticate a request. If none of these guards
| are able to authenticate the request, Sanctum will use the bearer
| token that's present on an incoming request for authentication.
|
*/
'guard' => ['web'],
/*
|--------------------------------------------------------------------------
| Expiration Minutes
|--------------------------------------------------------------------------
|
| This value controls the number of minutes until an issued token will be
| considered expired. If this value is null, personal access tokens do
| not expire. This won't tweak the lifetime of first-party sessions.
|
*/
'expiration' => null,
/*
|--------------------------------------------------------------------------
| Sanctum Middleware
|--------------------------------------------------------------------------
|
| When authenticating your first-party SPA with Sanctum you may need to
| customize some of the middleware Sanctum uses while processing the
| request. You may change the middleware listed below as required.
|
*/
'middleware' => [
'verify_csrf_token' => App\Http\Middleware\VerifyCsrfToken::class,
'encrypt_cookies' => App\Http\Middleware\EncryptCookies::class,
],
];
...@@ -18,7 +18,7 @@ return [ ...@@ -18,7 +18,7 @@ return [
| |
*/ */
'driver' => env('SESSION_DRIVER', 'file'), 'driver' => env('SESSION_DRIVER', 'database'),
/* /*
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------
......
<?php
namespace Database\Factories;
use App\Models\Team;
use App\Models\User;
use Illuminate\Database\Eloquent\Factories\Factory;
class TeamFactory extends Factory
{
/**
* The name of the factory's corresponding model.
*
* @var string
*/
protected $model = Team::class;
/**
* Define the model's default state.
*
* @return array
*/
public function definition()
{
return [
'name' => $this->faker->unique()->company(),
'user_id' => User::factory(),
'personal_team' => true,
];
}
}
...@@ -2,9 +2,11 @@ ...@@ -2,9 +2,11 @@
namespace Database\Factories; namespace Database\Factories;
use App\Models\Team;
use App\Models\User; use App\Models\User;
use Illuminate\Database\Eloquent\Factories\Factory; use Illuminate\Database\Eloquent\Factories\Factory;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use Laravel\Jetstream\Features;
class UserFactory extends Factory class UserFactory extends Factory
{ {
...@@ -23,11 +25,45 @@ class UserFactory extends Factory ...@@ -23,11 +25,45 @@ class UserFactory extends Factory
public function definition() public function definition()
{ {
return [ return [
'name' => $this->faker->name, 'name' => $this->faker->name(),
'email' => $this->faker->unique()->safeEmail, 'email' => $this->faker->unique()->safeEmail(),
'email_verified_at' => now(), 'email_verified_at' => now(),
'password' => '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', // password 'password' => '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', // password
'remember_token' => Str::random(10), 'remember_token' => Str::random(10),
]; ];
} }
/**
* Indicate that the model's email address should be unverified.
*
* @return \Illuminate\Database\Eloquent\Factories\Factory
*/
public function unverified()
{
return $this->state(function (array $attributes) {
return [
'email_verified_at' => null,
];
});
}
/**
* Indicate that the user should have a personal team.
*
* @return $this
*/
public function withPersonalTeam()
{
if (! Features::hasTeamFeatures()) {
return $this->state([]);
}
return $this->has(
Team::factory()
->state(function (array $attributes, User $user) {
return ['name' => $user->name.'\'s Team', 'user_id' => $user->id, 'personal_team' => true];
}),
'ownedTeams'
);
}
} }
...@@ -4,7 +4,7 @@ use Illuminate\Database\Migrations\Migration; ...@@ -4,7 +4,7 @@ use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint; use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema; use Illuminate\Support\Facades\Schema;
class CreateUsersTable extends Migration return new class extends Migration
{ {
/** /**
* Run the migrations. * Run the migrations.
...@@ -17,10 +17,11 @@ class CreateUsersTable extends Migration ...@@ -17,10 +17,11 @@ class CreateUsersTable extends Migration
$table->id(); $table->id();
$table->string('name'); $table->string('name');
$table->string('email')->unique(); $table->string('email')->unique();
$table->string('role');
$table->timestamp('email_verified_at')->nullable(); $table->timestamp('email_verified_at')->nullable();
$table->string('password'); $table->string('password');
$table->rememberToken(); $table->rememberToken();
$table->foreignId('current_team_id')->nullable();
$table->string('profile_photo_path', 2048)->nullable();
$table->timestamps(); $table->timestamps();
}); });
} }
...@@ -34,4 +35,4 @@ class CreateUsersTable extends Migration ...@@ -34,4 +35,4 @@ class CreateUsersTable extends Migration
{ {
Schema::dropIfExists('users'); Schema::dropIfExists('users');
} }
} };
...@@ -4,7 +4,7 @@ use Illuminate\Database\Migrations\Migration; ...@@ -4,7 +4,7 @@ use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint; use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema; use Illuminate\Support\Facades\Schema;
return new class extends Migration class CreatePasswordResetsTable extends Migration
{ {
/** /**
* Run the migrations. * Run the migrations.
...@@ -29,4 +29,4 @@ return new class extends Migration ...@@ -29,4 +29,4 @@ return new class extends Migration
{ {
Schema::dropIfExists('password_resets'); Schema::dropIfExists('password_resets');
} }
}; }
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
use Laravel\Fortify\Fortify;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::table('users', function (Blueprint $table) {
$table->text('two_factor_secret')
->after('password')
->nullable();
$table->text('two_factor_recovery_codes')
->after('two_factor_secret')
->nullable();
if (Fortify::confirmsTwoFactorAuthentication()) {
$table->timestamp('two_factor_confirmed_at')
->after('two_factor_recovery_codes')
->nullable();
}
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::table('users', function (Blueprint $table) {
$table->dropColumn(array_merge([
'two_factor_secret',
'two_factor_recovery_codes',
], Fortify::confirmsTwoFactorAuthentication() ? [
'two_factor_confirmed_at',
] : []));
});
}
};
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateBiodata extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('biodata', function (Blueprint $table) {
$table->uuid('id');
$table->uuid('user_id');
$table->string('noidentitas')->nullable();
$table->string('name')->nullable();
$table->string('fakultas')->nullable();
$table->string('prodi')->nullable();
$table->string('telephone')->nullable();
$table->string('phone')->nullable();
$table->string('email')->nullable();
$table->string('web')->nullable();
$table->uuid('userid_created')->nullable();
$table->uuid('userid_updated')->nullable();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('biodata');
}
}
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreatePersonalAccessTokensTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('personal_access_tokens', function (Blueprint $table) {
$table->bigIncrements('id');
$table->morphs('tokenable');
$table->string('name');
$table->string('token', 64)->unique();
$table->text('abilities')->nullable();
$table->timestamp('last_used_at')->nullable();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('personal_access_tokens');
}
}
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('teams', function (Blueprint $table) {
$table->id();
$table->foreignId('user_id')->index();
$table->string('name');
$table->boolean('personal_team');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('teams');
}
};
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('team_user', function (Blueprint $table) {
$table->id();
$table->foreignId('team_id');
$table->foreignId('user_id');
$table->string('role')->nullable();
$table->timestamps();
$table->unique(['team_id', 'user_id']);
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('team_user');
}
};
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('team_invitations', function (Blueprint $table) {
$table->id();
$table->foreignId('team_id')->constrained()->cascadeOnDelete();
$table->string('email');
$table->string('role')->nullable();
$table->timestamps();
$table->unique(['team_id', 'email']);
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('team_invitations');
}
};
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateSessionsTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('sessions', function (Blueprint $table) {
$table->string('id')->primary();
$table->foreignUuid('user_id')->nullable()->index();
$table->string('ip_address', 45)->nullable();
$table->text('user_agent')->nullable();
$table->text('payload');
$table->integer('last_activity')->index();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('sessions');
}
}
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreatePermissionTables extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
$tableNames = config('permission.table_names');
$columnNames = config('permission.column_names');
if (empty($tableNames)) {
throw new \Exception('Error: config/permission.php not loaded. Run [php artisan config:clear] and try again.');
}
Schema::create($tableNames['permissions'], function (Blueprint $table) {
// $table->bigIncrements('id');
$table->uuid('id');
$table->string('name');
$table->string('guard_name');
$table->timestamps();
$table->primary('id');
});
Schema::create($tableNames['roles'], function (Blueprint $table) {
// $table->bigIncrements('id');
$table->uuid('id');
$table->string('name');
$table->string('guard_name');
$table->timestamps();
$table->primary('id');
});
Schema::create($tableNames['model_has_permissions'], function (Blueprint $table) use ($tableNames, $columnNames) {
// $table->unsignedBigInteger('permission_id');
$table->uuid('permission_id');
$table->string('model_type');
// $table->unsignedBigInteger($columnNames['model_morph_key']);
$table->uuid($columnNames['model_morph_key']);
$table->index([$columnNames['model_morph_key'], 'model_type'], 'model_has_permissions_model_id_model_type_index');
$table->foreign('permission_id')
->references('id')
->on($tableNames['permissions'])
->onDelete('cascade');
$table->primary(['permission_id', $columnNames['model_morph_key'], 'model_type'],
'model_has_permissions_permission_model_type_primary');
});
Schema::create($tableNames['model_has_roles'], function (Blueprint $table) use ($tableNames, $columnNames) {
// $table->unsignedBigInteger('role_id');
$table->uuid('role_id');
$table->string('model_type');
$table->uuid($columnNames['model_morph_key']);
// $table->unsignedBigInteger($columnNames['model_morph_key']);
$table->index([$columnNames['model_morph_key'], 'model_type'], 'model_has_roles_model_id_model_type_index');
$table->foreign('role_id')
->references('id')
->on($tableNames['roles'])
->onDelete('cascade');
$table->primary(['role_id', $columnNames['model_morph_key'], 'model_type'],
'model_has_roles_role_model_type_primary');
});
Schema::create($tableNames['role_has_permissions'], function (Blueprint $table) use ($tableNames) {
// $table->unsignedBigInteger('permission_id');
// $table->unsignedBigInteger('role_id');
$table->uuid('permission_id');
$table->uuid('role_id');
$table->foreign('permission_id')
->references('id')
->on($tableNames['permissions'])
->onDelete('cascade');
$table->foreign('role_id')
->references('id')
->on($tableNames['roles'])
->onDelete('cascade');
$table->primary(['permission_id', 'role_id'], 'role_has_permissions_permission_id_role_id_primary');
});
app('cache')
->store(config('permission.cache.store') != 'default' ? config('permission.cache.store') : null)
->forget(config('permission.cache.key'));
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
$tableNames = config('permission.table_names');
if (empty($tableNames)) {
throw new \Exception('Error: config/permission.php not found and defaults could not be merged. Please publish the package configuration before proceeding, or drop the tables manually.');
}
Schema::drop($tableNames['role_has_permissions']);
Schema::drop($tableNames['model_has_roles']);
Schema::drop($tableNames['model_has_permissions']);
Schema::drop($tableNames['roles']);
Schema::drop($tableNames['permissions']);
}
}
This source diff could not be displayed because it is too large. You can view the blob instead.
...@@ -11,14 +11,22 @@ ...@@ -11,14 +11,22 @@
}, },
"devDependencies": { "devDependencies": {
"@popperjs/core": "^2.10.2", "@popperjs/core": "^2.10.2",
"@tailwindcss/forms": "^0.5.2",
"@tailwindcss/typography": "^0.5.0",
"@tailwindcss/ui": "^0.6.0",
"alpinejs": "^3.0.6",
"autoprefixer": "^10.4.7",
"axios": "^0.19", "axios": "^0.19",
"bootstrap": "^5.1.3", "bootstrap": "^5.1.3",
"cross-env": "^7.0", "cross-env": "^7.0",
"laravel-mix": "^5.0.1", "laravel-mix": "^5.0.1",
"lodash": "^4.17.19", "lodash": "^4.17.19",
"postcss": "^8.4.14",
"postcss-import": "^12.0.1",
"resolve-url-loader": "^3.1.0", "resolve-url-loader": "^3.1.0",
"sass": "^1.32.11", "sass": "^1.32.11",
"sass-loader": "^11.0.1", "sass-loader": "^11.0.1",
"tailwindcss": "^3.1.0",
"webpack-cli": "^4.10.0" "webpack-cli": "^4.10.0"
} }
} }
module.exports = {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
};
/*! normalize.css v8.0.1 | MIT License | github.com/necolas/normalize.css */html{line-height:1.15;-webkit-text-size-adjust:100%}body{margin:0}main{display:block}h1{font-size:2em;margin:.67em 0}hr{box-sizing:content-box;height:0;overflow:visible}pre{font-family:monospace,monospace;font-size:1em}a{background-color:transparent}abbr[title]{border-bottom:none;text-decoration:underline;-webkit-text-decoration:underline dotted;text-decoration:underline dotted}b,strong{font-weight:bolder}code,kbd,samp{font-family:monospace,monospace;font-size:1em}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}img{border-style:none}button,input,optgroup,select,textarea{font-family:inherit;font-size:100%;line-height:1.15;margin:0}button,input{overflow:visible}button,select{text-transform:none}[type=button],[type=reset],[type=submit],button{-webkit-appearance:button}[type=button]::-moz-focus-inner,[type=reset]::-moz-focus-inner,[type=submit]::-moz-focus-inner,button::-moz-focus-inner{border-style:none;padding:0}[type=button]:-moz-focusring,[type=reset]:-moz-focusring,[type=submit]:-moz-focusring,button:-moz-focusring{outline:1px dotted ButtonText}fieldset{padding:.35em .75em .625em}legend{box-sizing:border-box;color:inherit;display:table;max-width:100%;padding:0;white-space:normal}progress{vertical-align:baseline}textarea{overflow:auto}[type=checkbox],[type=radio]{box-sizing:border-box;padding:0}[type=number]::-webkit-inner-spin-button,[type=number]::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}[type=search]::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}details{display:block}summary{display:list-item}[hidden],template{display:none}blockquote,dd,dl,figure,h1,h2,h3,h4,h5,h6,hr,p,pre{margin:0}button{background-color:transparent;background-image:none}button:focus{outline:1px dotted;outline:5px auto -webkit-focus-ring-color}fieldset,ol,ul{margin:0;padding:0}ol,ul{list-style:none}html{font-family:Nunito,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,Noto Sans,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol,Noto Color Emoji;line-height:1.5}*,:after,:before{box-sizing:border-box;border:0 solid #d2d6dc}hr{border-top-width:1px}img{border-style:solid}textarea{resize:vertical}input::-moz-placeholder,textarea::-moz-placeholder{color:#a0aec0}input:-ms-input-placeholder,textarea:-ms-input-placeholder{color:#a0aec0}input::-ms-input-placeholder,textarea::-ms-input-placeholder{color:#a0aec0}input::placeholder,textarea::placeholder{color:#a0aec0}[role=button],button{cursor:pointer}table{border-collapse:collapse}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;text-decoration:inherit}button,input,optgroup,select,textarea{padding:0;line-height:inherit;color:inherit}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace}audio,canvas,embed,iframe,img,object,svg,video{display:block;vertical-align:middle}img,video{max-width:100%;height:auto}.container{width:100%}@media (min-width:640px){.container{max-width:640px}}@media (min-width:768px){.container{max-width:768px}}@media (min-width:1024px){.container{max-width:1024px}}@media (min-width:1280px){.container{max-width:1280px}}.form-input{-webkit-appearance:none;-moz-appearance:none;appearance:none;background-color:#fff;border-color:#d2d6dc;border-width:1px;border-radius:.375rem;padding:.5rem .75rem;font-size:1rem;line-height:1.5}.form-input::-moz-placeholder{color:#9fa6b2;opacity:1}.form-input:-ms-input-placeholder{color:#9fa6b2;opacity:1}.form-input::-ms-input-placeholder{color:#9fa6b2;opacity:1}.form-input::placeholder{color:#9fa6b2;opacity:1}.form-input:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-textarea{-webkit-appearance:none;-moz-appearance:none;appearance:none;background-color:#fff;border-color:#d2d6dc;border-width:1px;border-radius:.375rem;padding:.5rem .75rem;font-size:1rem;line-height:1.5}.form-textarea::-moz-placeholder{color:#9fa6b2;opacity:1}.form-textarea:-ms-input-placeholder{color:#9fa6b2;opacity:1}.form-textarea::-ms-input-placeholder{color:#9fa6b2;opacity:1}.form-textarea::placeholder{color:#9fa6b2;opacity:1}.form-textarea:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-multiselect{-webkit-appearance:none;-moz-appearance:none;appearance:none;background-color:#fff;border-color:#d2d6dc;border-width:1px;border-radius:.375rem;padding:.5rem .75rem;font-size:1rem;line-height:1.5}.form-multiselect:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-select{background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='none'%3E%3Cpath d='M7 7l3-3 3 3m0 6l-3 3-3-3' stroke='%239fa6b2' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");-webkit-appearance:none;-moz-appearance:none;appearance:none;-webkit-print-color-adjust:exact;color-adjust:exact;background-repeat:no-repeat;background-color:#fff;border-color:#d2d6dc;border-width:1px;border-radius:.375rem;padding:.5rem 2.5rem .5rem .75rem;font-size:1rem;line-height:1.5;background-position:right .5rem center;background-size:1.5em 1.5em}.form-select::-ms-expand{color:#9fa6b2;border:none}@media not print{.form-select::-ms-expand{display:none}}@media print and (-ms-high-contrast:active),print and (-ms-high-contrast:none){.form-select{padding-right:.75rem}}.form-select:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-checkbox:checked{background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg viewBox='0 0 16 16' fill='%23fff' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M5.707 7.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4a1 1 0 00-1.414-1.414L7 8.586 5.707 7.293z'/%3E%3C/svg%3E");border-color:transparent;background-color:currentColor;background-size:100% 100%;background-position:50%;background-repeat:no-repeat}@media not print{.form-checkbox::-ms-check{border-width:1px;color:transparent;background:inherit;border-color:inherit;border-radius:inherit}}.form-checkbox{-webkit-appearance:none;-moz-appearance:none;appearance:none;-webkit-print-color-adjust:exact;color-adjust:exact;display:inline-block;vertical-align:middle;background-origin:border-box;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;flex-shrink:0;height:1rem;width:1rem;color:#3f83f8;background-color:#fff;border-color:#d2d6dc;border-width:1px;border-radius:.25rem}.form-checkbox:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-checkbox:checked:focus,.form-radio:checked{border-color:transparent}.form-radio:checked{background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg viewBox='0 0 16 16' fill='%23fff' xmlns='http://www.w3.org/2000/svg'%3E%3Ccircle cx='8' cy='8' r='3'/%3E%3C/svg%3E");background-color:currentColor;background-size:100% 100%;background-position:50%;background-repeat:no-repeat}@media not print{.form-radio::-ms-check{border-width:1px;color:transparent;background:inherit;border-color:inherit;border-radius:inherit}}.form-radio{-webkit-appearance:none;-moz-appearance:none;appearance:none;-webkit-print-color-adjust:exact;color-adjust:exact;display:inline-block;vertical-align:middle;background-origin:border-box;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;flex-shrink:0;border-radius:100%;height:1rem;width:1rem;color:#3f83f8;background-color:#fff;border-color:#d2d6dc;border-width:1px}.form-radio:focus{outline:none;box-shadow:0 0 0 3px rgba(164,202,254,.45);border-color:#a4cafe}.form-radio:checked:focus{border-color:transparent}.prose{color:#374151;max-width:65ch}.prose [class~=lead]{color:#4b5563;font-size:1.25em;line-height:1.6;margin-top:1.2em;margin-bottom:1.2em}.prose a{color:#5850ec;text-decoration:none;font-weight:600}.prose strong{color:#161e2e;font-weight:600}.prose ol{counter-reset:list-counter;margin-top:1.25em;margin-bottom:1.25em}.prose ol>li{position:relative;counter-increment:list-counter;padding-left:1.75em}.prose ol>li:before{content:counter(list-counter) ".";position:absolute;font-weight:400;color:#6b7280}.prose ul>li{position:relative;padding-left:1.75em}.prose ul>li:before{content:"";position:absolute;background-color:#d2d6dc;border-radius:50%;width:.375em;height:.375em;top:.6875em;left:.25em}.prose hr{border-color:#e5e7eb;border-top-width:1px;margin-top:3em;margin-bottom:3em}.prose blockquote{font-weight:500;font-style:italic;color:#161e2e;border-left-width:.25rem;border-left-color:#e5e7eb;quotes:"\201C""\201D""\2018""\2019";margin-top:1.6em;margin-bottom:1.6em;padding-left:1em}.prose blockquote p:first-of-type:before{content:open-quote}.prose blockquote p:last-of-type:after{content:close-quote}.prose h1{color:#1a202c;font-weight:800;font-size:2.25em;margin-top:0;margin-bottom:.8888889em;line-height:1.1111111}.prose h2{color:#1a202c;font-weight:700;font-size:1.5em;margin-top:2em;margin-bottom:1em;line-height:1.3333333}.prose h3{font-size:1.25em;margin-top:1.6em;margin-bottom:.6em;line-height:1.6}.prose h3,.prose h4{color:#1a202c;font-weight:600}.prose h4{margin-top:1.5em;margin-bottom:.5em;line-height:1.5}.prose figure figcaption{color:#6b7280;font-size:.875em;line-height:1.4285714;margin-top:.8571429em}.prose code{color:#161e2e;font-weight:600;font-size:.875em}.prose code:after,.prose code:before{content:"`"}.prose pre{color:#e5e7eb;background-color:#252f3f;overflow-x:auto;font-size:.875em;line-height:1.7142857;margin-top:1.7142857em;margin-bottom:1.7142857em;border-radius:.375rem;padding:.8571429em 1.1428571em}.prose pre code{background-color:transparent;border-width:0;border-radius:0;padding:0;font-weight:400;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}.prose pre code:after,.prose pre code:before{content:""}.prose table{width:100%;table-layout:auto;text-align:left;margin-top:2em;margin-bottom:2em;font-size:.875em;line-height:1.7142857}.prose thead{color:#161e2e;font-weight:600;border-bottom-width:1px;border-bottom-color:#d2d6dc}.prose thead th{vertical-align:bottom;padding-right:.5714286em;padding-bottom:.5714286em;padding-left:.5714286em}.prose tbody tr{border-bottom-width:1px;border-bottom-color:#e5e7eb}.prose tbody tr:last-child{border-bottom-width:0}.prose tbody td{vertical-align:top;padding:.5714286em}.prose{font-size:1rem;line-height:1.75}.prose p{margin-top:1.25em;margin-bottom:1.25em}.prose figure,.prose img,.prose video{margin-top:2em;margin-bottom:2em}.prose figure>*{margin-top:0;margin-bottom:0}.prose h2 code{font-size:.875em}.prose h3 code{font-size:.9em}.prose ul{margin-top:1.25em;margin-bottom:1.25em}.prose li{margin-top:.5em;margin-bottom:.5em}.prose ol>li:before{left:0}.prose>ul>li p{margin-top:.75em;margin-bottom:.75em}.prose>ul>li>:first-child{margin-top:1.25em}.prose>ul>li>:last-child{margin-bottom:1.25em}.prose>ol>li>:first-child{margin-top:1.25em}.prose>ol>li>:last-child{margin-bottom:1.25em}.prose ol ol,.prose ol ul,.prose ul ol,.prose ul ul{margin-top:.75em;margin-bottom:.75em}.prose h2+*,.prose h3+*,.prose h4+*,.prose hr+*{margin-top:0}.prose thead th:first-child{padding-left:0}.prose thead th:last-child{padding-right:0}.prose tbody td:first-child{padding-left:0}.prose tbody td:last-child{padding-right:0}.prose>:first-child{margin-top:0}.prose>:last-child{margin-bottom:0}.prose h1,.prose h2,.prose h3,.prose h4{color:#161e2e}.prose-sm{font-size:.875rem;line-height:1.7142857}.prose-sm p{margin-top:1.1428571em;margin-bottom:1.1428571em}.prose-sm [class~=lead]{font-size:1.2857143em;line-height:1.5555556;margin-top:.8888889em;margin-bottom:.8888889em}.prose-sm blockquote{margin-top:1.3333333em;margin-bottom:1.3333333em;padding-left:1.1111111em}.prose-sm h1{font-size:2.1428571em;margin-top:0;margin-bottom:.8em;line-height:1.2}.prose-sm h2{font-size:1.4285714em;margin-top:1.6em;margin-bottom:.8em;line-height:1.4}.prose-sm h3{font-size:1.2857143em;margin-top:1.5555556em;margin-bottom:.4444444em;line-height:1.5555556}.prose-sm h4{margin-top:1.4285714em;margin-bottom:.5714286em;line-height:1.4285714}.prose-sm figure,.prose-sm img,.prose-sm video{margin-top:1.7142857em;margin-bottom:1.7142857em}.prose-sm figure>*{margin-top:0;margin-bottom:0}.prose-sm figure figcaption{font-size:.8571429em;line-height:1.3333333;margin-top:.6666667em}.prose-sm code{font-size:.8571429em}.prose-sm h2 code{font-size:.9em}.prose-sm h3 code{font-size:.8888889em}.prose-sm pre{font-size:.8571429em;line-height:1.6666667;margin-top:1.6666667em;margin-bottom:1.6666667em;border-radius:.25rem;padding:.6666667em 1em}.prose-sm ol,.prose-sm ul{margin-top:1.1428571em;margin-bottom:1.1428571em}.prose-sm li{margin-top:.2857143em;margin-bottom:.2857143em}.prose-sm ol>li{padding-left:1.5714286em}.prose-sm ol>li:before{left:0}.prose-sm ul>li{padding-left:1.5714286em}.prose-sm ul>li:before{height:.3571429em;width:.3571429em;top:.67857em;left:.2142857em}.prose-sm>ul>li p{margin-top:.5714286em;margin-bottom:.5714286em}.prose-sm>ul>li>:first-child{margin-top:1.1428571em}.prose-sm>ul>li>:last-child{margin-bottom:1.1428571em}.prose-sm>ol>li>:first-child{margin-top:1.1428571em}.prose-sm>ol>li>:last-child{margin-bottom:1.1428571em}.prose-sm ol ol,.prose-sm ol ul,.prose-sm ul ol,.prose-sm ul ul{margin-top:.5714286em;margin-bottom:.5714286em}.prose-sm hr{margin-top:2.8571429em;margin-bottom:2.8571429em}.prose-sm h2+*,.prose-sm h3+*,.prose-sm h4+*,.prose-sm hr+*{margin-top:0}.prose-sm table{font-size:.8571429em;line-height:1.5}.prose-sm thead th{padding-right:1em;padding-bottom:.6666667em;padding-left:1em}.prose-sm thead th:first-child{padding-left:0}.prose-sm thead th:last-child{padding-right:0}.prose-sm tbody td{padding:.6666667em 1em}.prose-sm tbody td:first-child{padding-left:0}.prose-sm tbody td:last-child{padding-right:0}.prose-sm>:first-child{margin-top:0}.prose-sm>:last-child{margin-bottom:0}.prose-lg{font-size:1.125rem;line-height:1.7777778}.prose-lg p{margin-top:1.3333333em;margin-bottom:1.3333333em}.prose-lg [class~=lead]{font-size:1.2222222em;line-height:1.4545455;margin-top:1.0909091em;margin-bottom:1.0909091em}.prose-lg blockquote{margin-top:1.6666667em;margin-bottom:1.6666667em;padding-left:1em}.prose-lg h1{font-size:2.6666667em;margin-top:0;margin-bottom:.8333333em;line-height:1}.prose-lg h2{font-size:1.6666667em;margin-top:1.8666667em;margin-bottom:1.0666667em;line-height:1.3333333}.prose-lg h3{font-size:1.3333333em;margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.prose-lg h4{margin-top:1.7777778em;margin-bottom:.4444444em;line-height:1.5555556}.prose-lg figure,.prose-lg img,.prose-lg video{margin-top:1.7777778em;margin-bottom:1.7777778em}.prose-lg figure>*{margin-top:0;margin-bottom:0}.prose-lg figure figcaption{font-size:.8888889em;line-height:1.5;margin-top:1em}.prose-lg code{font-size:.8888889em}.prose-lg h2 code{font-size:.8666667em}.prose-lg h3 code{font-size:.875em}.prose-lg pre{font-size:.8888889em;line-height:1.75;margin-top:2em;margin-bottom:2em;border-radius:.375rem;padding:1em 1.5em}.prose-lg ol,.prose-lg ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.prose-lg li{margin-top:.6666667em;margin-bottom:.6666667em}.prose-lg ol>li{padding-left:1.6666667em}.prose-lg ol>li:before{left:0}.prose-lg ul>li{padding-left:1.6666667em}.prose-lg ul>li:before{width:.3333333em;height:.3333333em;top:.72222em;left:.2222222em}.prose-lg>ul>li p{margin-top:.8888889em;margin-bottom:.8888889em}.prose-lg>ul>li>:first-child{margin-top:1.3333333em}.prose-lg>ul>li>:last-child{margin-bottom:1.3333333em}.prose-lg>ol>li>:first-child{margin-top:1.3333333em}.prose-lg>ol>li>:last-child{margin-bottom:1.3333333em}.prose-lg ol ol,.prose-lg ol ul,.prose-lg ul ol,.prose-lg ul ul{margin-top:.8888889em;margin-bottom:.8888889em}.prose-lg hr{margin-top:3.1111111em;margin-bottom:3.1111111em}.prose-lg h2+*,.prose-lg h3+*,.prose-lg h4+*,.prose-lg hr+*{margin-top:0}.prose-lg table{font-size:.8888889em;line-height:1.5}.prose-lg thead th{padding-right:.75em;padding-bottom:.75em;padding-left:.75em}.prose-lg thead th:first-child{padding-left:0}.prose-lg thead th:last-child{padding-right:0}.prose-lg tbody td{padding:.75em}.prose-lg tbody td:first-child{padding-left:0}.prose-lg tbody td:last-child{padding-right:0}.prose-lg>:first-child{margin-top:0}.prose-lg>:last-child{margin-bottom:0}.prose-xl{font-size:1.25rem;line-height:1.8}.prose-xl p{margin-top:1.2em;margin-bottom:1.2em}.prose-xl [class~=lead]{font-size:1.2em;line-height:1.5;margin-top:1em;margin-bottom:1em}.prose-xl blockquote{margin-top:1.6em;margin-bottom:1.6em;padding-left:1.0666667em}.prose-xl h1{font-size:2.8em;margin-top:0;margin-bottom:.8571429em;line-height:1}.prose-xl h2{font-size:1.8em;margin-top:1.5555556em;margin-bottom:.8888889em;line-height:1.1111111}.prose-xl h3{font-size:1.5em;margin-top:1.6em;margin-bottom:.6666667em;line-height:1.3333333}.prose-xl h4{margin-top:1.8em;margin-bottom:.6em;line-height:1.6}.prose-xl figure,.prose-xl img,.prose-xl video{margin-top:2em;margin-bottom:2em}.prose-xl figure>*{margin-top:0;margin-bottom:0}.prose-xl figure figcaption{font-size:.9em;line-height:1.5555556;margin-top:1em}.prose-xl code{font-size:.9em}.prose-xl h2 code{font-size:.8611111em}.prose-xl h3 code,.prose-xl pre{font-size:.9em}.prose-xl pre{line-height:1.7777778;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.1111111em 1.3333333em}.prose-xl ol,.prose-xl ul{margin-top:1.2em;margin-bottom:1.2em}.prose-xl li{margin-top:.6em;margin-bottom:.6em}.prose-xl ol>li{padding-left:1.8em}.prose-xl ol>li:before{left:0}.prose-xl ul>li{padding-left:1.8em}.prose-xl ul>li:before{width:.35em;height:.35em;top:.725em;left:.25em}.prose-xl>ul>li p{margin-top:.8em;margin-bottom:.8em}.prose-xl>ul>li>:first-child{margin-top:1.2em}.prose-xl>ul>li>:last-child{margin-bottom:1.2em}.prose-xl>ol>li>:first-child{margin-top:1.2em}.prose-xl>ol>li>:last-child{margin-bottom:1.2em}.prose-xl ol ol,.prose-xl ol ul,.prose-xl ul ol,.prose-xl ul ul{margin-top:.8em;margin-bottom:.8em}.prose-xl hr{margin-top:2.8em;margin-bottom:2.8em}.prose-xl h2+*,.prose-xl h3+*,.prose-xl h4+*,.prose-xl hr+*{margin-top:0}.prose-xl table{font-size:.9em;line-height:1.5555556}.prose-xl thead th{padding-right:.6666667em;padding-bottom:.8888889em;padding-left:.6666667em}.prose-xl thead th:first-child{padding-left:0}.prose-xl thead th:last-child{padding-right:0}.prose-xl tbody td{padding:.8888889em .6666667em}.prose-xl tbody td:first-child{padding-left:0}.prose-xl tbody td:last-child{padding-right:0}.prose-xl>:first-child{margin-top:0}.prose-xl>:last-child{margin-bottom:0}.prose-2xl{font-size:1.5rem;line-height:1.6666667}.prose-2xl p{margin-top:1.3333333em;margin-bottom:1.3333333em}.prose-2xl [class~=lead]{font-size:1.25em;line-height:1.4666667;margin-top:1.0666667em;margin-bottom:1.0666667em}.prose-2xl blockquote{margin-top:1.7777778em;margin-bottom:1.7777778em;padding-left:1.1111111em}.prose-2xl h1{font-size:2.6666667em;margin-top:0;margin-bottom:.875em;line-height:1}.prose-2xl h2{font-size:2em;margin-top:1.5em;margin-bottom:.8333333em;line-height:1.0833333}.prose-2xl h3{font-size:1.5em;margin-top:1.5555556em;margin-bottom:.6666667em;line-height:1.2222222}.prose-2xl h4{margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.prose-2xl figure,.prose-2xl img,.prose-2xl video{margin-top:2em;margin-bottom:2em}.prose-2xl figure>*{margin-top:0;margin-bottom:0}.prose-2xl figure figcaption{font-size:.8333333em;line-height:1.6;margin-top:1em}.prose-2xl code{font-size:.8333333em}.prose-2xl h2 code{font-size:.875em}.prose-2xl h3 code{font-size:.8888889em}.prose-2xl pre{font-size:.8333333em;line-height:1.8;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.2em 1.6em}.prose-2xl ol,.prose-2xl ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.prose-2xl li{margin-top:.5em;margin-bottom:.5em}.prose-2xl ol>li{padding-left:1.6666667em}.prose-2xl ol>li:before{left:0}.prose-2xl ul>li{padding-left:1.6666667em}.prose-2xl ul>li:before{width:.3333333em;height:.3333333em;top:.66667em;left:.25em}.prose-2xl>ul>li p{margin-top:.8333333em;margin-bottom:.8333333em}.prose-2xl>ul>li>:first-child{margin-top:1.3333333em}.prose-2xl>ul>li>:last-child{margin-bottom:1.3333333em}.prose-2xl>ol>li>:first-child{margin-top:1.3333333em}.prose-2xl>ol>li>:last-child{margin-bottom:1.3333333em}.prose-2xl ol ol,.prose-2xl ol ul,.prose-2xl ul ol,.prose-2xl ul ul{margin-top:.6666667em;margin-bottom:.6666667em}.prose-2xl hr{margin-top:3em;margin-bottom:3em}.prose-2xl h2+*,.prose-2xl h3+*,.prose-2xl h4+*,.prose-2xl hr+*{margin-top:0}.prose-2xl table{font-size:.8333333em;line-height:1.4}.prose-2xl thead th{padding-right:.6em;padding-bottom:.8em;padding-left:.6em}.prose-2xl thead th:first-child{padding-left:0}.prose-2xl thead th:last-child{padding-right:0}.prose-2xl tbody td{padding:.8em .6em}.prose-2xl tbody td:first-child{padding-left:0}.prose-2xl tbody td:last-child{padding-right:0}.prose-2xl>:first-child{margin-top:0}.prose-2xl>:last-child{margin-bottom:0}.space-y-1>:not(template)~:not(template){--space-y-reverse:0;margin-top:calc(0.25rem*(1 - var(--space-y-reverse)));margin-bottom:calc(0.25rem*var(--space-y-reverse))}.space-y-6>:not(template)~:not(template){--space-y-reverse:0;margin-top:calc(1.5rem*(1 - var(--space-y-reverse)));margin-bottom:calc(1.5rem*var(--space-y-reverse))}.space-x-8>:not(template)~:not(template){--space-x-reverse:0;margin-right:calc(2rem*var(--space-x-reverse));margin-left:calc(2rem*(1 - var(--space-x-reverse)))}.bg-white{--bg-opacity:1;background-color:#fff;background-color:rgba(255,255,255,var(--bg-opacity))}.bg-gray-50{--bg-opacity:1;background-color:#f9fafb;background-color:rgba(249,250,251,var(--bg-opacity))}.bg-gray-100{--bg-opacity:1;background-color:#f4f5f7;background-color:rgba(244,245,247,var(--bg-opacity))}.bg-gray-200{--bg-opacity:1;background-color:#e5e7eb;background-color:rgba(229,231,235,var(--bg-opacity))}.bg-gray-500{--bg-opacity:1;background-color:#6b7280;background-color:rgba(107,114,128,var(--bg-opacity))}.bg-gray-800{--bg-opacity:1;background-color:#252f3f;background-color:rgba(37,47,63,var(--bg-opacity))}.bg-red-100{--bg-opacity:1;background-color:#fde8e8;background-color:rgba(253,232,232,var(--bg-opacity))}.bg-red-600{--bg-opacity:1;background-color:#e02424;background-color:rgba(224,36,36,var(--bg-opacity))}.bg-indigo-50{--bg-opacity:1;background-color:#f0f5ff;background-color:rgba(240,245,255,var(--bg-opacity))}.hover\:bg-gray-50:hover{--bg-opacity:1;background-color:#f9fafb;background-color:rgba(249,250,251,var(--bg-opacity))}.hover\:bg-gray-100:hover{--bg-opacity:1;background-color:#f4f5f7;background-color:rgba(244,245,247,var(--bg-opacity))}.hover\:bg-gray-700:hover{--bg-opacity:1;background-color:#374151;background-color:rgba(55,65,81,var(--bg-opacity))}.hover\:bg-red-500:hover{--bg-opacity:1;background-color:#f05252;background-color:rgba(240,82,82,var(--bg-opacity))}.focus\:bg-gray-50:focus{--bg-opacity:1;background-color:#f9fafb;background-color:rgba(249,250,251,var(--bg-opacity))}.focus\:bg-gray-100:focus{--bg-opacity:1;background-color:#f4f5f7;background-color:rgba(244,245,247,var(--bg-opacity))}.focus\:bg-indigo-100:focus{--bg-opacity:1;background-color:#e5edff;background-color:rgba(229,237,255,var(--bg-opacity))}.active\:bg-gray-50:active{--bg-opacity:1;background-color:#f9fafb;background-color:rgba(249,250,251,var(--bg-opacity))}.active\:bg-gray-100:active{--bg-opacity:1;background-color:#f4f5f7;background-color:rgba(244,245,247,var(--bg-opacity))}.active\:bg-gray-900:active{--bg-opacity:1;background-color:#161e2e;background-color:rgba(22,30,46,var(--bg-opacity))}.active\:bg-red-600:active{--bg-opacity:1;background-color:#e02424;background-color:rgba(224,36,36,var(--bg-opacity))}.bg-opacity-25{--bg-opacity:0.25}.border-transparent{border-color:transparent}.border-gray-100{--border-opacity:1;border-color:#f4f5f7;border-color:rgba(244,245,247,var(--border-opacity))}.border-gray-200{--border-opacity:1;border-color:#e5e7eb;border-color:rgba(229,231,235,var(--border-opacity))}.border-gray-300{--border-opacity:1;border-color:#d2d6dc;border-color:rgba(210,214,220,var(--border-opacity))}.border-indigo-400{--border-opacity:1;border-color:#8da2fb;border-color:rgba(141,162,251,var(--border-opacity))}.focus\:border-gray-300:focus,.hover\:border-gray-300:hover{--border-opacity:1;border-color:#d2d6dc;border-color:rgba(210,214,220,var(--border-opacity))}.focus\:border-gray-900:focus{--border-opacity:1;border-color:#161e2e;border-color:rgba(22,30,46,var(--border-opacity))}.focus\:border-red-700:focus{--border-opacity:1;border-color:#c81e1e;border-color:rgba(200,30,30,var(--border-opacity))}.focus\:border-blue-300:focus{--border-opacity:1;border-color:#a4cafe;border-color:rgba(164,202,254,var(--border-opacity))}.focus\:border-indigo-700:focus{--border-opacity:1;border-color:#5145cd;border-color:rgba(81,69,205,var(--border-opacity))}.rounded{border-radius:.25rem}.rounded-md{border-radius:.375rem}.rounded-lg{border-radius:.5rem}.rounded-full{border-radius:9999px}.rounded-r-md{border-top-right-radius:.375rem;border-bottom-right-radius:.375rem}.rounded-l-md{border-top-left-radius:.375rem;border-bottom-left-radius:.375rem}.border-2{border-width:2px}.border{border-width:1px}.border-b-2{border-bottom-width:2px}.border-l-4{border-left-width:4px}.border-t{border-top-width:1px}.border-b{border-bottom-width:1px}.cursor-default{cursor:default}.cursor-pointer{cursor:pointer}.block{display:block}.flex{display:flex}.inline-flex{display:inline-flex}.grid{display:grid}.hidden{display:none}.flex-col{flex-direction:column}.items-center{align-items:center}.justify-end{justify-content:flex-end}.justify-center{justify-content:center}.justify-between{justify-content:space-between}.flex-1{flex:1 1 0%}.flex-shrink-0{flex-shrink:0}.font-sans{font-family:Nunito,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,Noto Sans,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol,Noto Color Emoji}.font-mono{font-family:Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace}.font-medium{font-weight:500}.font-semibold{font-weight:600}.h-4{height:1rem}.h-5{height:1.25rem}.h-6{height:1.5rem}.h-8{height:2rem}.h-9{height:2.25rem}.h-10{height:2.5rem}.h-12{height:3rem}.h-16{height:4rem}.h-20{height:5rem}.text-xs{font-size:.75rem}.text-sm{font-size:.875rem}.text-base{font-size:1rem}.text-lg{font-size:1.125rem}.text-xl{font-size:1.25rem}.text-2xl{font-size:1.5rem}.leading-5{line-height:1.25rem}.leading-7{line-height:1.75rem}.leading-tight{line-height:1.25}.list-inside{list-style-position:inside}.list-disc{list-style-type:disc}.mx-auto{margin-left:auto;margin-right:auto}.mt-1{margin-top:.25rem}.ml-1{margin-left:.25rem}.mt-2{margin-top:.5rem}.mr-2{margin-right:.5rem}.ml-2{margin-left:.5rem}.mt-3{margin-top:.75rem}.mr-3{margin-right:.75rem}.ml-3{margin-left:.75rem}.mt-4{margin-top:1rem}.mb-4{margin-bottom:1rem}.ml-4{margin-left:1rem}.mt-5{margin-top:1.25rem}.mt-6{margin-top:1.5rem}.ml-6{margin-left:1.5rem}.mt-8{margin-top:2rem}.mt-10{margin-top:2.5rem}.ml-12{margin-left:3rem}.-mr-2{margin-right:-.5rem}.-mt-px{margin-top:-1px}.-ml-px{margin-left:-1px}.max-w-xl{max-width:36rem}.max-w-6xl{max-width:72rem}.max-w-7xl{max-width:80rem}.min-h-screen{min-height:100vh}.opacity-0{opacity:0}.opacity-50{opacity:.5}.opacity-75{opacity:.75}.opacity-100{opacity:1}.disabled\:opacity-25:disabled{opacity:.25}.focus\:outline-none:focus{outline:0}.overflow-hidden{overflow:hidden}.p-2{padding:.5rem}.p-6{padding:1.5rem}.py-1{padding-top:.25rem;padding-bottom:.25rem}.px-1{padding-left:.25rem;padding-right:.25rem}.py-2{padding-top:.5rem;padding-bottom:.5rem}.px-2{padding-left:.5rem;padding-right:.5rem}.py-3{padding-top:.75rem;padding-bottom:.75rem}.py-4{padding-top:1rem;padding-bottom:1rem}.px-4{padding-left:1rem;padding-right:1rem}.py-5{padding-top:1.25rem;padding-bottom:1.25rem}.py-6{padding-top:1.5rem;padding-bottom:1.5rem}.px-6{padding-left:1.5rem;padding-right:1.5rem}.py-8{padding-top:2rem;padding-bottom:2rem}.py-10{padding-top:2.5rem;padding-bottom:2.5rem}.py-12{padding-top:3rem;padding-bottom:3rem}.pt-1{padding-top:.25rem}.pb-1{padding-bottom:.25rem}.pt-2{padding-top:.5rem}.pb-3{padding-bottom:.75rem}.pl-3{padding-left:.75rem}.pt-4{padding-top:1rem}.pr-4{padding-right:1rem}.pb-4{padding-bottom:1rem}.pt-5{padding-top:1.25rem}.pt-6{padding-top:1.5rem}.pt-8{padding-top:2rem}.fixed{position:fixed}.absolute{position:absolute}.relative{position:relative}.inset-0{top:0;bottom:0}.inset-0,.inset-x-0{right:0;left:0}.top-0{top:0}.right-0{right:0}.left-0{left:0}.shadow-xs{box-shadow:0 0 0 1px rgba(0,0,0,.05)}.shadow-sm{box-shadow:0 1px 2px 0 rgba(0,0,0,.05)}.shadow{box-shadow:0 1px 3px 0 rgba(0,0,0,.1),0 1px 2px 0 rgba(0,0,0,.06)}.shadow-md{box-shadow:0 4px 6px -1px rgba(0,0,0,.1),0 2px 4px -1px rgba(0,0,0,.06)}.shadow-lg{box-shadow:0 10px 15px -3px rgba(0,0,0,.1),0 4px 6px -2px rgba(0,0,0,.05)}.shadow-xl{box-shadow:0 20px 25px -5px rgba(0,0,0,.1),0 10px 10px -5px rgba(0,0,0,.04)}.focus\:shadow-outline-gray:focus{box-shadow:0 0 0 3px rgba(159,166,178,.45)}.focus\:shadow-outline-blue:focus{box-shadow:0 0 0 3px rgba(164,202,254,.45)}.focus\:shadow-outline-red:focus{box-shadow:0 0 0 3px rgba(248,180,180,.45)}.text-center{text-align:center}.text-right{text-align:right}.text-white{--text-opacity:1;color:#fff;color:rgba(255,255,255,var(--text-opacity))}.text-gray-200{--text-opacity:1;color:#e5e7eb;color:rgba(229,231,235,var(--text-opacity))}.text-gray-300{--text-opacity:1;color:#d2d6dc;color:rgba(210,214,220,var(--text-opacity))}.text-gray-400{--text-opacity:1;color:#9fa6b2;color:rgba(159,166,178,var(--text-opacity))}.text-gray-500{--text-opacity:1;color:#6b7280;color:rgba(107,114,128,var(--text-opacity))}.text-gray-600{--text-opacity:1;color:#4b5563;color:rgba(75,85,99,var(--text-opacity))}.text-gray-700{--text-opacity:1;color:#374151;color:rgba(55,65,81,var(--text-opacity))}.text-gray-800{--text-opacity:1;color:#252f3f;color:rgba(37,47,63,var(--text-opacity))}.text-gray-900{--text-opacity:1;color:#161e2e;color:rgba(22,30,46,var(--text-opacity))}.text-red-500{--text-opacity:1;color:#f05252;color:rgba(240,82,82,var(--text-opacity))}.text-red-600{--text-opacity:1;color:#e02424;color:rgba(224,36,36,var(--text-opacity))}.text-green-400{--text-opacity:1;color:#31c48d;color:rgba(49,196,141,var(--text-opacity))}.text-green-500{--text-opacity:1;color:#0e9f6e;color:rgba(14,159,110,var(--text-opacity))}.text-green-600{--text-opacity:1;color:#057a55;color:rgba(5,122,85,var(--text-opacity))}.text-indigo-500{--text-opacity:1;color:#6875f5;color:rgba(104,117,245,var(--text-opacity))}.text-indigo-700{--text-opacity:1;color:#5145cd;color:rgba(81,69,205,var(--text-opacity))}.hover\:text-gray-400:hover{--text-opacity:1;color:#9fa6b2;color:rgba(159,166,178,var(--text-opacity))}.hover\:text-gray-500:hover{--text-opacity:1;color:#6b7280;color:rgba(107,114,128,var(--text-opacity))}.hover\:text-gray-700:hover{--text-opacity:1;color:#374151;color:rgba(55,65,81,var(--text-opacity))}.hover\:text-gray-800:hover{--text-opacity:1;color:#252f3f;color:rgba(37,47,63,var(--text-opacity))}.hover\:text-gray-900:hover{--text-opacity:1;color:#161e2e;color:rgba(22,30,46,var(--text-opacity))}.focus\:text-gray-500:focus{--text-opacity:1;color:#6b7280;color:rgba(107,114,128,var(--text-opacity))}.focus\:text-gray-700:focus{--text-opacity:1;color:#374151;color:rgba(55,65,81,var(--text-opacity))}.focus\:text-gray-800:focus{--text-opacity:1;color:#252f3f;color:rgba(37,47,63,var(--text-opacity))}.focus\:text-indigo-800:focus{--text-opacity:1;color:#42389d;color:rgba(66,56,157,var(--text-opacity))}.active\:text-gray-500:active{--text-opacity:1;color:#6b7280;color:rgba(107,114,128,var(--text-opacity))}.active\:text-gray-700:active{--text-opacity:1;color:#374151;color:rgba(55,65,81,var(--text-opacity))}.active\:text-gray-800:active{--text-opacity:1;color:#252f3f;color:rgba(37,47,63,var(--text-opacity))}.uppercase{text-transform:uppercase}.underline{text-decoration:underline}.antialiased{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.tracking-widest{letter-spacing:.1em}.break-all{word-break:break-all}.w-4{width:1rem}.w-5{width:1.25rem}.w-6{width:1.5rem}.w-8{width:2rem}.w-10{width:2.5rem}.w-12{width:3rem}.w-16{width:4rem}.w-20{width:5rem}.w-48{width:12rem}.w-auto{width:auto}.w-3\/4{width:75%}.w-full{width:100%}.z-0{z-index:0}.z-50{z-index:50}.focus\:z-10:focus{z-index:10}.gap-1{grid-gap:.25rem;gap:.25rem}.gap-4{grid-gap:1rem;gap:1rem}.gap-6{grid-gap:1.5rem;gap:1.5rem}.grid-cols-1{grid-template-columns:repeat(1,minmax(0,1fr))}.grid-cols-6{grid-template-columns:repeat(6,minmax(0,1fr))}.col-span-6{grid-column:span 6/span 6}.transform{--transform-translate-x:0;--transform-translate-y:0;--transform-rotate:0;--transform-skew-x:0;--transform-skew-y:0;--transform-scale-x:1;--transform-scale-y:1;transform:translateX(var(--transform-translate-x)) translateY(var(--transform-translate-y)) rotate(var(--transform-rotate)) skewX(var(--transform-skew-x)) skewY(var(--transform-skew-y)) scaleX(var(--transform-scale-x)) scaleY(var(--transform-scale-y))}.origin-top{transform-origin:top}.origin-top-right{transform-origin:top right}.origin-top-left{transform-origin:top left}.scale-95{--transform-scale-x:.95;--transform-scale-y:.95}.scale-100{--transform-scale-x:1;--transform-scale-y:1}.translate-y-0{--transform-translate-y:0}.translate-y-4{--transform-translate-y:1rem}.transition-all{transition-property:all}.transition{transition-property:background-color,border-color,color,fill,stroke,opacity,box-shadow,transform}.ease-in{transition-timing-function:cubic-bezier(.4,0,1,1)}.ease-out{transition-timing-function:cubic-bezier(0,0,.2,1)}.ease-in-out{transition-timing-function:cubic-bezier(.4,0,.2,1)}.duration-75{transition-duration:75ms}.duration-150{transition-duration:.15s}.duration-200{transition-duration:.2s}.duration-300{transition-duration:.3s}@-webkit-keyframes spin{to{transform:rotate(1turn)}}@keyframes spin{to{transform:rotate(1turn)}}@-webkit-keyframes ping{75%,to{transform:scale(2);opacity:0}}@keyframes ping{75%,to{transform:scale(2);opacity:0}}@-webkit-keyframes pulse{50%{opacity:.5}}@keyframes pulse{50%{opacity:.5}}@-webkit-keyframes bounce{0%,to{transform:translateY(-25%);-webkit-animation-timing-function:cubic-bezier(.8,0,1,1);animation-timing-function:cubic-bezier(.8,0,1,1)}50%{transform:none;-webkit-animation-timing-function:cubic-bezier(0,0,.2,1);animation-timing-function:cubic-bezier(0,0,.2,1)}}@keyframes bounce{0%,to{transform:translateY(-25%);-webkit-animation-timing-function:cubic-bezier(.8,0,1,1);animation-timing-function:cubic-bezier(.8,0,1,1)}50%{transform:none;-webkit-animation-timing-function:cubic-bezier(0,0,.2,1);animation-timing-function:cubic-bezier(0,0,.2,1)}}@media (min-width:640px){.sm\:container{width:100%;max-width:640px}@media (min-width:768px){.sm\:container{max-width:768px}}@media (min-width:1024px){.sm\:container{max-width:1024px}}@media (min-width:1280px){.sm\:container{max-width:1280px}}.sm\:prose{color:#374151;max-width:65ch}.sm\:prose [class~=lead]{color:#4b5563;font-size:1.25em;line-height:1.6;margin-top:1.2em;margin-bottom:1.2em}.sm\:prose a{color:#5850ec;text-decoration:none;font-weight:600}.sm\:prose strong{color:#161e2e;font-weight:600}.sm\:prose ol{counter-reset:list-counter;margin-top:1.25em;margin-bottom:1.25em}.sm\:prose ol>li{position:relative;counter-increment:list-counter;padding-left:1.75em}.sm\:prose ol>li:before{content:counter(list-counter) ".";position:absolute;font-weight:400;color:#6b7280}.sm\:prose ul>li{position:relative;padding-left:1.75em}.sm\:prose ul>li:before{content:"";position:absolute;background-color:#d2d6dc;border-radius:50%;width:.375em;height:.375em;top:.6875em;left:.25em}.sm\:prose hr{border-color:#e5e7eb;border-top-width:1px;margin-top:3em;margin-bottom:3em}.sm\:prose blockquote{font-weight:500;font-style:italic;color:#161e2e;border-left-width:.25rem;border-left-color:#e5e7eb;quotes:"\201C""\201D""\2018""\2019";margin-top:1.6em;margin-bottom:1.6em;padding-left:1em}.sm\:prose blockquote p:first-of-type:before{content:open-quote}.sm\:prose blockquote p:last-of-type:after{content:close-quote}.sm\:prose h1{color:#1a202c;font-weight:800;font-size:2.25em;margin-top:0;margin-bottom:.8888889em;line-height:1.1111111}.sm\:prose h2{color:#1a202c;font-weight:700;font-size:1.5em;margin-top:2em;margin-bottom:1em;line-height:1.3333333}.sm\:prose h3{font-size:1.25em;margin-top:1.6em;margin-bottom:.6em;line-height:1.6}.sm\:prose h3,.sm\:prose h4{color:#1a202c;font-weight:600}.sm\:prose h4{margin-top:1.5em;margin-bottom:.5em;line-height:1.5}.sm\:prose figure figcaption{color:#6b7280;font-size:.875em;line-height:1.4285714;margin-top:.8571429em}.sm\:prose code{color:#161e2e;font-weight:600;font-size:.875em}.sm\:prose code:after,.sm\:prose code:before{content:"`"}.sm\:prose pre{color:#e5e7eb;background-color:#252f3f;overflow-x:auto;font-size:.875em;line-height:1.7142857;margin-top:1.7142857em;margin-bottom:1.7142857em;border-radius:.375rem;padding:.8571429em 1.1428571em}.sm\:prose pre code{background-color:transparent;border-width:0;border-radius:0;padding:0;font-weight:400;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}.sm\:prose pre code:after,.sm\:prose pre code:before{content:""}.sm\:prose table{width:100%;table-layout:auto;text-align:left;margin-top:2em;margin-bottom:2em;font-size:.875em;line-height:1.7142857}.sm\:prose thead{color:#161e2e;font-weight:600;border-bottom-width:1px;border-bottom-color:#d2d6dc}.sm\:prose thead th{vertical-align:bottom;padding-right:.5714286em;padding-bottom:.5714286em;padding-left:.5714286em}.sm\:prose tbody tr{border-bottom-width:1px;border-bottom-color:#e5e7eb}.sm\:prose tbody tr:last-child{border-bottom-width:0}.sm\:prose tbody td{vertical-align:top;padding:.5714286em}.sm\:prose{font-size:1rem;line-height:1.75}.sm\:prose p{margin-top:1.25em;margin-bottom:1.25em}.sm\:prose figure,.sm\:prose img,.sm\:prose video{margin-top:2em;margin-bottom:2em}.sm\:prose figure>*{margin-top:0;margin-bottom:0}.sm\:prose h2 code{font-size:.875em}.sm\:prose h3 code{font-size:.9em}.sm\:prose ul{margin-top:1.25em;margin-bottom:1.25em}.sm\:prose li{margin-top:.5em;margin-bottom:.5em}.sm\:prose ol>li:before{left:0}.sm\:prose>ul>li p{margin-top:.75em;margin-bottom:.75em}.sm\:prose>ul>li>:first-child{margin-top:1.25em}.sm\:prose>ul>li>:last-child{margin-bottom:1.25em}.sm\:prose>ol>li>:first-child{margin-top:1.25em}.sm\:prose>ol>li>:last-child{margin-bottom:1.25em}.sm\:prose ol ol,.sm\:prose ol ul,.sm\:prose ul ol,.sm\:prose ul ul{margin-top:.75em;margin-bottom:.75em}.sm\:prose h2+*,.sm\:prose h3+*,.sm\:prose h4+*,.sm\:prose hr+*{margin-top:0}.sm\:prose thead th:first-child{padding-left:0}.sm\:prose thead th:last-child{padding-right:0}.sm\:prose tbody td:first-child{padding-left:0}.sm\:prose tbody td:last-child{padding-right:0}.sm\:prose>:first-child{margin-top:0}.sm\:prose>:last-child{margin-bottom:0}.sm\:prose h1,.sm\:prose h2,.sm\:prose h3,.sm\:prose h4{color:#161e2e}.sm\:prose-sm{font-size:.875rem;line-height:1.7142857}.sm\:prose-sm p{margin-top:1.1428571em;margin-bottom:1.1428571em}.sm\:prose-sm [class~=lead]{font-size:1.2857143em;line-height:1.5555556;margin-top:.8888889em;margin-bottom:.8888889em}.sm\:prose-sm blockquote{margin-top:1.3333333em;margin-bottom:1.3333333em;padding-left:1.1111111em}.sm\:prose-sm h1{font-size:2.1428571em;margin-top:0;margin-bottom:.8em;line-height:1.2}.sm\:prose-sm h2{font-size:1.4285714em;margin-top:1.6em;margin-bottom:.8em;line-height:1.4}.sm\:prose-sm h3{font-size:1.2857143em;margin-top:1.5555556em;margin-bottom:.4444444em;line-height:1.5555556}.sm\:prose-sm h4{margin-top:1.4285714em;margin-bottom:.5714286em;line-height:1.4285714}.sm\:prose-sm figure,.sm\:prose-sm img,.sm\:prose-sm video{margin-top:1.7142857em;margin-bottom:1.7142857em}.sm\:prose-sm figure>*{margin-top:0;margin-bottom:0}.sm\:prose-sm figure figcaption{font-size:.8571429em;line-height:1.3333333;margin-top:.6666667em}.sm\:prose-sm code{font-size:.8571429em}.sm\:prose-sm h2 code{font-size:.9em}.sm\:prose-sm h3 code{font-size:.8888889em}.sm\:prose-sm pre{font-size:.8571429em;line-height:1.6666667;margin-top:1.6666667em;margin-bottom:1.6666667em;border-radius:.25rem;padding:.6666667em 1em}.sm\:prose-sm ol,.sm\:prose-sm ul{margin-top:1.1428571em;margin-bottom:1.1428571em}.sm\:prose-sm li{margin-top:.2857143em;margin-bottom:.2857143em}.sm\:prose-sm ol>li{padding-left:1.5714286em}.sm\:prose-sm ol>li:before{left:0}.sm\:prose-sm ul>li{padding-left:1.5714286em}.sm\:prose-sm ul>li:before{height:.3571429em;width:.3571429em;top:.67857em;left:.2142857em}.sm\:prose-sm>ul>li p{margin-top:.5714286em;margin-bottom:.5714286em}.sm\:prose-sm>ul>li>:first-child{margin-top:1.1428571em}.sm\:prose-sm>ul>li>:last-child{margin-bottom:1.1428571em}.sm\:prose-sm>ol>li>:first-child{margin-top:1.1428571em}.sm\:prose-sm>ol>li>:last-child{margin-bottom:1.1428571em}.sm\:prose-sm ol ol,.sm\:prose-sm ol ul,.sm\:prose-sm ul ol,.sm\:prose-sm ul ul{margin-top:.5714286em;margin-bottom:.5714286em}.sm\:prose-sm hr{margin-top:2.8571429em;margin-bottom:2.8571429em}.sm\:prose-sm h2+*,.sm\:prose-sm h3+*,.sm\:prose-sm h4+*,.sm\:prose-sm hr+*{margin-top:0}.sm\:prose-sm table{font-size:.8571429em;line-height:1.5}.sm\:prose-sm thead th{padding-right:1em;padding-bottom:.6666667em;padding-left:1em}.sm\:prose-sm thead th:first-child{padding-left:0}.sm\:prose-sm thead th:last-child{padding-right:0}.sm\:prose-sm tbody td{padding:.6666667em 1em}.sm\:prose-sm tbody td:first-child{padding-left:0}.sm\:prose-sm tbody td:last-child{padding-right:0}.sm\:prose-sm>:first-child{margin-top:0}.sm\:prose-sm>:last-child{margin-bottom:0}.sm\:prose-lg{font-size:1.125rem;line-height:1.7777778}.sm\:prose-lg p{margin-top:1.3333333em;margin-bottom:1.3333333em}.sm\:prose-lg [class~=lead]{font-size:1.2222222em;line-height:1.4545455;margin-top:1.0909091em;margin-bottom:1.0909091em}.sm\:prose-lg blockquote{margin-top:1.6666667em;margin-bottom:1.6666667em;padding-left:1em}.sm\:prose-lg h1{font-size:2.6666667em;margin-top:0;margin-bottom:.8333333em;line-height:1}.sm\:prose-lg h2{font-size:1.6666667em;margin-top:1.8666667em;margin-bottom:1.0666667em;line-height:1.3333333}.sm\:prose-lg h3{font-size:1.3333333em;margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.sm\:prose-lg h4{margin-top:1.7777778em;margin-bottom:.4444444em;line-height:1.5555556}.sm\:prose-lg figure,.sm\:prose-lg img,.sm\:prose-lg video{margin-top:1.7777778em;margin-bottom:1.7777778em}.sm\:prose-lg figure>*{margin-top:0;margin-bottom:0}.sm\:prose-lg figure figcaption{font-size:.8888889em;line-height:1.5;margin-top:1em}.sm\:prose-lg code{font-size:.8888889em}.sm\:prose-lg h2 code{font-size:.8666667em}.sm\:prose-lg h3 code{font-size:.875em}.sm\:prose-lg pre{font-size:.8888889em;line-height:1.75;margin-top:2em;margin-bottom:2em;border-radius:.375rem;padding:1em 1.5em}.sm\:prose-lg ol,.sm\:prose-lg ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.sm\:prose-lg li{margin-top:.6666667em;margin-bottom:.6666667em}.sm\:prose-lg ol>li{padding-left:1.6666667em}.sm\:prose-lg ol>li:before{left:0}.sm\:prose-lg ul>li{padding-left:1.6666667em}.sm\:prose-lg ul>li:before{width:.3333333em;height:.3333333em;top:.72222em;left:.2222222em}.sm\:prose-lg>ul>li p{margin-top:.8888889em;margin-bottom:.8888889em}.sm\:prose-lg>ul>li>:first-child{margin-top:1.3333333em}.sm\:prose-lg>ul>li>:last-child{margin-bottom:1.3333333em}.sm\:prose-lg>ol>li>:first-child{margin-top:1.3333333em}.sm\:prose-lg>ol>li>:last-child{margin-bottom:1.3333333em}.sm\:prose-lg ol ol,.sm\:prose-lg ol ul,.sm\:prose-lg ul ol,.sm\:prose-lg ul ul{margin-top:.8888889em;margin-bottom:.8888889em}.sm\:prose-lg hr{margin-top:3.1111111em;margin-bottom:3.1111111em}.sm\:prose-lg h2+*,.sm\:prose-lg h3+*,.sm\:prose-lg h4+*,.sm\:prose-lg hr+*{margin-top:0}.sm\:prose-lg table{font-size:.8888889em;line-height:1.5}.sm\:prose-lg thead th{padding-right:.75em;padding-bottom:.75em;padding-left:.75em}.sm\:prose-lg thead th:first-child{padding-left:0}.sm\:prose-lg thead th:last-child{padding-right:0}.sm\:prose-lg tbody td{padding:.75em}.sm\:prose-lg tbody td:first-child{padding-left:0}.sm\:prose-lg tbody td:last-child{padding-right:0}.sm\:prose-lg>:first-child{margin-top:0}.sm\:prose-lg>:last-child{margin-bottom:0}.sm\:prose-xl{font-size:1.25rem;line-height:1.8}.sm\:prose-xl p{margin-top:1.2em;margin-bottom:1.2em}.sm\:prose-xl [class~=lead]{font-size:1.2em;line-height:1.5;margin-top:1em;margin-bottom:1em}.sm\:prose-xl blockquote{margin-top:1.6em;margin-bottom:1.6em;padding-left:1.0666667em}.sm\:prose-xl h1{font-size:2.8em;margin-top:0;margin-bottom:.8571429em;line-height:1}.sm\:prose-xl h2{font-size:1.8em;margin-top:1.5555556em;margin-bottom:.8888889em;line-height:1.1111111}.sm\:prose-xl h3{font-size:1.5em;margin-top:1.6em;margin-bottom:.6666667em;line-height:1.3333333}.sm\:prose-xl h4{margin-top:1.8em;margin-bottom:.6em;line-height:1.6}.sm\:prose-xl figure,.sm\:prose-xl img,.sm\:prose-xl video{margin-top:2em;margin-bottom:2em}.sm\:prose-xl figure>*{margin-top:0;margin-bottom:0}.sm\:prose-xl figure figcaption{font-size:.9em;line-height:1.5555556;margin-top:1em}.sm\:prose-xl code{font-size:.9em}.sm\:prose-xl h2 code{font-size:.8611111em}.sm\:prose-xl h3 code{font-size:.9em}.sm\:prose-xl pre{font-size:.9em;line-height:1.7777778;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.1111111em 1.3333333em}.sm\:prose-xl ol,.sm\:prose-xl ul{margin-top:1.2em;margin-bottom:1.2em}.sm\:prose-xl li{margin-top:.6em;margin-bottom:.6em}.sm\:prose-xl ol>li{padding-left:1.8em}.sm\:prose-xl ol>li:before{left:0}.sm\:prose-xl ul>li{padding-left:1.8em}.sm\:prose-xl ul>li:before{width:.35em;height:.35em;top:.725em;left:.25em}.sm\:prose-xl>ul>li p{margin-top:.8em;margin-bottom:.8em}.sm\:prose-xl>ul>li>:first-child{margin-top:1.2em}.sm\:prose-xl>ul>li>:last-child{margin-bottom:1.2em}.sm\:prose-xl>ol>li>:first-child{margin-top:1.2em}.sm\:prose-xl>ol>li>:last-child{margin-bottom:1.2em}.sm\:prose-xl ol ol,.sm\:prose-xl ol ul,.sm\:prose-xl ul ol,.sm\:prose-xl ul ul{margin-top:.8em;margin-bottom:.8em}.sm\:prose-xl hr{margin-top:2.8em;margin-bottom:2.8em}.sm\:prose-xl h2+*,.sm\:prose-xl h3+*,.sm\:prose-xl h4+*,.sm\:prose-xl hr+*{margin-top:0}.sm\:prose-xl table{font-size:.9em;line-height:1.5555556}.sm\:prose-xl thead th{padding-right:.6666667em;padding-bottom:.8888889em;padding-left:.6666667em}.sm\:prose-xl thead th:first-child{padding-left:0}.sm\:prose-xl thead th:last-child{padding-right:0}.sm\:prose-xl tbody td{padding:.8888889em .6666667em}.sm\:prose-xl tbody td:first-child{padding-left:0}.sm\:prose-xl tbody td:last-child{padding-right:0}.sm\:prose-xl>:first-child{margin-top:0}.sm\:prose-xl>:last-child{margin-bottom:0}.sm\:prose-2xl{font-size:1.5rem;line-height:1.6666667}.sm\:prose-2xl p{margin-top:1.3333333em;margin-bottom:1.3333333em}.sm\:prose-2xl [class~=lead]{font-size:1.25em;line-height:1.4666667;margin-top:1.0666667em;margin-bottom:1.0666667em}.sm\:prose-2xl blockquote{margin-top:1.7777778em;margin-bottom:1.7777778em;padding-left:1.1111111em}.sm\:prose-2xl h1{font-size:2.6666667em;margin-top:0;margin-bottom:.875em;line-height:1}.sm\:prose-2xl h2{font-size:2em;margin-top:1.5em;margin-bottom:.8333333em;line-height:1.0833333}.sm\:prose-2xl h3{font-size:1.5em;margin-top:1.5555556em;margin-bottom:.6666667em;line-height:1.2222222}.sm\:prose-2xl h4{margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.sm\:prose-2xl figure,.sm\:prose-2xl img,.sm\:prose-2xl video{margin-top:2em;margin-bottom:2em}.sm\:prose-2xl figure>*{margin-top:0;margin-bottom:0}.sm\:prose-2xl figure figcaption{font-size:.8333333em;line-height:1.6;margin-top:1em}.sm\:prose-2xl code{font-size:.8333333em}.sm\:prose-2xl h2 code{font-size:.875em}.sm\:prose-2xl h3 code{font-size:.8888889em}.sm\:prose-2xl pre{font-size:.8333333em;line-height:1.8;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.2em 1.6em}.sm\:prose-2xl ol,.sm\:prose-2xl ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.sm\:prose-2xl li{margin-top:.5em;margin-bottom:.5em}.sm\:prose-2xl ol>li{padding-left:1.6666667em}.sm\:prose-2xl ol>li:before{left:0}.sm\:prose-2xl ul>li{padding-left:1.6666667em}.sm\:prose-2xl ul>li:before{width:.3333333em;height:.3333333em;top:.66667em;left:.25em}.sm\:prose-2xl>ul>li p{margin-top:.8333333em;margin-bottom:.8333333em}.sm\:prose-2xl>ul>li>:first-child{margin-top:1.3333333em}.sm\:prose-2xl>ul>li>:last-child{margin-bottom:1.3333333em}.sm\:prose-2xl>ol>li>:first-child{margin-top:1.3333333em}.sm\:prose-2xl>ol>li>:last-child{margin-bottom:1.3333333em}.sm\:prose-2xl ol ol,.sm\:prose-2xl ol ul,.sm\:prose-2xl ul ol,.sm\:prose-2xl ul ul{margin-top:.6666667em;margin-bottom:.6666667em}.sm\:prose-2xl hr{margin-top:3em;margin-bottom:3em}.sm\:prose-2xl h2+*,.sm\:prose-2xl h3+*,.sm\:prose-2xl h4+*,.sm\:prose-2xl hr+*{margin-top:0}.sm\:prose-2xl table{font-size:.8333333em;line-height:1.4}.sm\:prose-2xl thead th{padding-right:.6em;padding-bottom:.8em;padding-left:.6em}.sm\:prose-2xl thead th:first-child{padding-left:0}.sm\:prose-2xl thead th:last-child{padding-right:0}.sm\:prose-2xl tbody td{padding:.8em .6em}.sm\:prose-2xl tbody td:first-child{padding-left:0}.sm\:prose-2xl tbody td:last-child{padding-right:0}.sm\:prose-2xl>:first-child{margin-top:0}.sm\:prose-2xl>:last-child{margin-bottom:0}.sm\:rounded-md{border-radius:.375rem}.sm\:rounded-lg{border-radius:.5rem}.sm\:block{display:block}.sm\:flex{display:flex}.sm\:hidden{display:none}.sm\:items-start{align-items:flex-start}.sm\:items-center{align-items:center}.sm\:justify-start{justify-content:flex-start}.sm\:justify-center{justify-content:center}.sm\:justify-between{justify-content:space-between}.sm\:flex-1{flex:1 1 0%}.sm\:h-10{height:2.5rem}.sm\:h-20{height:5rem}.sm\:mx-0{margin-left:0;margin-right:0}.sm\:-my-px{margin-top:-1px;margin-bottom:-1px}.sm\:mt-0{margin-top:0}.sm\:ml-0{margin-left:0}.sm\:ml-4{margin-left:1rem}.sm\:ml-6{margin-left:1.5rem}.sm\:ml-10{margin-left:2.5rem}.sm\:max-w-sm{max-width:24rem}.sm\:max-w-md{max-width:28rem}.sm\:max-w-lg{max-width:32rem}.sm\:max-w-xl{max-width:36rem}.sm\:max-w-2xl{max-width:42rem}.sm\:p-6{padding:1.5rem}.sm\:px-0{padding-left:0;padding-right:0}.sm\:px-6{padding-left:1.5rem;padding-right:1.5rem}.sm\:px-20{padding-left:5rem;padding-right:5rem}.sm\:pt-0{padding-top:0}.sm\:pb-4{padding-bottom:1rem}.sm\:text-left{text-align:left}.sm\:text-right{text-align:right}.sm\:w-10{width:2.5rem}.sm\:w-full{width:100%}.sm\:col-span-4{grid-column:span 4/span 4}.sm\:scale-95{--transform-scale-x:.95;--transform-scale-y:.95}.sm\:scale-100{--transform-scale-x:1;--transform-scale-y:1}.sm\:translate-y-0{--transform-translate-y:0}}@media (min-width:768px){.md\:container{width:100%}@media (min-width:640px){.md\:container{max-width:640px}}@media (min-width:768px){.md\:container{max-width:768px}}@media (min-width:1024px){.md\:container{max-width:1024px}}@media (min-width:1280px){.md\:container{max-width:1280px}}.md\:prose{color:#374151;max-width:65ch}.md\:prose [class~=lead]{color:#4b5563;font-size:1.25em;line-height:1.6;margin-top:1.2em;margin-bottom:1.2em}.md\:prose a{color:#5850ec;text-decoration:none;font-weight:600}.md\:prose strong{color:#161e2e;font-weight:600}.md\:prose ol{counter-reset:list-counter;margin-top:1.25em;margin-bottom:1.25em}.md\:prose ol>li{position:relative;counter-increment:list-counter;padding-left:1.75em}.md\:prose ol>li:before{content:counter(list-counter) ".";position:absolute;font-weight:400;color:#6b7280}.md\:prose ul>li{position:relative;padding-left:1.75em}.md\:prose ul>li:before{content:"";position:absolute;background-color:#d2d6dc;border-radius:50%;width:.375em;height:.375em;top:.6875em;left:.25em}.md\:prose hr{border-color:#e5e7eb;border-top-width:1px;margin-top:3em;margin-bottom:3em}.md\:prose blockquote{font-weight:500;font-style:italic;color:#161e2e;border-left-width:.25rem;border-left-color:#e5e7eb;quotes:"\201C""\201D""\2018""\2019";margin-top:1.6em;margin-bottom:1.6em;padding-left:1em}.md\:prose blockquote p:first-of-type:before{content:open-quote}.md\:prose blockquote p:last-of-type:after{content:close-quote}.md\:prose h1{color:#1a202c;font-weight:800;font-size:2.25em;margin-top:0;margin-bottom:.8888889em;line-height:1.1111111}.md\:prose h2{color:#1a202c;font-weight:700;font-size:1.5em;margin-top:2em;margin-bottom:1em;line-height:1.3333333}.md\:prose h3{font-size:1.25em;margin-top:1.6em;margin-bottom:.6em;line-height:1.6}.md\:prose h3,.md\:prose h4{color:#1a202c;font-weight:600}.md\:prose h4{margin-top:1.5em;margin-bottom:.5em;line-height:1.5}.md\:prose figure figcaption{color:#6b7280;font-size:.875em;line-height:1.4285714;margin-top:.8571429em}.md\:prose code{color:#161e2e;font-weight:600;font-size:.875em}.md\:prose code:after,.md\:prose code:before{content:"`"}.md\:prose pre{color:#e5e7eb;background-color:#252f3f;overflow-x:auto;font-size:.875em;line-height:1.7142857;margin-top:1.7142857em;margin-bottom:1.7142857em;border-radius:.375rem;padding:.8571429em 1.1428571em}.md\:prose pre code{background-color:transparent;border-width:0;border-radius:0;padding:0;font-weight:400;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}.md\:prose pre code:after,.md\:prose pre code:before{content:""}.md\:prose table{width:100%;table-layout:auto;text-align:left;margin-top:2em;margin-bottom:2em;font-size:.875em;line-height:1.7142857}.md\:prose thead{color:#161e2e;font-weight:600;border-bottom-width:1px;border-bottom-color:#d2d6dc}.md\:prose thead th{vertical-align:bottom;padding-right:.5714286em;padding-bottom:.5714286em;padding-left:.5714286em}.md\:prose tbody tr{border-bottom-width:1px;border-bottom-color:#e5e7eb}.md\:prose tbody tr:last-child{border-bottom-width:0}.md\:prose tbody td{vertical-align:top;padding:.5714286em}.md\:prose{font-size:1rem;line-height:1.75}.md\:prose p{margin-top:1.25em;margin-bottom:1.25em}.md\:prose figure,.md\:prose img,.md\:prose video{margin-top:2em;margin-bottom:2em}.md\:prose figure>*{margin-top:0;margin-bottom:0}.md\:prose h2 code{font-size:.875em}.md\:prose h3 code{font-size:.9em}.md\:prose ul{margin-top:1.25em;margin-bottom:1.25em}.md\:prose li{margin-top:.5em;margin-bottom:.5em}.md\:prose ol>li:before{left:0}.md\:prose>ul>li p{margin-top:.75em;margin-bottom:.75em}.md\:prose>ul>li>:first-child{margin-top:1.25em}.md\:prose>ul>li>:last-child{margin-bottom:1.25em}.md\:prose>ol>li>:first-child{margin-top:1.25em}.md\:prose>ol>li>:last-child{margin-bottom:1.25em}.md\:prose ol ol,.md\:prose ol ul,.md\:prose ul ol,.md\:prose ul ul{margin-top:.75em;margin-bottom:.75em}.md\:prose h2+*,.md\:prose h3+*,.md\:prose h4+*,.md\:prose hr+*{margin-top:0}.md\:prose thead th:first-child{padding-left:0}.md\:prose thead th:last-child{padding-right:0}.md\:prose tbody td:first-child{padding-left:0}.md\:prose tbody td:last-child{padding-right:0}.md\:prose>:first-child{margin-top:0}.md\:prose>:last-child{margin-bottom:0}.md\:prose h1,.md\:prose h2,.md\:prose h3,.md\:prose h4{color:#161e2e}.md\:prose-sm{font-size:.875rem;line-height:1.7142857}.md\:prose-sm p{margin-top:1.1428571em;margin-bottom:1.1428571em}.md\:prose-sm [class~=lead]{font-size:1.2857143em;line-height:1.5555556;margin-top:.8888889em;margin-bottom:.8888889em}.md\:prose-sm blockquote{margin-top:1.3333333em;margin-bottom:1.3333333em;padding-left:1.1111111em}.md\:prose-sm h1{font-size:2.1428571em;margin-top:0;margin-bottom:.8em;line-height:1.2}.md\:prose-sm h2{font-size:1.4285714em;margin-top:1.6em;margin-bottom:.8em;line-height:1.4}.md\:prose-sm h3{font-size:1.2857143em;margin-top:1.5555556em;margin-bottom:.4444444em;line-height:1.5555556}.md\:prose-sm h4{margin-top:1.4285714em;margin-bottom:.5714286em;line-height:1.4285714}.md\:prose-sm figure,.md\:prose-sm img,.md\:prose-sm video{margin-top:1.7142857em;margin-bottom:1.7142857em}.md\:prose-sm figure>*{margin-top:0;margin-bottom:0}.md\:prose-sm figure figcaption{font-size:.8571429em;line-height:1.3333333;margin-top:.6666667em}.md\:prose-sm code{font-size:.8571429em}.md\:prose-sm h2 code{font-size:.9em}.md\:prose-sm h3 code{font-size:.8888889em}.md\:prose-sm pre{font-size:.8571429em;line-height:1.6666667;margin-top:1.6666667em;margin-bottom:1.6666667em;border-radius:.25rem;padding:.6666667em 1em}.md\:prose-sm ol,.md\:prose-sm ul{margin-top:1.1428571em;margin-bottom:1.1428571em}.md\:prose-sm li{margin-top:.2857143em;margin-bottom:.2857143em}.md\:prose-sm ol>li{padding-left:1.5714286em}.md\:prose-sm ol>li:before{left:0}.md\:prose-sm ul>li{padding-left:1.5714286em}.md\:prose-sm ul>li:before{height:.3571429em;width:.3571429em;top:.67857em;left:.2142857em}.md\:prose-sm>ul>li p{margin-top:.5714286em;margin-bottom:.5714286em}.md\:prose-sm>ul>li>:first-child{margin-top:1.1428571em}.md\:prose-sm>ul>li>:last-child{margin-bottom:1.1428571em}.md\:prose-sm>ol>li>:first-child{margin-top:1.1428571em}.md\:prose-sm>ol>li>:last-child{margin-bottom:1.1428571em}.md\:prose-sm ol ol,.md\:prose-sm ol ul,.md\:prose-sm ul ol,.md\:prose-sm ul ul{margin-top:.5714286em;margin-bottom:.5714286em}.md\:prose-sm hr{margin-top:2.8571429em;margin-bottom:2.8571429em}.md\:prose-sm h2+*,.md\:prose-sm h3+*,.md\:prose-sm h4+*,.md\:prose-sm hr+*{margin-top:0}.md\:prose-sm table{font-size:.8571429em;line-height:1.5}.md\:prose-sm thead th{padding-right:1em;padding-bottom:.6666667em;padding-left:1em}.md\:prose-sm thead th:first-child{padding-left:0}.md\:prose-sm thead th:last-child{padding-right:0}.md\:prose-sm tbody td{padding:.6666667em 1em}.md\:prose-sm tbody td:first-child{padding-left:0}.md\:prose-sm tbody td:last-child{padding-right:0}.md\:prose-sm>:first-child{margin-top:0}.md\:prose-sm>:last-child{margin-bottom:0}.md\:prose-lg{font-size:1.125rem;line-height:1.7777778}.md\:prose-lg p{margin-top:1.3333333em;margin-bottom:1.3333333em}.md\:prose-lg [class~=lead]{font-size:1.2222222em;line-height:1.4545455;margin-top:1.0909091em;margin-bottom:1.0909091em}.md\:prose-lg blockquote{margin-top:1.6666667em;margin-bottom:1.6666667em;padding-left:1em}.md\:prose-lg h1{font-size:2.6666667em;margin-top:0;margin-bottom:.8333333em;line-height:1}.md\:prose-lg h2{font-size:1.6666667em;margin-top:1.8666667em;margin-bottom:1.0666667em;line-height:1.3333333}.md\:prose-lg h3{font-size:1.3333333em;margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.md\:prose-lg h4{margin-top:1.7777778em;margin-bottom:.4444444em;line-height:1.5555556}.md\:prose-lg figure,.md\:prose-lg img,.md\:prose-lg video{margin-top:1.7777778em;margin-bottom:1.7777778em}.md\:prose-lg figure>*{margin-top:0;margin-bottom:0}.md\:prose-lg figure figcaption{font-size:.8888889em;line-height:1.5;margin-top:1em}.md\:prose-lg code{font-size:.8888889em}.md\:prose-lg h2 code{font-size:.8666667em}.md\:prose-lg h3 code{font-size:.875em}.md\:prose-lg pre{font-size:.8888889em;line-height:1.75;margin-top:2em;margin-bottom:2em;border-radius:.375rem;padding:1em 1.5em}.md\:prose-lg ol,.md\:prose-lg ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.md\:prose-lg li{margin-top:.6666667em;margin-bottom:.6666667em}.md\:prose-lg ol>li{padding-left:1.6666667em}.md\:prose-lg ol>li:before{left:0}.md\:prose-lg ul>li{padding-left:1.6666667em}.md\:prose-lg ul>li:before{width:.3333333em;height:.3333333em;top:.72222em;left:.2222222em}.md\:prose-lg>ul>li p{margin-top:.8888889em;margin-bottom:.8888889em}.md\:prose-lg>ul>li>:first-child{margin-top:1.3333333em}.md\:prose-lg>ul>li>:last-child{margin-bottom:1.3333333em}.md\:prose-lg>ol>li>:first-child{margin-top:1.3333333em}.md\:prose-lg>ol>li>:last-child{margin-bottom:1.3333333em}.md\:prose-lg ol ol,.md\:prose-lg ol ul,.md\:prose-lg ul ol,.md\:prose-lg ul ul{margin-top:.8888889em;margin-bottom:.8888889em}.md\:prose-lg hr{margin-top:3.1111111em;margin-bottom:3.1111111em}.md\:prose-lg h2+*,.md\:prose-lg h3+*,.md\:prose-lg h4+*,.md\:prose-lg hr+*{margin-top:0}.md\:prose-lg table{font-size:.8888889em;line-height:1.5}.md\:prose-lg thead th{padding-right:.75em;padding-bottom:.75em;padding-left:.75em}.md\:prose-lg thead th:first-child{padding-left:0}.md\:prose-lg thead th:last-child{padding-right:0}.md\:prose-lg tbody td{padding:.75em}.md\:prose-lg tbody td:first-child{padding-left:0}.md\:prose-lg tbody td:last-child{padding-right:0}.md\:prose-lg>:first-child{margin-top:0}.md\:prose-lg>:last-child{margin-bottom:0}.md\:prose-xl{font-size:1.25rem;line-height:1.8}.md\:prose-xl p{margin-top:1.2em;margin-bottom:1.2em}.md\:prose-xl [class~=lead]{font-size:1.2em;line-height:1.5;margin-top:1em;margin-bottom:1em}.md\:prose-xl blockquote{margin-top:1.6em;margin-bottom:1.6em;padding-left:1.0666667em}.md\:prose-xl h1{font-size:2.8em;margin-top:0;margin-bottom:.8571429em;line-height:1}.md\:prose-xl h2{font-size:1.8em;margin-top:1.5555556em;margin-bottom:.8888889em;line-height:1.1111111}.md\:prose-xl h3{font-size:1.5em;margin-top:1.6em;margin-bottom:.6666667em;line-height:1.3333333}.md\:prose-xl h4{margin-top:1.8em;margin-bottom:.6em;line-height:1.6}.md\:prose-xl figure,.md\:prose-xl img,.md\:prose-xl video{margin-top:2em;margin-bottom:2em}.md\:prose-xl figure>*{margin-top:0;margin-bottom:0}.md\:prose-xl figure figcaption{font-size:.9em;line-height:1.5555556;margin-top:1em}.md\:prose-xl code{font-size:.9em}.md\:prose-xl h2 code{font-size:.8611111em}.md\:prose-xl h3 code{font-size:.9em}.md\:prose-xl pre{font-size:.9em;line-height:1.7777778;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.1111111em 1.3333333em}.md\:prose-xl ol,.md\:prose-xl ul{margin-top:1.2em;margin-bottom:1.2em}.md\:prose-xl li{margin-top:.6em;margin-bottom:.6em}.md\:prose-xl ol>li{padding-left:1.8em}.md\:prose-xl ol>li:before{left:0}.md\:prose-xl ul>li{padding-left:1.8em}.md\:prose-xl ul>li:before{width:.35em;height:.35em;top:.725em;left:.25em}.md\:prose-xl>ul>li p{margin-top:.8em;margin-bottom:.8em}.md\:prose-xl>ul>li>:first-child{margin-top:1.2em}.md\:prose-xl>ul>li>:last-child{margin-bottom:1.2em}.md\:prose-xl>ol>li>:first-child{margin-top:1.2em}.md\:prose-xl>ol>li>:last-child{margin-bottom:1.2em}.md\:prose-xl ol ol,.md\:prose-xl ol ul,.md\:prose-xl ul ol,.md\:prose-xl ul ul{margin-top:.8em;margin-bottom:.8em}.md\:prose-xl hr{margin-top:2.8em;margin-bottom:2.8em}.md\:prose-xl h2+*,.md\:prose-xl h3+*,.md\:prose-xl h4+*,.md\:prose-xl hr+*{margin-top:0}.md\:prose-xl table{font-size:.9em;line-height:1.5555556}.md\:prose-xl thead th{padding-right:.6666667em;padding-bottom:.8888889em;padding-left:.6666667em}.md\:prose-xl thead th:first-child{padding-left:0}.md\:prose-xl thead th:last-child{padding-right:0}.md\:prose-xl tbody td{padding:.8888889em .6666667em}.md\:prose-xl tbody td:first-child{padding-left:0}.md\:prose-xl tbody td:last-child{padding-right:0}.md\:prose-xl>:first-child{margin-top:0}.md\:prose-xl>:last-child{margin-bottom:0}.md\:prose-2xl{font-size:1.5rem;line-height:1.6666667}.md\:prose-2xl p{margin-top:1.3333333em;margin-bottom:1.3333333em}.md\:prose-2xl [class~=lead]{font-size:1.25em;line-height:1.4666667;margin-top:1.0666667em;margin-bottom:1.0666667em}.md\:prose-2xl blockquote{margin-top:1.7777778em;margin-bottom:1.7777778em;padding-left:1.1111111em}.md\:prose-2xl h1{font-size:2.6666667em;margin-top:0;margin-bottom:.875em;line-height:1}.md\:prose-2xl h2{font-size:2em;margin-top:1.5em;margin-bottom:.8333333em;line-height:1.0833333}.md\:prose-2xl h3{font-size:1.5em;margin-top:1.5555556em;margin-bottom:.6666667em;line-height:1.2222222}.md\:prose-2xl h4{margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.md\:prose-2xl figure,.md\:prose-2xl img,.md\:prose-2xl video{margin-top:2em;margin-bottom:2em}.md\:prose-2xl figure>*{margin-top:0;margin-bottom:0}.md\:prose-2xl figure figcaption{font-size:.8333333em;line-height:1.6;margin-top:1em}.md\:prose-2xl code{font-size:.8333333em}.md\:prose-2xl h2 code{font-size:.875em}.md\:prose-2xl h3 code{font-size:.8888889em}.md\:prose-2xl pre{font-size:.8333333em;line-height:1.8;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.2em 1.6em}.md\:prose-2xl ol,.md\:prose-2xl ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.md\:prose-2xl li{margin-top:.5em;margin-bottom:.5em}.md\:prose-2xl ol>li{padding-left:1.6666667em}.md\:prose-2xl ol>li:before{left:0}.md\:prose-2xl ul>li{padding-left:1.6666667em}.md\:prose-2xl ul>li:before{width:.3333333em;height:.3333333em;top:.66667em;left:.25em}.md\:prose-2xl>ul>li p{margin-top:.8333333em;margin-bottom:.8333333em}.md\:prose-2xl>ul>li>:first-child{margin-top:1.3333333em}.md\:prose-2xl>ul>li>:last-child{margin-bottom:1.3333333em}.md\:prose-2xl>ol>li>:first-child{margin-top:1.3333333em}.md\:prose-2xl>ol>li>:last-child{margin-bottom:1.3333333em}.md\:prose-2xl ol ol,.md\:prose-2xl ol ul,.md\:prose-2xl ul ol,.md\:prose-2xl ul ul{margin-top:.6666667em;margin-bottom:.6666667em}.md\:prose-2xl hr{margin-top:3em;margin-bottom:3em}.md\:prose-2xl h2+*,.md\:prose-2xl h3+*,.md\:prose-2xl h4+*,.md\:prose-2xl hr+*{margin-top:0}.md\:prose-2xl table{font-size:.8333333em;line-height:1.4}.md\:prose-2xl thead th{padding-right:.6em;padding-bottom:.8em;padding-left:.6em}.md\:prose-2xl thead th:first-child{padding-left:0}.md\:prose-2xl thead th:last-child{padding-right:0}.md\:prose-2xl tbody td{padding:.8em .6em}.md\:prose-2xl tbody td:first-child{padding-left:0}.md\:prose-2xl tbody td:last-child{padding-right:0}.md\:prose-2xl>:first-child{margin-top:0}.md\:prose-2xl>:last-child{margin-bottom:0}.md\:border-t-0{border-top-width:0}.md\:border-l{border-left-width:1px}.md\:grid{display:grid}.md\:mt-0{margin-top:0}.md\:gap-6{grid-gap:1.5rem;gap:1.5rem}.md\:grid-cols-2{grid-template-columns:repeat(2,minmax(0,1fr))}.md\:grid-cols-3{grid-template-columns:repeat(3,minmax(0,1fr))}.md\:col-span-1{grid-column:span 1/span 1}.md\:col-span-2{grid-column:span 2/span 2}}@media (min-width:1024px){.lg\:container{width:100%}@media (min-width:640px){.lg\:container{max-width:640px}}@media (min-width:768px){.lg\:container{max-width:768px}}@media (min-width:1024px){.lg\:container{max-width:1024px}}@media (min-width:1280px){.lg\:container{max-width:1280px}}.lg\:prose{color:#374151;max-width:65ch}.lg\:prose [class~=lead]{color:#4b5563;font-size:1.25em;line-height:1.6;margin-top:1.2em;margin-bottom:1.2em}.lg\:prose a{color:#5850ec;text-decoration:none;font-weight:600}.lg\:prose strong{color:#161e2e;font-weight:600}.lg\:prose ol{counter-reset:list-counter;margin-top:1.25em;margin-bottom:1.25em}.lg\:prose ol>li{position:relative;counter-increment:list-counter;padding-left:1.75em}.lg\:prose ol>li:before{content:counter(list-counter) ".";position:absolute;font-weight:400;color:#6b7280}.lg\:prose ul>li{position:relative;padding-left:1.75em}.lg\:prose ul>li:before{content:"";position:absolute;background-color:#d2d6dc;border-radius:50%;width:.375em;height:.375em;top:.6875em;left:.25em}.lg\:prose hr{border-color:#e5e7eb;border-top-width:1px;margin-top:3em;margin-bottom:3em}.lg\:prose blockquote{font-weight:500;font-style:italic;color:#161e2e;border-left-width:.25rem;border-left-color:#e5e7eb;quotes:"\201C""\201D""\2018""\2019";margin-top:1.6em;margin-bottom:1.6em;padding-left:1em}.lg\:prose blockquote p:first-of-type:before{content:open-quote}.lg\:prose blockquote p:last-of-type:after{content:close-quote}.lg\:prose h1{color:#1a202c;font-weight:800;font-size:2.25em;margin-top:0;margin-bottom:.8888889em;line-height:1.1111111}.lg\:prose h2{color:#1a202c;font-weight:700;font-size:1.5em;margin-top:2em;margin-bottom:1em;line-height:1.3333333}.lg\:prose h3{font-size:1.25em;margin-top:1.6em;margin-bottom:.6em;line-height:1.6}.lg\:prose h3,.lg\:prose h4{color:#1a202c;font-weight:600}.lg\:prose h4{margin-top:1.5em;margin-bottom:.5em;line-height:1.5}.lg\:prose figure figcaption{color:#6b7280;font-size:.875em;line-height:1.4285714;margin-top:.8571429em}.lg\:prose code{color:#161e2e;font-weight:600;font-size:.875em}.lg\:prose code:after,.lg\:prose code:before{content:"`"}.lg\:prose pre{color:#e5e7eb;background-color:#252f3f;overflow-x:auto;font-size:.875em;line-height:1.7142857;margin-top:1.7142857em;margin-bottom:1.7142857em;border-radius:.375rem;padding:.8571429em 1.1428571em}.lg\:prose pre code{background-color:transparent;border-width:0;border-radius:0;padding:0;font-weight:400;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}.lg\:prose pre code:after,.lg\:prose pre code:before{content:""}.lg\:prose table{width:100%;table-layout:auto;text-align:left;margin-top:2em;margin-bottom:2em;font-size:.875em;line-height:1.7142857}.lg\:prose thead{color:#161e2e;font-weight:600;border-bottom-width:1px;border-bottom-color:#d2d6dc}.lg\:prose thead th{vertical-align:bottom;padding-right:.5714286em;padding-bottom:.5714286em;padding-left:.5714286em}.lg\:prose tbody tr{border-bottom-width:1px;border-bottom-color:#e5e7eb}.lg\:prose tbody tr:last-child{border-bottom-width:0}.lg\:prose tbody td{vertical-align:top;padding:.5714286em}.lg\:prose{font-size:1rem;line-height:1.75}.lg\:prose p{margin-top:1.25em;margin-bottom:1.25em}.lg\:prose figure,.lg\:prose img,.lg\:prose video{margin-top:2em;margin-bottom:2em}.lg\:prose figure>*{margin-top:0;margin-bottom:0}.lg\:prose h2 code{font-size:.875em}.lg\:prose h3 code{font-size:.9em}.lg\:prose ul{margin-top:1.25em;margin-bottom:1.25em}.lg\:prose li{margin-top:.5em;margin-bottom:.5em}.lg\:prose ol>li:before{left:0}.lg\:prose>ul>li p{margin-top:.75em;margin-bottom:.75em}.lg\:prose>ul>li>:first-child{margin-top:1.25em}.lg\:prose>ul>li>:last-child{margin-bottom:1.25em}.lg\:prose>ol>li>:first-child{margin-top:1.25em}.lg\:prose>ol>li>:last-child{margin-bottom:1.25em}.lg\:prose ol ol,.lg\:prose ol ul,.lg\:prose ul ol,.lg\:prose ul ul{margin-top:.75em;margin-bottom:.75em}.lg\:prose h2+*,.lg\:prose h3+*,.lg\:prose h4+*,.lg\:prose hr+*{margin-top:0}.lg\:prose thead th:first-child{padding-left:0}.lg\:prose thead th:last-child{padding-right:0}.lg\:prose tbody td:first-child{padding-left:0}.lg\:prose tbody td:last-child{padding-right:0}.lg\:prose>:first-child{margin-top:0}.lg\:prose>:last-child{margin-bottom:0}.lg\:prose h1,.lg\:prose h2,.lg\:prose h3,.lg\:prose h4{color:#161e2e}.lg\:prose-sm{font-size:.875rem;line-height:1.7142857}.lg\:prose-sm p{margin-top:1.1428571em;margin-bottom:1.1428571em}.lg\:prose-sm [class~=lead]{font-size:1.2857143em;line-height:1.5555556;margin-top:.8888889em;margin-bottom:.8888889em}.lg\:prose-sm blockquote{margin-top:1.3333333em;margin-bottom:1.3333333em;padding-left:1.1111111em}.lg\:prose-sm h1{font-size:2.1428571em;margin-top:0;margin-bottom:.8em;line-height:1.2}.lg\:prose-sm h2{font-size:1.4285714em;margin-top:1.6em;margin-bottom:.8em;line-height:1.4}.lg\:prose-sm h3{font-size:1.2857143em;margin-top:1.5555556em;margin-bottom:.4444444em;line-height:1.5555556}.lg\:prose-sm h4{margin-top:1.4285714em;margin-bottom:.5714286em;line-height:1.4285714}.lg\:prose-sm figure,.lg\:prose-sm img,.lg\:prose-sm video{margin-top:1.7142857em;margin-bottom:1.7142857em}.lg\:prose-sm figure>*{margin-top:0;margin-bottom:0}.lg\:prose-sm figure figcaption{font-size:.8571429em;line-height:1.3333333;margin-top:.6666667em}.lg\:prose-sm code{font-size:.8571429em}.lg\:prose-sm h2 code{font-size:.9em}.lg\:prose-sm h3 code{font-size:.8888889em}.lg\:prose-sm pre{font-size:.8571429em;line-height:1.6666667;margin-top:1.6666667em;margin-bottom:1.6666667em;border-radius:.25rem;padding:.6666667em 1em}.lg\:prose-sm ol,.lg\:prose-sm ul{margin-top:1.1428571em;margin-bottom:1.1428571em}.lg\:prose-sm li{margin-top:.2857143em;margin-bottom:.2857143em}.lg\:prose-sm ol>li{padding-left:1.5714286em}.lg\:prose-sm ol>li:before{left:0}.lg\:prose-sm ul>li{padding-left:1.5714286em}.lg\:prose-sm ul>li:before{height:.3571429em;width:.3571429em;top:.67857em;left:.2142857em}.lg\:prose-sm>ul>li p{margin-top:.5714286em;margin-bottom:.5714286em}.lg\:prose-sm>ul>li>:first-child{margin-top:1.1428571em}.lg\:prose-sm>ul>li>:last-child{margin-bottom:1.1428571em}.lg\:prose-sm>ol>li>:first-child{margin-top:1.1428571em}.lg\:prose-sm>ol>li>:last-child{margin-bottom:1.1428571em}.lg\:prose-sm ol ol,.lg\:prose-sm ol ul,.lg\:prose-sm ul ol,.lg\:prose-sm ul ul{margin-top:.5714286em;margin-bottom:.5714286em}.lg\:prose-sm hr{margin-top:2.8571429em;margin-bottom:2.8571429em}.lg\:prose-sm h2+*,.lg\:prose-sm h3+*,.lg\:prose-sm h4+*,.lg\:prose-sm hr+*{margin-top:0}.lg\:prose-sm table{font-size:.8571429em;line-height:1.5}.lg\:prose-sm thead th{padding-right:1em;padding-bottom:.6666667em;padding-left:1em}.lg\:prose-sm thead th:first-child{padding-left:0}.lg\:prose-sm thead th:last-child{padding-right:0}.lg\:prose-sm tbody td{padding:.6666667em 1em}.lg\:prose-sm tbody td:first-child{padding-left:0}.lg\:prose-sm tbody td:last-child{padding-right:0}.lg\:prose-sm>:first-child{margin-top:0}.lg\:prose-sm>:last-child{margin-bottom:0}.lg\:prose-lg{font-size:1.125rem;line-height:1.7777778}.lg\:prose-lg p{margin-top:1.3333333em;margin-bottom:1.3333333em}.lg\:prose-lg [class~=lead]{font-size:1.2222222em;line-height:1.4545455;margin-top:1.0909091em;margin-bottom:1.0909091em}.lg\:prose-lg blockquote{margin-top:1.6666667em;margin-bottom:1.6666667em;padding-left:1em}.lg\:prose-lg h1{font-size:2.6666667em;margin-top:0;margin-bottom:.8333333em;line-height:1}.lg\:prose-lg h2{font-size:1.6666667em;margin-top:1.8666667em;margin-bottom:1.0666667em;line-height:1.3333333}.lg\:prose-lg h3{font-size:1.3333333em;margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.lg\:prose-lg h4{margin-top:1.7777778em;margin-bottom:.4444444em;line-height:1.5555556}.lg\:prose-lg figure,.lg\:prose-lg img,.lg\:prose-lg video{margin-top:1.7777778em;margin-bottom:1.7777778em}.lg\:prose-lg figure>*{margin-top:0;margin-bottom:0}.lg\:prose-lg figure figcaption{font-size:.8888889em;line-height:1.5;margin-top:1em}.lg\:prose-lg code{font-size:.8888889em}.lg\:prose-lg h2 code{font-size:.8666667em}.lg\:prose-lg h3 code{font-size:.875em}.lg\:prose-lg pre{font-size:.8888889em;line-height:1.75;margin-top:2em;margin-bottom:2em;border-radius:.375rem;padding:1em 1.5em}.lg\:prose-lg ol,.lg\:prose-lg ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.lg\:prose-lg li{margin-top:.6666667em;margin-bottom:.6666667em}.lg\:prose-lg ol>li{padding-left:1.6666667em}.lg\:prose-lg ol>li:before{left:0}.lg\:prose-lg ul>li{padding-left:1.6666667em}.lg\:prose-lg ul>li:before{width:.3333333em;height:.3333333em;top:.72222em;left:.2222222em}.lg\:prose-lg>ul>li p{margin-top:.8888889em;margin-bottom:.8888889em}.lg\:prose-lg>ul>li>:first-child{margin-top:1.3333333em}.lg\:prose-lg>ul>li>:last-child{margin-bottom:1.3333333em}.lg\:prose-lg>ol>li>:first-child{margin-top:1.3333333em}.lg\:prose-lg>ol>li>:last-child{margin-bottom:1.3333333em}.lg\:prose-lg ol ol,.lg\:prose-lg ol ul,.lg\:prose-lg ul ol,.lg\:prose-lg ul ul{margin-top:.8888889em;margin-bottom:.8888889em}.lg\:prose-lg hr{margin-top:3.1111111em;margin-bottom:3.1111111em}.lg\:prose-lg h2+*,.lg\:prose-lg h3+*,.lg\:prose-lg h4+*,.lg\:prose-lg hr+*{margin-top:0}.lg\:prose-lg table{font-size:.8888889em;line-height:1.5}.lg\:prose-lg thead th{padding-right:.75em;padding-bottom:.75em;padding-left:.75em}.lg\:prose-lg thead th:first-child{padding-left:0}.lg\:prose-lg thead th:last-child{padding-right:0}.lg\:prose-lg tbody td{padding:.75em}.lg\:prose-lg tbody td:first-child{padding-left:0}.lg\:prose-lg tbody td:last-child{padding-right:0}.lg\:prose-lg>:first-child{margin-top:0}.lg\:prose-lg>:last-child{margin-bottom:0}.lg\:prose-xl{font-size:1.25rem;line-height:1.8}.lg\:prose-xl p{margin-top:1.2em;margin-bottom:1.2em}.lg\:prose-xl [class~=lead]{font-size:1.2em;line-height:1.5;margin-top:1em;margin-bottom:1em}.lg\:prose-xl blockquote{margin-top:1.6em;margin-bottom:1.6em;padding-left:1.0666667em}.lg\:prose-xl h1{font-size:2.8em;margin-top:0;margin-bottom:.8571429em;line-height:1}.lg\:prose-xl h2{font-size:1.8em;margin-top:1.5555556em;margin-bottom:.8888889em;line-height:1.1111111}.lg\:prose-xl h3{font-size:1.5em;margin-top:1.6em;margin-bottom:.6666667em;line-height:1.3333333}.lg\:prose-xl h4{margin-top:1.8em;margin-bottom:.6em;line-height:1.6}.lg\:prose-xl figure,.lg\:prose-xl img,.lg\:prose-xl video{margin-top:2em;margin-bottom:2em}.lg\:prose-xl figure>*{margin-top:0;margin-bottom:0}.lg\:prose-xl figure figcaption{font-size:.9em;line-height:1.5555556;margin-top:1em}.lg\:prose-xl code{font-size:.9em}.lg\:prose-xl h2 code{font-size:.8611111em}.lg\:prose-xl h3 code{font-size:.9em}.lg\:prose-xl pre{font-size:.9em;line-height:1.7777778;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.1111111em 1.3333333em}.lg\:prose-xl ol,.lg\:prose-xl ul{margin-top:1.2em;margin-bottom:1.2em}.lg\:prose-xl li{margin-top:.6em;margin-bottom:.6em}.lg\:prose-xl ol>li{padding-left:1.8em}.lg\:prose-xl ol>li:before{left:0}.lg\:prose-xl ul>li{padding-left:1.8em}.lg\:prose-xl ul>li:before{width:.35em;height:.35em;top:.725em;left:.25em}.lg\:prose-xl>ul>li p{margin-top:.8em;margin-bottom:.8em}.lg\:prose-xl>ul>li>:first-child{margin-top:1.2em}.lg\:prose-xl>ul>li>:last-child{margin-bottom:1.2em}.lg\:prose-xl>ol>li>:first-child{margin-top:1.2em}.lg\:prose-xl>ol>li>:last-child{margin-bottom:1.2em}.lg\:prose-xl ol ol,.lg\:prose-xl ol ul,.lg\:prose-xl ul ol,.lg\:prose-xl ul ul{margin-top:.8em;margin-bottom:.8em}.lg\:prose-xl hr{margin-top:2.8em;margin-bottom:2.8em}.lg\:prose-xl h2+*,.lg\:prose-xl h3+*,.lg\:prose-xl h4+*,.lg\:prose-xl hr+*{margin-top:0}.lg\:prose-xl table{font-size:.9em;line-height:1.5555556}.lg\:prose-xl thead th{padding-right:.6666667em;padding-bottom:.8888889em;padding-left:.6666667em}.lg\:prose-xl thead th:first-child{padding-left:0}.lg\:prose-xl thead th:last-child{padding-right:0}.lg\:prose-xl tbody td{padding:.8888889em .6666667em}.lg\:prose-xl tbody td:first-child{padding-left:0}.lg\:prose-xl tbody td:last-child{padding-right:0}.lg\:prose-xl>:first-child{margin-top:0}.lg\:prose-xl>:last-child{margin-bottom:0}.lg\:prose-2xl{font-size:1.5rem;line-height:1.6666667}.lg\:prose-2xl p{margin-top:1.3333333em;margin-bottom:1.3333333em}.lg\:prose-2xl [class~=lead]{font-size:1.25em;line-height:1.4666667;margin-top:1.0666667em;margin-bottom:1.0666667em}.lg\:prose-2xl blockquote{margin-top:1.7777778em;margin-bottom:1.7777778em;padding-left:1.1111111em}.lg\:prose-2xl h1{font-size:2.6666667em;margin-top:0;margin-bottom:.875em;line-height:1}.lg\:prose-2xl h2{font-size:2em;margin-top:1.5em;margin-bottom:.8333333em;line-height:1.0833333}.lg\:prose-2xl h3{font-size:1.5em;margin-top:1.5555556em;margin-bottom:.6666667em;line-height:1.2222222}.lg\:prose-2xl h4{margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.lg\:prose-2xl figure,.lg\:prose-2xl img,.lg\:prose-2xl video{margin-top:2em;margin-bottom:2em}.lg\:prose-2xl figure>*{margin-top:0;margin-bottom:0}.lg\:prose-2xl figure figcaption{font-size:.8333333em;line-height:1.6;margin-top:1em}.lg\:prose-2xl code{font-size:.8333333em}.lg\:prose-2xl h2 code{font-size:.875em}.lg\:prose-2xl h3 code{font-size:.8888889em}.lg\:prose-2xl pre{font-size:.8333333em;line-height:1.8;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.2em 1.6em}.lg\:prose-2xl ol,.lg\:prose-2xl ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.lg\:prose-2xl li{margin-top:.5em;margin-bottom:.5em}.lg\:prose-2xl ol>li{padding-left:1.6666667em}.lg\:prose-2xl ol>li:before{left:0}.lg\:prose-2xl ul>li{padding-left:1.6666667em}.lg\:prose-2xl ul>li:before{width:.3333333em;height:.3333333em;top:.66667em;left:.25em}.lg\:prose-2xl>ul>li p{margin-top:.8333333em;margin-bottom:.8333333em}.lg\:prose-2xl>ul>li>:first-child{margin-top:1.3333333em}.lg\:prose-2xl>ul>li>:last-child{margin-bottom:1.3333333em}.lg\:prose-2xl>ol>li>:first-child{margin-top:1.3333333em}.lg\:prose-2xl>ol>li>:last-child{margin-bottom:1.3333333em}.lg\:prose-2xl ol ol,.lg\:prose-2xl ol ul,.lg\:prose-2xl ul ol,.lg\:prose-2xl ul ul{margin-top:.6666667em;margin-bottom:.6666667em}.lg\:prose-2xl hr{margin-top:3em;margin-bottom:3em}.lg\:prose-2xl h2+*,.lg\:prose-2xl h3+*,.lg\:prose-2xl h4+*,.lg\:prose-2xl hr+*{margin-top:0}.lg\:prose-2xl table{font-size:.8333333em;line-height:1.4}.lg\:prose-2xl thead th{padding-right:.6em;padding-bottom:.8em;padding-left:.6em}.lg\:prose-2xl thead th:first-child{padding-left:0}.lg\:prose-2xl thead th:last-child{padding-right:0}.lg\:prose-2xl tbody td{padding:.8em .6em}.lg\:prose-2xl tbody td:first-child{padding-left:0}.lg\:prose-2xl tbody td:last-child{padding-right:0}.lg\:prose-2xl>:first-child{margin-top:0}.lg\:prose-2xl>:last-child{margin-bottom:0}.lg\:px-8{padding-left:2rem;padding-right:2rem}.lg\:col-span-4{grid-column:span 4/span 4}}@media (min-width:1280px){.xl\:container{width:100%}@media (min-width:640px){.xl\:container{max-width:640px}}@media (min-width:768px){.xl\:container{max-width:768px}}@media (min-width:1024px){.xl\:container{max-width:1024px}}@media (min-width:1280px){.xl\:container{max-width:1280px}}.xl\:prose{color:#374151;max-width:65ch}.xl\:prose [class~=lead]{color:#4b5563;font-size:1.25em;line-height:1.6;margin-top:1.2em;margin-bottom:1.2em}.xl\:prose a{color:#5850ec;text-decoration:none;font-weight:600}.xl\:prose strong{color:#161e2e;font-weight:600}.xl\:prose ol{counter-reset:list-counter;margin-top:1.25em;margin-bottom:1.25em}.xl\:prose ol>li{position:relative;counter-increment:list-counter;padding-left:1.75em}.xl\:prose ol>li:before{content:counter(list-counter) ".";position:absolute;font-weight:400;color:#6b7280}.xl\:prose ul>li{position:relative;padding-left:1.75em}.xl\:prose ul>li:before{content:"";position:absolute;background-color:#d2d6dc;border-radius:50%;width:.375em;height:.375em;top:.6875em;left:.25em}.xl\:prose hr{border-color:#e5e7eb;border-top-width:1px;margin-top:3em;margin-bottom:3em}.xl\:prose blockquote{font-weight:500;font-style:italic;color:#161e2e;border-left-width:.25rem;border-left-color:#e5e7eb;quotes:"\201C""\201D""\2018""\2019";margin-top:1.6em;margin-bottom:1.6em;padding-left:1em}.xl\:prose blockquote p:first-of-type:before{content:open-quote}.xl\:prose blockquote p:last-of-type:after{content:close-quote}.xl\:prose h1{color:#1a202c;font-weight:800;font-size:2.25em;margin-top:0;margin-bottom:.8888889em;line-height:1.1111111}.xl\:prose h2{color:#1a202c;font-weight:700;font-size:1.5em;margin-top:2em;margin-bottom:1em;line-height:1.3333333}.xl\:prose h3{font-size:1.25em;margin-top:1.6em;margin-bottom:.6em;line-height:1.6}.xl\:prose h3,.xl\:prose h4{color:#1a202c;font-weight:600}.xl\:prose h4{margin-top:1.5em;margin-bottom:.5em;line-height:1.5}.xl\:prose figure figcaption{color:#6b7280;font-size:.875em;line-height:1.4285714;margin-top:.8571429em}.xl\:prose code{color:#161e2e;font-weight:600;font-size:.875em}.xl\:prose code:after,.xl\:prose code:before{content:"`"}.xl\:prose pre{color:#e5e7eb;background-color:#252f3f;overflow-x:auto;font-size:.875em;line-height:1.7142857;margin-top:1.7142857em;margin-bottom:1.7142857em;border-radius:.375rem;padding:.8571429em 1.1428571em}.xl\:prose pre code{background-color:transparent;border-width:0;border-radius:0;padding:0;font-weight:400;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}.xl\:prose pre code:after,.xl\:prose pre code:before{content:""}.xl\:prose table{width:100%;table-layout:auto;text-align:left;margin-top:2em;margin-bottom:2em;font-size:.875em;line-height:1.7142857}.xl\:prose thead{color:#161e2e;font-weight:600;border-bottom-width:1px;border-bottom-color:#d2d6dc}.xl\:prose thead th{vertical-align:bottom;padding-right:.5714286em;padding-bottom:.5714286em;padding-left:.5714286em}.xl\:prose tbody tr{border-bottom-width:1px;border-bottom-color:#e5e7eb}.xl\:prose tbody tr:last-child{border-bottom-width:0}.xl\:prose tbody td{vertical-align:top;padding:.5714286em}.xl\:prose{font-size:1rem;line-height:1.75}.xl\:prose p{margin-top:1.25em;margin-bottom:1.25em}.xl\:prose figure,.xl\:prose img,.xl\:prose video{margin-top:2em;margin-bottom:2em}.xl\:prose figure>*{margin-top:0;margin-bottom:0}.xl\:prose h2 code{font-size:.875em}.xl\:prose h3 code{font-size:.9em}.xl\:prose ul{margin-top:1.25em;margin-bottom:1.25em}.xl\:prose li{margin-top:.5em;margin-bottom:.5em}.xl\:prose ol>li:before{left:0}.xl\:prose>ul>li p{margin-top:.75em;margin-bottom:.75em}.xl\:prose>ul>li>:first-child{margin-top:1.25em}.xl\:prose>ul>li>:last-child{margin-bottom:1.25em}.xl\:prose>ol>li>:first-child{margin-top:1.25em}.xl\:prose>ol>li>:last-child{margin-bottom:1.25em}.xl\:prose ol ol,.xl\:prose ol ul,.xl\:prose ul ol,.xl\:prose ul ul{margin-top:.75em;margin-bottom:.75em}.xl\:prose h2+*,.xl\:prose h3+*,.xl\:prose h4+*,.xl\:prose hr+*{margin-top:0}.xl\:prose thead th:first-child{padding-left:0}.xl\:prose thead th:last-child{padding-right:0}.xl\:prose tbody td:first-child{padding-left:0}.xl\:prose tbody td:last-child{padding-right:0}.xl\:prose>:first-child{margin-top:0}.xl\:prose>:last-child{margin-bottom:0}.xl\:prose h1,.xl\:prose h2,.xl\:prose h3,.xl\:prose h4{color:#161e2e}.xl\:prose-sm{font-size:.875rem;line-height:1.7142857}.xl\:prose-sm p{margin-top:1.1428571em;margin-bottom:1.1428571em}.xl\:prose-sm [class~=lead]{font-size:1.2857143em;line-height:1.5555556;margin-top:.8888889em;margin-bottom:.8888889em}.xl\:prose-sm blockquote{margin-top:1.3333333em;margin-bottom:1.3333333em;padding-left:1.1111111em}.xl\:prose-sm h1{font-size:2.1428571em;margin-top:0;margin-bottom:.8em;line-height:1.2}.xl\:prose-sm h2{font-size:1.4285714em;margin-top:1.6em;margin-bottom:.8em;line-height:1.4}.xl\:prose-sm h3{font-size:1.2857143em;margin-top:1.5555556em;margin-bottom:.4444444em;line-height:1.5555556}.xl\:prose-sm h4{margin-top:1.4285714em;margin-bottom:.5714286em;line-height:1.4285714}.xl\:prose-sm figure,.xl\:prose-sm img,.xl\:prose-sm video{margin-top:1.7142857em;margin-bottom:1.7142857em}.xl\:prose-sm figure>*{margin-top:0;margin-bottom:0}.xl\:prose-sm figure figcaption{font-size:.8571429em;line-height:1.3333333;margin-top:.6666667em}.xl\:prose-sm code{font-size:.8571429em}.xl\:prose-sm h2 code{font-size:.9em}.xl\:prose-sm h3 code{font-size:.8888889em}.xl\:prose-sm pre{font-size:.8571429em;line-height:1.6666667;margin-top:1.6666667em;margin-bottom:1.6666667em;border-radius:.25rem;padding:.6666667em 1em}.xl\:prose-sm ol,.xl\:prose-sm ul{margin-top:1.1428571em;margin-bottom:1.1428571em}.xl\:prose-sm li{margin-top:.2857143em;margin-bottom:.2857143em}.xl\:prose-sm ol>li{padding-left:1.5714286em}.xl\:prose-sm ol>li:before{left:0}.xl\:prose-sm ul>li{padding-left:1.5714286em}.xl\:prose-sm ul>li:before{height:.3571429em;width:.3571429em;top:.67857em;left:.2142857em}.xl\:prose-sm>ul>li p{margin-top:.5714286em;margin-bottom:.5714286em}.xl\:prose-sm>ul>li>:first-child{margin-top:1.1428571em}.xl\:prose-sm>ul>li>:last-child{margin-bottom:1.1428571em}.xl\:prose-sm>ol>li>:first-child{margin-top:1.1428571em}.xl\:prose-sm>ol>li>:last-child{margin-bottom:1.1428571em}.xl\:prose-sm ol ol,.xl\:prose-sm ol ul,.xl\:prose-sm ul ol,.xl\:prose-sm ul ul{margin-top:.5714286em;margin-bottom:.5714286em}.xl\:prose-sm hr{margin-top:2.8571429em;margin-bottom:2.8571429em}.xl\:prose-sm h2+*,.xl\:prose-sm h3+*,.xl\:prose-sm h4+*,.xl\:prose-sm hr+*{margin-top:0}.xl\:prose-sm table{font-size:.8571429em;line-height:1.5}.xl\:prose-sm thead th{padding-right:1em;padding-bottom:.6666667em;padding-left:1em}.xl\:prose-sm thead th:first-child{padding-left:0}.xl\:prose-sm thead th:last-child{padding-right:0}.xl\:prose-sm tbody td{padding:.6666667em 1em}.xl\:prose-sm tbody td:first-child{padding-left:0}.xl\:prose-sm tbody td:last-child{padding-right:0}.xl\:prose-sm>:first-child{margin-top:0}.xl\:prose-sm>:last-child{margin-bottom:0}.xl\:prose-lg{font-size:1.125rem;line-height:1.7777778}.xl\:prose-lg p{margin-top:1.3333333em;margin-bottom:1.3333333em}.xl\:prose-lg [class~=lead]{font-size:1.2222222em;line-height:1.4545455;margin-top:1.0909091em;margin-bottom:1.0909091em}.xl\:prose-lg blockquote{margin-top:1.6666667em;margin-bottom:1.6666667em;padding-left:1em}.xl\:prose-lg h1{font-size:2.6666667em;margin-top:0;margin-bottom:.8333333em;line-height:1}.xl\:prose-lg h2{font-size:1.6666667em;margin-top:1.8666667em;margin-bottom:1.0666667em;line-height:1.3333333}.xl\:prose-lg h3{font-size:1.3333333em;margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.xl\:prose-lg h4{margin-top:1.7777778em;margin-bottom:.4444444em;line-height:1.5555556}.xl\:prose-lg figure,.xl\:prose-lg img,.xl\:prose-lg video{margin-top:1.7777778em;margin-bottom:1.7777778em}.xl\:prose-lg figure>*{margin-top:0;margin-bottom:0}.xl\:prose-lg figure figcaption{font-size:.8888889em;line-height:1.5;margin-top:1em}.xl\:prose-lg code{font-size:.8888889em}.xl\:prose-lg h2 code{font-size:.8666667em}.xl\:prose-lg h3 code{font-size:.875em}.xl\:prose-lg pre{font-size:.8888889em;line-height:1.75;margin-top:2em;margin-bottom:2em;border-radius:.375rem;padding:1em 1.5em}.xl\:prose-lg ol,.xl\:prose-lg ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.xl\:prose-lg li{margin-top:.6666667em;margin-bottom:.6666667em}.xl\:prose-lg ol>li{padding-left:1.6666667em}.xl\:prose-lg ol>li:before{left:0}.xl\:prose-lg ul>li{padding-left:1.6666667em}.xl\:prose-lg ul>li:before{width:.3333333em;height:.3333333em;top:.72222em;left:.2222222em}.xl\:prose-lg>ul>li p{margin-top:.8888889em;margin-bottom:.8888889em}.xl\:prose-lg>ul>li>:first-child{margin-top:1.3333333em}.xl\:prose-lg>ul>li>:last-child{margin-bottom:1.3333333em}.xl\:prose-lg>ol>li>:first-child{margin-top:1.3333333em}.xl\:prose-lg>ol>li>:last-child{margin-bottom:1.3333333em}.xl\:prose-lg ol ol,.xl\:prose-lg ol ul,.xl\:prose-lg ul ol,.xl\:prose-lg ul ul{margin-top:.8888889em;margin-bottom:.8888889em}.xl\:prose-lg hr{margin-top:3.1111111em;margin-bottom:3.1111111em}.xl\:prose-lg h2+*,.xl\:prose-lg h3+*,.xl\:prose-lg h4+*,.xl\:prose-lg hr+*{margin-top:0}.xl\:prose-lg table{font-size:.8888889em;line-height:1.5}.xl\:prose-lg thead th{padding-right:.75em;padding-bottom:.75em;padding-left:.75em}.xl\:prose-lg thead th:first-child{padding-left:0}.xl\:prose-lg thead th:last-child{padding-right:0}.xl\:prose-lg tbody td{padding:.75em}.xl\:prose-lg tbody td:first-child{padding-left:0}.xl\:prose-lg tbody td:last-child{padding-right:0}.xl\:prose-lg>:first-child{margin-top:0}.xl\:prose-lg>:last-child{margin-bottom:0}.xl\:prose-xl{font-size:1.25rem;line-height:1.8}.xl\:prose-xl p{margin-top:1.2em;margin-bottom:1.2em}.xl\:prose-xl [class~=lead]{font-size:1.2em;line-height:1.5;margin-top:1em;margin-bottom:1em}.xl\:prose-xl blockquote{margin-top:1.6em;margin-bottom:1.6em;padding-left:1.0666667em}.xl\:prose-xl h1{font-size:2.8em;margin-top:0;margin-bottom:.8571429em;line-height:1}.xl\:prose-xl h2{font-size:1.8em;margin-top:1.5555556em;margin-bottom:.8888889em;line-height:1.1111111}.xl\:prose-xl h3{font-size:1.5em;margin-top:1.6em;margin-bottom:.6666667em;line-height:1.3333333}.xl\:prose-xl h4{margin-top:1.8em;margin-bottom:.6em;line-height:1.6}.xl\:prose-xl figure,.xl\:prose-xl img,.xl\:prose-xl video{margin-top:2em;margin-bottom:2em}.xl\:prose-xl figure>*{margin-top:0;margin-bottom:0}.xl\:prose-xl figure figcaption{font-size:.9em;line-height:1.5555556;margin-top:1em}.xl\:prose-xl code{font-size:.9em}.xl\:prose-xl h2 code{font-size:.8611111em}.xl\:prose-xl h3 code{font-size:.9em}.xl\:prose-xl pre{font-size:.9em;line-height:1.7777778;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.1111111em 1.3333333em}.xl\:prose-xl ol,.xl\:prose-xl ul{margin-top:1.2em;margin-bottom:1.2em}.xl\:prose-xl li{margin-top:.6em;margin-bottom:.6em}.xl\:prose-xl ol>li{padding-left:1.8em}.xl\:prose-xl ol>li:before{left:0}.xl\:prose-xl ul>li{padding-left:1.8em}.xl\:prose-xl ul>li:before{width:.35em;height:.35em;top:.725em;left:.25em}.xl\:prose-xl>ul>li p{margin-top:.8em;margin-bottom:.8em}.xl\:prose-xl>ul>li>:first-child{margin-top:1.2em}.xl\:prose-xl>ul>li>:last-child{margin-bottom:1.2em}.xl\:prose-xl>ol>li>:first-child{margin-top:1.2em}.xl\:prose-xl>ol>li>:last-child{margin-bottom:1.2em}.xl\:prose-xl ol ol,.xl\:prose-xl ol ul,.xl\:prose-xl ul ol,.xl\:prose-xl ul ul{margin-top:.8em;margin-bottom:.8em}.xl\:prose-xl hr{margin-top:2.8em;margin-bottom:2.8em}.xl\:prose-xl h2+*,.xl\:prose-xl h3+*,.xl\:prose-xl h4+*,.xl\:prose-xl hr+*{margin-top:0}.xl\:prose-xl table{font-size:.9em;line-height:1.5555556}.xl\:prose-xl thead th{padding-right:.6666667em;padding-bottom:.8888889em;padding-left:.6666667em}.xl\:prose-xl thead th:first-child{padding-left:0}.xl\:prose-xl thead th:last-child{padding-right:0}.xl\:prose-xl tbody td{padding:.8888889em .6666667em}.xl\:prose-xl tbody td:first-child{padding-left:0}.xl\:prose-xl tbody td:last-child{padding-right:0}.xl\:prose-xl>:first-child{margin-top:0}.xl\:prose-xl>:last-child{margin-bottom:0}.xl\:prose-2xl{font-size:1.5rem;line-height:1.6666667}.xl\:prose-2xl p{margin-top:1.3333333em;margin-bottom:1.3333333em}.xl\:prose-2xl [class~=lead]{font-size:1.25em;line-height:1.4666667;margin-top:1.0666667em;margin-bottom:1.0666667em}.xl\:prose-2xl blockquote{margin-top:1.7777778em;margin-bottom:1.7777778em;padding-left:1.1111111em}.xl\:prose-2xl h1{font-size:2.6666667em;margin-top:0;margin-bottom:.875em;line-height:1}.xl\:prose-2xl h2{font-size:2em;margin-top:1.5em;margin-bottom:.8333333em;line-height:1.0833333}.xl\:prose-2xl h3{font-size:1.5em;margin-top:1.5555556em;margin-bottom:.6666667em;line-height:1.2222222}.xl\:prose-2xl h4{margin-top:1.6666667em;margin-bottom:.6666667em;line-height:1.5}.xl\:prose-2xl figure,.xl\:prose-2xl img,.xl\:prose-2xl video{margin-top:2em;margin-bottom:2em}.xl\:prose-2xl figure>*{margin-top:0;margin-bottom:0}.xl\:prose-2xl figure figcaption{font-size:.8333333em;line-height:1.6;margin-top:1em}.xl\:prose-2xl code{font-size:.8333333em}.xl\:prose-2xl h2 code{font-size:.875em}.xl\:prose-2xl h3 code{font-size:.8888889em}.xl\:prose-2xl pre{font-size:.8333333em;line-height:1.8;margin-top:2em;margin-bottom:2em;border-radius:.5rem;padding:1.2em 1.6em}.xl\:prose-2xl ol,.xl\:prose-2xl ul{margin-top:1.3333333em;margin-bottom:1.3333333em}.xl\:prose-2xl li{margin-top:.5em;margin-bottom:.5em}.xl\:prose-2xl ol>li{padding-left:1.6666667em}.xl\:prose-2xl ol>li:before{left:0}.xl\:prose-2xl ul>li{padding-left:1.6666667em}.xl\:prose-2xl ul>li:before{width:.3333333em;height:.3333333em;top:.66667em;left:.25em}.xl\:prose-2xl>ul>li p{margin-top:.8333333em;margin-bottom:.8333333em}.xl\:prose-2xl>ul>li>:first-child{margin-top:1.3333333em}.xl\:prose-2xl>ul>li>:last-child{margin-bottom:1.3333333em}.xl\:prose-2xl>ol>li>:first-child{margin-top:1.3333333em}.xl\:prose-2xl>ol>li>:last-child{margin-bottom:1.3333333em}.xl\:prose-2xl ol ol,.xl\:prose-2xl ol ul,.xl\:prose-2xl ul ol,.xl\:prose-2xl ul ul{margin-top:.6666667em;margin-bottom:.6666667em}.xl\:prose-2xl hr{margin-top:3em;margin-bottom:3em}.xl\:prose-2xl h2+*,.xl\:prose-2xl h3+*,.xl\:prose-2xl h4+*,.xl\:prose-2xl hr+*{margin-top:0}.xl\:prose-2xl table{font-size:.8333333em;line-height:1.4}.xl\:prose-2xl thead th{padding-right:.6em;padding-bottom:.8em;padding-left:.6em}.xl\:prose-2xl thead th:first-child{padding-left:0}.xl\:prose-2xl thead th:last-child{padding-right:0}.xl\:prose-2xl tbody td{padding:.8em .6em}.xl\:prose-2xl tbody td:first-child{padding-left:0}.xl\:prose-2xl tbody td:last-child{padding-right:0}.xl\:prose-2xl>:first-child{margin-top:0}.xl\:prose-2xl>:last-child{margin-bottom:0}}
function carianggota() {
var val_nim = $("#nim").val();
if (val_nim) {
var request = $.ajax({
url: urlPerson,
beforeSend: function (xhr) {
var token = $('meta[name="csrf_token"]').attr('content');
if (token) {
return xhr.setRequestHeader('X-CSRF-TOKEN', token);
}
},
data: "nim=" + val_nim,
type: "post",
dataType: "html"
});
$('#viewPersonil').html('<div class="progress mb-4"><div class="progress-bar bg-success" role="progressbar" style="width: 25%" aria-valuenow="25" aria-valuemin="0" aria-valuemax="100"></div></div>');
//$('#viewPersonil').html("<div class='progress'><div class='progress-bar progress-bar-success progress-bar-striped' role='progressbar' aria-valuenow='40' aria-valuemin='0' aria-valuemax='100' style='width: 40%'><span class='sr-only'>40% Complete (success)</span></div></div>");
request.done(function (output) {
$('#viewPersonil').html(output);
});
}
}
$('#nim').on('keydown', function (e) {
if (e.which == 13) {
carianggota();
$("#nim").val("");
}
});
function hanyaAngka(evt) {
var charCode = (evt.which) ? evt.which : event.keyCode
if (charCode > 31 && (charCode < 48 || charCode > 57))
return false;
return true;
}
$(".btnSimpanPersonil").click(function (e) {
e.preventDefault();
$(".btnSimpanPersonil").hide();
$("#andou").html("<h3>Sedang proses ... </h3>");
$("#addPersonil").submit();
});
$('a#btn_delete').on('click', function (e) {
e.preventDefault();
var data = $(this).attr('data-file');
swal({
title: "Apakah Anda Yakin?",
text: "Anda akan menghapus data ini!",
type: "warning",
showCancelButton: true,
confirmButtonColor: "#DD6B55",
confirmButtonText: "Yes",
cancelButtonText: "No",
closeOnConfirm: false,
closeOnCancel: false
},
function (isConfirm) {
if (isConfirm) {
swal("Terhapus", "Data berhasil dihapus", "success");
setTimeout(function () {
$("#" + data).submit();
}, 1000); // 1 second delay
}
else {
swal("Dibatalkan", "Data batal dihapus", "error");
}
}
);
});
public/theme/images/logo-dark.png

8.15 KB | W: | H:

public/theme/images/logo-dark.png

29.7 KB | W: | H:

public/theme/images/logo-dark.png
public/theme/images/logo-dark.png
public/theme/images/logo-dark.png
public/theme/images/logo-dark.png
  • 2-up
  • Swipe
  • Onion skin
public/theme/images/logo-light.png

6.89 KB | W: | H:

public/theme/images/logo-light.png

25.1 KB | W: | H:

public/theme/images/logo-light.png
public/theme/images/logo-light.png
public/theme/images/logo-light.png
public/theme/images/logo-light.png
  • 2-up
  • Swipe
  • Onion skin
@tailwind base;
@tailwind components;
@tailwind utilities;
require('./bootstrap'); import './bootstrap';
import Alpine from 'alpinejs';
window.Alpine = Alpine;
Alpine.start();
# Privacy Policy
Edit this file to define the privacy policy for your application.
# Terms of Service
Edit this file to define the terms of service for your application.
// Body
$body-bg: #f8fafc;
// Typography
$font-family-sans-serif: 'Nunito', sans-serif;
$font-size-base: 0.9rem;
$line-height-base: 1.6;
// Fonts
@import url('https://fonts.googleapis.com/css?family=Nunito');
// Variables
@import 'variables';
// Bootstrap
@import '~bootstrap/scss/bootstrap';
<div>
<!-- Generate API Token -->
<x-jet-form-section submit="createApiToken">
<x-slot name="title">
{{ __('Create API Token') }}
</x-slot>
<x-slot name="description">
{{ __('API tokens allow third-party services to authenticate with our application on your behalf.') }}
</x-slot>
<x-slot name="form">
<!-- Token Name -->
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="name" value="{{ __('Token Name') }}" />
<x-jet-input id="name" type="text" class="mt-1 block w-full" wire:model.defer="createApiTokenForm.name" autofocus />
<x-jet-input-error for="name" class="mt-2" />
</div>
<!-- Token Permissions -->
@if (Laravel\Jetstream\Jetstream::hasPermissions())
<div class="col-span-6">
<x-jet-label for="permissions" value="{{ __('Permissions') }}" />
<div class="mt-2 grid grid-cols-1 md:grid-cols-2 gap-4">
@foreach (Laravel\Jetstream\Jetstream::$permissions as $permission)
<label class="flex items-center">
<x-jet-checkbox wire:model.defer="createApiTokenForm.permissions" :value="$permission"/>
<span class="ml-2 text-sm text-gray-600">{{ $permission }}</span>
</label>
@endforeach
</div>
</div>
@endif
</x-slot>
<x-slot name="actions">
<x-jet-action-message class="mr-3" on="created">
{{ __('Created.') }}
</x-jet-action-message>
<x-jet-button>
{{ __('Create') }}
</x-jet-button>
</x-slot>
</x-jet-form-section>
@if ($this->user->tokens->isNotEmpty())
<x-jet-section-border />
<!-- Manage API Tokens -->
<div class="mt-10 sm:mt-0">
<x-jet-action-section>
<x-slot name="title">
{{ __('Manage API Tokens') }}
</x-slot>
<x-slot name="description">
{{ __('You may delete any of your existing tokens if they are no longer needed.') }}
</x-slot>
<!-- API Token List -->
<x-slot name="content">
<div class="space-y-6">
@foreach ($this->user->tokens->sortBy('name') as $token)
<div class="flex items-center justify-between">
<div>
{{ $token->name }}
</div>
<div class="flex items-center">
@if ($token->last_used_at)
<div class="text-sm text-gray-400">
{{ __('Last used') }} {{ $token->last_used_at->diffForHumans() }}
</div>
@endif
@if (Laravel\Jetstream\Jetstream::hasPermissions())
<button class="cursor-pointer ml-6 text-sm text-gray-400 underline" wire:click="manageApiTokenPermissions({{ $token->id }})">
{{ __('Permissions') }}
</button>
@endif
<button class="cursor-pointer ml-6 text-sm text-red-500" wire:click="confirmApiTokenDeletion({{ $token->id }})">
{{ __('Delete') }}
</button>
</div>
</div>
@endforeach
</div>
</x-slot>
</x-jet-action-section>
</div>
@endif
<!-- Token Value Modal -->
<x-jet-dialog-modal wire:model="displayingToken">
<x-slot name="title">
{{ __('API Token') }}
</x-slot>
<x-slot name="content">
<div>
{{ __('Please copy your new API token. For your security, it won\'t be shown again.') }}
</div>
<x-jet-input x-ref="plaintextToken" type="text" readonly :value="$plainTextToken"
class="mt-4 bg-gray-100 px-4 py-2 rounded font-mono text-sm text-gray-500 w-full"
autofocus autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@showing-token-modal.window="setTimeout(() => $refs.plaintextToken.select(), 250)"
/>
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$set('displayingToken', false)" wire:loading.attr="disabled">
{{ __('Close') }}
</x-jet-secondary-button>
</x-slot>
</x-jet-dialog-modal>
<!-- API Token Permissions Modal -->
<x-jet-dialog-modal wire:model="managingApiTokenPermissions">
<x-slot name="title">
{{ __('API Token Permissions') }}
</x-slot>
<x-slot name="content">
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
@foreach (Laravel\Jetstream\Jetstream::$permissions as $permission)
<label class="flex items-center">
<x-jet-checkbox wire:model.defer="updateApiTokenForm.permissions" :value="$permission"/>
<span class="ml-2 text-sm text-gray-600">{{ $permission }}</span>
</label>
@endforeach
</div>
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$set('managingApiTokenPermissions', false)" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-button class="ml-3" wire:click="updateApiToken" wire:loading.attr="disabled">
{{ __('Save') }}
</x-jet-button>
</x-slot>
</x-jet-dialog-modal>
<!-- Delete Token Confirmation Modal -->
<x-jet-confirmation-modal wire:model="confirmingApiTokenDeletion">
<x-slot name="title">
{{ __('Delete API Token') }}
</x-slot>
<x-slot name="content">
{{ __('Are you sure you would like to delete this API token?') }}
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingApiTokenDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-danger-button class="ml-3" wire:click="deleteApiToken" wire:loading.attr="disabled">
{{ __('Delete') }}
</x-jet-danger-button>
</x-slot>
</x-jet-confirmation-modal>
</div>
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 leading-tight">
{{ __('API Tokens') }}
</h2>
</x-slot>
<div>
<div class="max-w-7xl mx-auto py-10 sm:px-6 lg:px-8">
@livewire('api.api-token-manager')
</div>
</div>
</x-app-layout>
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600">
{{ __('This is a secure area of the application. Please confirm your password before continuing.') }}
</div>
<x-jet-validation-errors class="mb-4" />
<form method="POST" action="{{ route('password.confirm') }}">
@csrf
<div>
<x-jet-label for="password" value="{{ __('Password') }}" />
<x-jet-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="current-password" autofocus />
</div>
<div class="flex justify-end mt-4">
<x-jet-button class="ml-4">
{{ __('Confirm') }}
</x-jet-button>
</div>
</form>
</x-jet-authentication-card>
</x-guest-layout>
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600">
{{ __('Forgot your password? No problem. Just let us know your email address and we will email you a password reset link that will allow you to choose a new one.') }}
</div>
@if (session('status'))
<div class="mb-4 font-medium text-sm text-green-600">
{{ session('status') }}
</div>
@endif
<x-jet-validation-errors class="mb-4" />
<form method="POST" action="{{ route('password.email') }}">
@csrf
<div class="block">
<x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required autofocus />
</div>
<div class="flex items-center justify-end mt-4">
<x-jet-button>
{{ __('Email Password Reset Link') }}
</x-jet-button>
</div>
</form>
</x-jet-authentication-card>
</x-guest-layout>
@extends('layouts.app')
@section('contents') <!doctype html>
<div class="home-btn d-none d-sm-block"> <html lang="en">
<a href="index.html" class="text-dark"><i class="fas fa-home h2"></i></a>
</div> <head>
<div class="account-pages my-5 pt-5">
<meta charset="utf-8">
<title>Login | SIM PKM UNESA</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta content="Premium Multipurpose Admin & Dashboard Template" name="description">
<meta content="Themesbrand" name="author">
<!-- App favicon -->
<link rel="shortcut icon" href="{{ asset('theme/images/favicon.ico') }}">
<!-- Bootstrap Css -->
<link href="{{ asset('theme/css/bootstrap.min.css') }}" id="bootstrap-style" rel="stylesheet" type="text/css">
<!-- Icons Css -->
<link href="{{ asset('theme/css/icons.min.css') }}" rel="stylesheet" type="text/css">
<!-- App Css-->
<link href="{{ asset('theme/css/app.min.css') }}" id="app-style" rel="stylesheet" type="text/css">
</head>
<body>
<div class="account-pages my-5 pt-5">
<div class="container"> <div class="container">
<div class="row justify-content-center"> <div class="row justify-content-center">
<div class="col-md-8 col-lg-6 col-xl-4"> <div class="col-md-8 col-lg-6 col-xl-4">
<div class="card overflow-hidden"> <div class="card overflow-hidden">
<div class="bg-primary"> <div class="bg-primary">
<div class="text-primary text-center p-4"> <div class="text-primary text-center p-4">
<h5 class="text-white font-size-20">Welcome Back !</h5> <h5 class="text-white font-size-20">LOGIN</h5>
<p class="text-white-50">Sign in to continue to SIMPKM.</p> <p class="text-white-50">Sistem Informasi PKM.</p>
<a href="index.html" class="logo logo-admin"> <a href="index.html" class="logo logo-admin">
<img src="{{ asset('theme/images/logo-sm.png') }}" height="24" alt="logo"> <img src="assets/images/logo-sm.png" height="24" alt="logo">
</a> </a>
</div> </div>
</div> </div>
<div class="card-body p-4"> <div class="card-body p-4">
<div class="p-3"> <div class="p-3">
<form class="mt-4" action="{{ route('login') }}"> <form method="POST" action="{{ route('login') }}">
@csrf
<div class="mb-3"> <div class="mb-3">
<label class="form-label" for="username">Username</label> <label class="form-label" for="email">Email</label>
<input type="text" class="form-control" name="username" id="username" placeholder="Enter username"> <input class="form-control" id="email" type="email" name="email" :value="old('email')" required autofocus>
@error('username')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div> </div>
<div class="mb-3"> <div class="mb-3">
<label class="form-label" for="password">Password</label> <label class="form-label" for="userpassword">Password</label>
<input type="password" class="form-control" name="password" id="password" placeholder="Enter password"> <input class="form-control" id="password" type="password" name="password" required autocomplete="current-password">
@error('password')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div> </div>
<div class="mb-3 row"> <div class="mb-3 row">
<div class="col-sm-6"> <div class="col-sm-6">
</div> </div>
<div class="col-sm-6 text-end"> <div class="col-sm-6 text-end">
<button class="btn btn-primary w-md waves-effect waves-light" type="submit">Log In</button> <button class="btn btn-primary w-md waves-effect waves-light" type="submit">Log In</button>
</div> </div>
</div> </div>
</form> </form>
</div> </div>
...@@ -58,8 +67,25 @@ ...@@ -58,8 +67,25 @@
</div> </div>
<div class="mt-5 text-center">
<p class="mb-0">© <script>document.write(new Date().getFullYear())</script> SIM PKM. Crafted with <i class="mdi mdi-heart text-danger"></i> by PPTI</p>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
@endsection
<!-- JAVASCRIPT -->
<script src="{{ asset('theme/libs/jquery/jquery.min.js') }}"></script>
<script src="{{ asset('theme/libs/bootstrap/js/bootstrap.bundle.min.js') }}"></script>
<script src="{{ asset('theme/libs/metismenu/metisMenu.min.js') }}"></script>
<script src="{{ asset('theme/libs/simplebar/simplebar.min.js') }}"></script>
<script src="{{ asset('theme/libs/node-waves/waves.min.js') }}"></script>
<script src="{{ asset('theme/js/app.js') }}"></script>
</body>
</html>
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<x-jet-validation-errors class="mb-4" />
@if (session('status'))
<div class="mb-4 font-medium text-sm text-green-600">
{{ session('status') }}
</div>
@endif
<form method="POST" action="{{ route('login') }}">
@csrf
<div>
<x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required autofocus />
</div>
<div class="mt-4">
<x-jet-label for="password" value="{{ __('Password') }}" />
<x-jet-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="current-password" />
</div>
<div class="block mt-4">
<label for="remember_me" class="flex items-center">
<x-jet-checkbox id="remember_me" name="remember" />
<span class="ml-2 text-sm text-gray-600">{{ __('Remember me') }}</span>
</label>
</div>
<div class="flex items-center justify-end mt-4">
@if (Route::has('password.request'))
<a class="underline text-sm text-gray-600 hover:text-gray-900" href="{{ route('password.request') }}">
{{ __('Forgot your password?') }}
</a>
@endif
<x-jet-button class="ml-4">
{{ __('Log in') }}
</x-jet-button>
</div>
</form>
</x-jet-authentication-card>
</x-guest-layout>
@extends('layouts.app') <x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
@section('content') <x-jet-validation-errors class="mb-4" />
<div class="container">
<div class="row justify-content-center">
<div class="col-md-8">
<div class="card">
<div class="card-header">{{ __('Register') }}</div>
<div class="card-body">
<form method="POST" action="{{ route('register') }}"> <form method="POST" action="{{ route('register') }}">
@csrf @csrf
<div class="row mb-3"> <div>
<label for="name" class="col-md-4 col-form-label text-md-end">{{ __('Name') }}</label> <x-jet-label for="name" value="{{ __('Name') }}" />
<x-jet-input id="name" class="block mt-1 w-full" type="text" name="name" :value="old('name')" required autofocus autocomplete="name" />
<div class="col-md-6">
<input id="name" type="text" class="form-control @error('name') is-invalid @enderror" name="name" value="{{ old('name') }}" required autocomplete="name" autofocus>
@error('name')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div> </div>
</div>
<div class="row mb-3">
<label for="email" class="col-md-4 col-form-label text-md-end">{{ __('Email Address') }}</label>
<div class="col-md-6"> <div class="mt-4">
<input id="email" type="email" class="form-control @error('email') is-invalid @enderror" name="email" value="{{ old('email') }}" required autocomplete="email"> <x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required />
@error('email')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div>
</div> </div>
<div class="row mb-3"> <div class="mt-4">
<label for="password" class="col-md-4 col-form-label text-md-end">{{ __('Password') }}</label> <x-jet-label for="password" value="{{ __('Password') }}" />
<x-jet-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="new-password" />
<div class="col-md-6">
<input id="password" type="password" class="form-control @error('password') is-invalid @enderror" name="password" required autocomplete="new-password">
@error('password')
<span class="invalid-feedback" role="alert">
<strong>{{ $message }}</strong>
</span>
@enderror
</div> </div>
<div class="mt-4">
<x-jet-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-jet-input id="password_confirmation" class="block mt-1 w-full" type="password" name="password_confirmation" required autocomplete="new-password" />
</div> </div>
<div class="row mb-3"> @if (Laravel\Jetstream\Jetstream::hasTermsAndPrivacyPolicyFeature())
<label for="password-confirm" class="col-md-4 col-form-label text-md-end">{{ __('Confirm Password') }}</label> <div class="mt-4">
<x-jet-label for="terms">
<div class="flex items-center">
<x-jet-checkbox name="terms" id="terms"/>
<div class="col-md-6"> <div class="ml-2">
<input id="password-confirm" type="password" class="form-control" name="password_confirmation" required autocomplete="new-password"> {!! __('I agree to the :terms_of_service and :privacy_policy', [
'terms_of_service' => '<a target="_blank" href="'.route('terms.show').'" class="underline text-sm text-gray-600 hover:text-gray-900">'.__('Terms of Service').'</a>',
'privacy_policy' => '<a target="_blank" href="'.route('policy.show').'" class="underline text-sm text-gray-600 hover:text-gray-900">'.__('Privacy Policy').'</a>',
]) !!}
</div>
</div> </div>
</x-jet-label>
</div> </div>
@endif
<div class="row mb-0"> <div class="flex items-center justify-end mt-4">
<div class="col-md-6 offset-md-4"> <a class="underline text-sm text-gray-600 hover:text-gray-900" href="{{ route('login') }}">
<button type="submit" class="btn btn-primary"> {{ __('Already registered?') }}
</a>
<x-jet-button class="ml-4">
{{ __('Register') }} {{ __('Register') }}
</button> </x-jet-button>
</div>
</div> </div>
</form> </form>
</div> </x-jet-authentication-card>
</div> </x-guest-layout>
</div>
</div>
</div>
@endsection
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<x-jet-validation-errors class="mb-4" />
<form method="POST" action="{{ route('password.update') }}">
@csrf
<input type="hidden" name="token" value="{{ $request->route('token') }}">
<div class="block">
<x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email', $request->email)" required autofocus />
</div>
<div class="mt-4">
<x-jet-label for="password" value="{{ __('Password') }}" />
<x-jet-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="new-password" />
</div>
<div class="mt-4">
<x-jet-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-jet-input id="password_confirmation" class="block mt-1 w-full" type="password" name="password_confirmation" required autocomplete="new-password" />
</div>
<div class="flex items-center justify-end mt-4">
<x-jet-button>
{{ __('Reset Password') }}
</x-jet-button>
</div>
</form>
</x-jet-authentication-card>
</x-guest-layout>
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<div x-data="{ recovery: false }">
<div class="mb-4 text-sm text-gray-600" x-show="! recovery">
{{ __('Please confirm access to your account by entering the authentication code provided by your authenticator application.') }}
</div>
<div class="mb-4 text-sm text-gray-600" x-show="recovery">
{{ __('Please confirm access to your account by entering one of your emergency recovery codes.') }}
</div>
<x-jet-validation-errors class="mb-4" />
<form method="POST" action="{{ route('two-factor.login') }}">
@csrf
<div class="mt-4" x-show="! recovery">
<x-jet-label for="code" value="{{ __('Code') }}" />
<x-jet-input id="code" class="block mt-1 w-full" type="text" inputmode="numeric" name="code" autofocus x-ref="code" autocomplete="one-time-code" />
</div>
<div class="mt-4" x-show="recovery">
<x-jet-label for="recovery_code" value="{{ __('Recovery Code') }}" />
<x-jet-input id="recovery_code" class="block mt-1 w-full" type="text" name="recovery_code" x-ref="recovery_code" autocomplete="one-time-code" />
</div>
<div class="flex items-center justify-end mt-4">
<button type="button" class="text-sm text-gray-600 hover:text-gray-900 underline cursor-pointer"
x-show="! recovery"
x-on:click="
recovery = true;
$nextTick(() => { $refs.recovery_code.focus() })
">
{{ __('Use a recovery code') }}
</button>
<button type="button" class="text-sm text-gray-600 hover:text-gray-900 underline cursor-pointer"
x-show="recovery"
x-on:click="
recovery = false;
$nextTick(() => { $refs.code.focus() })
">
{{ __('Use an authentication code') }}
</button>
<x-jet-button class="ml-4">
{{ __('Log in') }}
</x-jet-button>
</div>
</form>
</div>
</x-jet-authentication-card>
</x-guest-layout>
<x-guest-layout>
<x-jet-authentication-card>
<x-slot name="logo">
<x-jet-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600">
{{ __('Before continuing, could you verify your email address by clicking on the link we just emailed to you? If you didn\'t receive the email, we will gladly send you another.') }}
</div>
@if (session('status') == 'verification-link-sent')
<div class="mb-4 font-medium text-sm text-green-600">
{{ __('A new verification link has been sent to the email address you provided in your profile settings.') }}
</div>
@endif
<div class="mt-4 flex items-center justify-between">
<form method="POST" action="{{ route('verification.send') }}">
@csrf
<div>
<x-jet-button type="submit">
{{ __('Resend Verification Email') }}
</x-jet-button>
</div>
</form>
<div>
<a
href="{{ route('profile.show') }}"
class="underline text-sm text-gray-600 hover:text-gray-900"
>
{{ __('Edit Profile') }}</a>
<form method="POST" action="{{ route('logout') }}" class="inline">
@csrf
<button type="submit" class="underline text-sm text-gray-600 hover:text-gray-900 ml-2">
{{ __('Log Out') }}
</button>
</form>
</div>
</div>
</x-jet-authentication-card>
</x-guest-layout>
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-xl-4 col-md-6">
<div class="card directory-card">
<div class="card-body">
<div class="d-flex">
<div class="flex-shrink-0">
@if (Auth::user()->roles->first()->name != 'mahasiswa')
<img src="https://siakadu.unesa.ac.id/photo/fotomhs/{{ $biodata->noidentitas }}.jpg" alt="" class="img-fluid img-thumbnail rounded-circle avatar-lg">
@else
<img src="https://siakadu.unesa.ac.id/photo/{{ $biodata->noidentitas }}.jpg" alt="" class="img-fluid img-thumbnail rounded-circle avatar-lg">
@endif
</div>
<div class="flex-grow-1 ms-3">
<h5 class="text-primary font-size-18 mb-1">{{ $biodata->name }}</h5>
<p class="font-size-12 mb-2">{{ $biodata->noidentitas }}</p>
<p class="mb-0">{{ $biodata->email }}</p>
</div>
</div>
<hr>
<p class="mb-0"><b>Fakultas : </b> {{ $biodata->fakultas }}</p>
<p class="mb-0"><b>Program Studi : </b> {{ $biodata->prodi }} </p>
</div>
</div>
</div>
</div>
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.kelompok.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Dosen</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="row col-mb-3">
<label class="col-sm-1 col-form-label">Tahun : </label>
<div class="col-sm-2">
<select class="form-select">
<option value="2021">2021</option>
<option value="2022">2022</option>
<option value="2023">2023</option>
</select>
</div>
</div><br>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Ketua</th>
<th>NIM</th>
<th>Dosen Pembimbing</th>
<th>NIDN</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($kelompok as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->kode }}</td>
<td>{{ $item->rAnggota->where('status_ketua', 1)->count() > 0 ? $item->rAnggota->where('status_ketua', 1)[0]->nama : '' }}</td>
<td>{{ $item->rAnggota->where('status_ketua', 1)->count() > 0 ? $item->rAnggota->where('status_ketua', 1)[0]->nim : ''}}</td>
<td>{{ $item->nama_dosen }}</td>
<td>{{ $item->nidn_dosen }}</td>
<td>
@if(!is_null($item->kirim))
@if($item->status == 0)
<span class="badge bg-danger">Menunggu Persetujuan Dosen</span>
@else
<span class="badge bg-success">Sudah Disetujui Dosen</span>
@endif
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->kelompok_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->kelompok_id)) }}" class="btn btn-info btn-sm"><i class="far fa-eye"></i> Lihat</button>
@if($item->status == 0)
<a onclick="setuju('{{ encrypt($item->kelompok_id) }}', 'row-{{ $token }}')" class="btn btn-success btn-sm"><i class="fas fa-check"></i> Setuju</a>
<a onclick="tolak('{{ encrypt($item->kelompok_id) }}', 'row-{{ $token }}')" class="btn btn-danger btn-sm"><i class="fas fa-times"></i> Tolak</a>
@endif
@if((auth()->user()->id == $item->created_user) && ($item->status == 0))
<a href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->kelompok_id)) }}" class="btn btn-warning btn-sm">Edit</a>
<a onclick="hapus('{{ encrypt($item->kelompok_id) }}', 'row-{{ $token }}')" class="btn btn-danger btn-sm">Hapus</a>
@endif
<div id="{{ 'lihat'.$item->kelompok_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Data Kelompok </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table table-striped mb-0">
<thead>
<tr>
<th>No</th>
<th>Nama</th>
<th>NIM</th>
<th>Fakultas</th>
<th>Program Studi</th>
<th>Keterangan</th>
</tr>
</thead>
<tbody>
<tr>
@foreach ($item->rAnggota as $value)
<tr>
<td>{{ $loop->iteration }}</td>
<td>{{ $value->nama }}</td>
<td>{{ $value->nim }}</td>
<td>{{ $value->fakultas }}</td>
<td>{{ $value->prodi }}</td>
<td>
@if($value->status_ketua == 1)
Ketua
@else
Anggota {{ $loop->iteration-1 }}
@endif
</td>
</tr>
@endforeach
</tr>
</tbody>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
<div id="tmbhKel" class="modal fade" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<form action="{{ route('mahasiswa.kelompok.store') }}" method="POST">
@csrf
<div class="modal-header">
<h5 class="modal-title" id="myModalLabel">Tambah Kelompok Baru</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<div class="col-12">
<h5 class="font-size-16">Silahkan pilih dosen pembimbing : </h5>
<p>
<input type="hidden" name="periode" value="{{ $periode['periode_id'] }}" >
<select class="form-select" style="width: 100%" id="selectmodal" name="dosen">
<option selected>Pilih Dosen</option>
@foreach($dosen as $item)
<option value="{{ encrypt($item['id_sdm'].'_'.$item['nm_sdm'].'_'.$item['nidn']) }}">{{ $item['nm_sdm'].' - '.$item['prodi']}}</option>
@endforeach
</select>
</p>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary waves-effect" data-bs-dismiss="modal">Close</button>
<button type="submit" class="btn btn-primary waves-effect waves-light">Save changes</button>
</div>
</form>
</div>
<!-- /.modal-content -->
</div>
<!-- /.modal-dialog -->
</div>
@endsection
@section('js')
<script src="{{ asset('theme/js/pages/datatables.init.js') }}"></script>
<script>
$(document).ready(function() {
$("#selectmodal").select2({
dropdownParent: $("#tmbhKel")
});
});
function setuju(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menyetujui Kelompok ini?',
text: "Kelompok yang di setujui akan di teruskan untuk upload proposal",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('dosen.kelompok.terima') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
position: 'top-center',
icon: 'success',
title: 'Kelompok berhasil di setujui',
showConfirmButton: false,
timer: 1500
});
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
function tolak(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menolak kelompok ini?',
text: "Kelompok yang tidak di setujui tidak bisa untuk upload proposal",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('dosen.kelompok.tolak') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
position: 'top-center',
icon: 'success',
title: 'Kelompok berhasil di tolak',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td> <a data-bs-toggle="modal" data-bs-target="#uploadRev" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a> </td>
<td> <a data-bs-toggle="modal" data-bs-target="#uploadRev" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a> </td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<span class="badge bg-danger">Belum upload Logbook</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<span class="badge bg-danger">Belum upload laporan Kemajuan File</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-success btn-sm"> Lihat Hasil Penilaian</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<span class="badge bg-danger">Belum upload Logbook</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<span class="badge bg-danger">Belum upload Laporan Kemajuan File</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-success btn-sm">Lihat Hasil Penilaian</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Laporan Akhir</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<span class="badge bg-danger">Belum upload Logbook</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<span class="badge bg-danger">Belum upload Laporan Kemajuan File</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_akhir_file))
<span class="badge bg-danger">Belum upload Laporan Akhir File</span>
@else
<a href="https://statik.unesa.ac.id/simpkm/akhir/{{ $item->rPeriode->nama }}/{{ $item->laporan_akhir_file }}" target="_blank" title="Laporan Akhir" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-success btn-sm">Lihat Hasil Penilaian</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->upload_dokumen))
<span class="badge bg-danger">Belum Upload Proposal</span> <br>
<strong> Keterangan : </strong> <br>
Upload proposal pada : -<br>
Disetujui proposal pada : -<br>
@if($item->status == '1')
<span class="badge bg-success">Sudah Disetujui Dosen</span> <br>
<strong> Keterangan : </strong> <br>
Upload proposal pada : <h6 class="text-primary"> {{ $item->date_upload }} </h6>
Disetujui proposal pada : <h6 class="text-primary"> {{ $item->date_approval }} </h6>
@else
<span class="badge bg-warning">Menunggu Persetujuan Dosen</span> <br>
<strong> Keterangan : </strong> <br>
Upload proposal pada : <h6 class="text-primary"> {{ $item->date_upload }} </h6>
Disetujui proposal pada :
@endif
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm"><i class="far fa-eye"></i> Lihat</button>
@if($item->upload_dokumen)
<a onclick="setuju('{{ encrypt($item->proposal_id) }}', 'row-{{ $token }}')" class="btn btn-success btn-sm"><i class="fas fa-check"></i> Setuju</a>
@endif
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Menunggu Persetujuan Dosen</span>
@else
<span class="badge bg-success">Sudah Disetujui Dosen</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td>
@if($item->upload_dokumen)
<iframe id="view-pdf" width="100%" height="400px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe>
@else
<div class="alert alert-danger alert-dismissible fade show mb-0" role="alert">
<strong>Informasi!</strong><br/> File tidak ditemukan.
</div>
@endif
</td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script src="{{ asset('theme/js/pages/datatables.init.js') }}"></script>
<script>
function setuju(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menyetujui Kelompok ini?',
text: "Kelompok yang di setujui akan di teruskan untuk upload proposal",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('dosen.proposal.setuju') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
position: 'top-center',
icon: 'success',
title: 'Kelompok berhasil di setujui',
showConfirmButton: false,
timer: 1500
});
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->status))
<span class="badge bg-success">Lolos Seleksi Internal</span>
@else
<span class="badge bg-danger">Tidak Lolos Seleksi Internal</span>
@endif
</td>
<td>
@if(is_null($item->revisi_filebelmawa))
<span class="badge bg-danger">Belum Upload Proposal</span>
@else
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
@endif
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/revisi/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
<div id="uploadRev" class="modal fade" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<form action="{{ route('mahasiswa.kelompok.store') }}" method="POST">
@csrf
<div class="modal-header">
<h5 class="modal-title" id="myModalLabel">Tambah Kelompok Baru</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<div class="col-12">
<h5 class="font-size-16">Silahkan pilih dosen pembimbing : </h5>
<p>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<br/>
<iframe id="view-pdf" width="100%" height="320px" src="" frameborder="0"></iframe>
</div>
</div>
</p>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary waves-effect" data-bs-dismiss="modal">Close</button>
<button type="submit" class="btn btn-primary waves-effect waves-light">Save changes</button>
</div>
</form>
</div>
<!-- /.modal-content -->
</div>
<!-- /.modal-dialog -->
</div>
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$("#uploadRev iframe").attr("src", url);
})
})
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<form action="{{ route('mahasiswa.proposal.store') }}" method="POST" enctype="multipart/form-data">
@csrf
<h4 class="card-title">{!! $title !!}</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<label for="kode" class="col-sm-2 col-form-label">Judul</label>
<div class="col-sm-10">
<input class="form-control" type="text" id="judul" name="judul" required>
<input class="form-control" type="hidden" id="kode_kelompok" name="kode_kelompok" value="{{ $kelompok->kelompok_id }}" >
<input class="form-control" type="hidden" id="periode_id" name="periode_id" value="{{ $periode->periode_id }}" >
</div>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Jenis PKM</label>
<div class="col-sm-10">
<select class="form-select select2" name="jenis">
<option selected>Pilih Jenis</option>
@foreach($jenis as $item => $pkm)
<option value="{{ $item }}">{{ $pkm }}</option>
@endforeach
</select>
</div>
</div>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<iframe id="view-pdf" width="80%" height="80%" src="" frameborder="0"></iframe>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1"> Submit </button>
<button type="reset" class="btn btn-secondary waves-effect"> Cancel </button>
</div>
</div>
</form>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$('#view-pdf').attr('src',url);
$('#view-pdf').attr('height','500px');
})
})
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
@php
$menu = 'dashboard';
@endphp
<!-- start page title -->
<div class="page-title-box">
</div>
<!-- end page title -->
<div class="row">
<div class="col-lg-12">
<div class="card">
<div class="card-body">
<center>
<h1 class="display-5">Selamat Datang di SIM PKM </h1>
<h1 class="display-6 text-primary">(Sistem Informasi Manajemen Program Kreativitas Mahasiswa )</h1>
<h1 class="display-7 text-warning">Universitas Negeri Surabaya</h1>
</center>
</div>
</div>
</div>
<div class="col-lg-12">
<div class="card">
<div class="card-body">
<h4 class="card-title">Pengumuman :</h4>
<h5> </h5>
</div>
</div>
</div>
</div>
@endsection
@section('js')
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-xl-4 col-md-6">
<div class="card directory-card">
<div class="card-body">
<div class="d-flex">
<div class="flex-shrink-0">
@if (Auth::user()->roles->first()->name != 'mahasiswa')
<img src="https://siakadu.unesa.ac.id/photo/fotomhs/{{ $biodata->noidentitas }}.jpg" alt="" class="img-fluid img-thumbnail rounded-circle avatar-lg">
@else
<img src="https://siakadu.unesa.ac.id/photo/{{ $biodata->noidentitas }}.jpg" alt="" class="img-fluid img-thumbnail rounded-circle avatar-lg">
@endif
</div>
<div class="flex-grow-1 ms-3">
<h5 class="text-primary font-size-18 mb-1">{{ $biodata->name }}</h5>
<p class="font-size-12 mb-2">{{ $biodata->noidentitas }}</p>
<p class="mb-0">{{ $biodata->email }}</p>
</div>
</div>
<hr>
<p class="mb-0"><b>Fakultas : </b> {{ $biodata->fakultas }}</p>
<p class="mb-0"><b>Program Studi : </b> {{ $biodata->prodi }} </p>
</div>
</div>
</div>
</div>
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.kelompok.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<form action="{{ route('mahasiswa.kelompok.store') }}" method="POST">
@csrf
<h4 class="card-title">Kelompok Baru</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<label for="kode" class="col-sm-2 col-form-label">Kode Kelompok</label>
<div class="col-sm-10">
<input class="form-control" type="text" id="kode" name="kode" value="{{ $kode }}" disabled>
<input type="hidden" name="kode" value="{{ $kode }}">
<input type="hidden" name="periode" value="{{ $periode['periode_id'] }}" >
</div>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Dosen Pembimbing</label>
<div class="col-sm-10">
<select class="form-select select2" name="dosen">
<option selected>Pilih Dosen</option>
@foreach($dosen as $item)
<option value="{{ encrypt($item['id_sdm'].'_'.$item['nm_sdm'].'_'.$item['nidn']) }}">{{ $item['nm_sdm'].' - '.$item['prodi']}}</option>
@endforeach
</select>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1">
Submit
</button>
<button type="reset" class="btn btn-secondary waves-effect">
Cancel
</button>
</div>
</div>
</form>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-lg-12">
<div class="card">
<div class="card-body">
<div class="row">
<div class="col-10">
<h4 class="card-title">Dosen Pembimbing</h4>
</div>
</div>
<br/>
<table class="table table-hover table-centered table-nowrap mb-0">
<tbody>
<tr class="table-light">
<td>Kode Kelompok</td>
<td>NIDN Dosen</td>
<td>Dosen Pembimbing</td>
</tr>
<tr>
<td>{{ $kelompok->kode }}</td>
<td>{{ $kelompok->nidn_dosen }}</td>
<td>{{ $kelompok->nama_dosen }}</td>
</tr>
</tbody>
</table>
<br/>
<div class="row">
<div class="col-10">
<h4 class="card-title">Anggota Kelompok</h4>
</div>
<div class="col-2">
<a href="{{ URL::to('mahasiswa/anggota/create') }}" class="btn btn-info btn-sm">Tambah Anggota</a>
</div>
</div>
<br/>
<table class="table table-hover table-centered table-nowrap mb-0">
<thead>
<tr class="table-light">
<td>No</td>
<td>Nama</td>
<td>NIM</td>
<td>Fakultas</td>
<td>Program Studi</td>
<td>Keterangan</td>
<td></td>
</tr>
<thead>
<tbody>
@foreach ($kelompok->rAnggota as $item)
<tr>
<td>{{ $loop->iteration }}</td>
<td>{{ $item->nama }}</td>
<td>{{ $item->nim }}</td>
<td>{{ $item->fakultas }}</td>
<td>{{ $item->prodi }}</td>
<td>
@if($item->status_ketua == 1)
Ketua
@else
Anggota {{ $loop->iteration-1 }}
@endif
</td>
<td></td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div>
{{ Form::open(['url' => route('mahasiswa.kelompok.kirim'), 'method' => 'post', 'id' => 'addKelompok']) }}
{!! Form::hidden('kelompok_id', $kelompok->kelompok_id) !!}
{{ Form::close() }}
<div class="col-lg-12">
<div class="card">
<div class="card-body">
<div class="mb-0">
@if($kelompok->rAnggota->count() >= 3)
<button type="submit" class="btn btn-primary waves-effect waves-light me-1 btnSimpanKelompok" id="btnSimpanKelompok"> Submit </button>
@endif
<a href="{{ URL::to('mahasiswa/kelompok') }}" type="reset" class="btn btn-secondary waves-effect"> Kembali </a>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
@endsection
@section('js')
<script>
$(".btnSimpanKelompok").click(function (e) {
e.preventDefault();
$(".btnSimpanKelompok").hide();
$("#andou").html("<h3>Sedang proses ... </h3>");
$("#addKelompok").submit();
});
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
@if($cekKel == 0)
<button type="button" class="btn btn-primary waves-effect waves-light" data-bs-toggle="modal" data-bs-target="#tmbhKel">Tambah Data</button>
@endif
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Ketua</th>
<th>NIM</th>
<th>Dosen Pembimbing</th>
<th>NIDN</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($kelompok as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->kode }}</td>
<td>{{ $item->rAnggota->where('status_ketua', 1)->count() > 0 ? $item->rAnggota->where('status_ketua', 1)[0]->nama : '' }}</td>
<td>{{ $item->rAnggota->where('status_ketua', 1)->count() > 0 ? $item->rAnggota->where('status_ketua', 1)[0]->nim : ''}}</td>
<td>{{ $item->nama_dosen }}</td>
<td>{{ $item->nidn_dosen }}</td>
<td>
@if(!is_null($item->kirim))
@if($item->status == 0)
<span class="badge bg-danger">Menunggu Persetujuan Dosen</span>
@else
<span class="badge bg-success">Sudah Disetujui Dosen</span>
@endif
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->kelompok_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->kelompok_id)) }}" class="btn btn-info btn-sm">Lihat</button>
@if((auth()->user()->id == $item->created_user) && ($item->status == 0))
<a href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->kelompok_id)) }}" class="btn btn-warning btn-sm">Edit</a>
<a onclick="hapus('{{ encrypt($item->kelompok_id) }}', 'row-{{ $token }}')" class="btn btn-danger btn-sm">Hapus</a>
@endif
<div id="{{ 'lihat'.$item->kelompok_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Data Kelompok </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table table-striped mb-0">
<thead>
<tr>
<th>No</th>
<th>Nama</th>
<th>NIM</th>
<th>Fakultas</th>
<th>Program Studi</th>
<th>Keterangan</th>
</tr>
</thead>
<tbody>
<tr>
@foreach ($item->rAnggota as $value)
<tr>
<td>{{ $loop->iteration }}</td>
<td>{{ $value->nama }}</td>
<td>{{ $value->nim }}</td>
<td>{{ $value->fakultas }}</td>
<td>{{ $value->prodi }}</td>
<td>
@if($value->status_ketua == 1)
Ketua
@else
Anggota {{ $loop->iteration-1 }}
@endif
</td>
</tr>
@endforeach
</tr>
</tbody>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
<div id="tmbhKel" class="modal fade" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<form action="{{ route('mahasiswa.kelompok.store') }}" method="POST">
@csrf
<div class="modal-header">
<h5 class="modal-title" id="myModalLabel">Tambah Kelompok Baru</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<div class="col-12">
<h5 class="font-size-16">Silahkan pilih dosen pembimbing : </h5>
<p>
<input type="hidden" name="periode" value="{{ $periode['periode_id'] }}" >
<select class="form-select" style="width: 100%" id="selectmodal" name="dosen">
<option selected>Pilih Dosen</option>
@foreach($dosen as $item)
<option value="{{ encrypt($item['id_sdm'].'_'.$item['nm_sdm'].'_'.$item['nidn']) }}">{{ $item['nm_sdm'].' - '.$item['prodi']}}</option>
@endforeach
</select>
</p>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary waves-effect" data-bs-dismiss="modal">Close</button>
<button type="submit" class="btn btn-primary waves-effect waves-light">Save changes</button>
</div>
</form>
</div>
<!-- /.modal-content -->
</div>
<!-- /.modal-dialog -->
</div>
@endsection
@section('js')
<script>
$(document).ready(function() {
$("#selectmodal").select2({
dropdownParent: $("#tmbhKel")
});
});
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.kelompok.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<h4 class="card-title">Anggota Kelompok</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<label for="kode" class="col-sm-2 col-form-label">NIM</label>
<div class="col-sm-4">
<div class="input-group">
<input class="form-control" type="text" id="nim" name="txCari" placeholder="NIM" onkeypress="return hanyaAngka(event)">
<span class="input-group-btn" id="btn-addon2">
<button id="btnCari" class="btn btn-warning" onclick="carianggota();">
<i class="fa fa-search"></i>
</button>
</span>
</div>
</div>
</div>
<div id="viewPersonil">
<div class="row mb-3">
<label for="nama" class="col-sm-2 col-form-label">Nama</label>
<div class="col-sm-10">
<span id="nama"> - </span>
</div>
</div>
<div class="row mb-3">
<label for="fakultas" class="col-sm-2 col-form-label">Fakultas</label>
<div class="col-sm-10">
<span id="fakultas"> - </span>
</div>
</div>
<div class="row mb-3">
<label for="prodi" class="col-sm-2 col-form-label">Program Studi</label>
<div class="col-sm-10">
<span id="prodi"> - </span>
</div>
</div>
</div>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
<meta name="csrf_token" content="{{ csrf_token() }}" />
@endsection
@section('js')
<script>
var urlPerson = "{{url('/selectmahasiswa')}}";
</script>
{{Html::script('js/person.js')}}
@endsection
<div id="viewPersonil">
<div class="row mb-3">
<label for="nama" class="col-sm-2 col-form-label">Nama</label>
<div class="col-sm-10">
<span id="nama"> - </span>
</div>
</div>
<div class="row mb-3">
<label for="fakultas" class="col-sm-2 col-form-label">Fakultas</label>
<div class="col-sm-10">
<span id="fakultas"> - </span>
</div>
</div>
<div class="row mb-3">
<label for="prodi" class="col-sm-2 col-form-label">Program Studi</label>
<div class="col-sm-10">
<span id="prodi"> - </span>
</div>
</div>
<div class="alert alert-danger mb-0" role="alert">
<strong>Informasi!</strong> Data tidak di temukan
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
</div>
</div>
<div id="viewPersonil">
<div class="row mb-3">
<label for="nama" class="col-sm-2 col-form-label">Nama</label>
<div class="col-sm-10">
<span id="nama"> {{ $person['nm_pengguna'] }} </span>
</div>
</div>
<div class="row mb-3">
<label for="fakultas" class="col-sm-2 col-form-label">Fakultas</label>
<div class="col-sm-10">
<span id="fakultas"> {{ $person['nama_fakultas'] }} </span>
</div>
</div>
<div class="row mb-3">
<label for="prodi" class="col-sm-2 col-form-label">Program Studi</label>
<div class="col-sm-10">
<span id="prodi"> {{ $person['nama_prodi'] }} </span>
</div>
</div>
</div>
{{ Form::open(['url' => route('mahasiswa.anggota.store'), 'method' => 'post', 'id' => 'addPersonil']) }}
{!! Form::hidden('kelompok_id', $kelompok->kelompok_id) !!}
{!! Form::hidden('id_reg_pd', $person['id_pengguna']) !!}
{!! Form::hidden('nim', $person['username']) !!}
{!! Form::hidden('nama', $person['nm_pengguna']) !!}
{!! Form::hidden('fakultas', $person['nama_fakultas']) !!}
{!! Form::hidden('prodi', $person['nama_prodi']) !!}
{!! Form::hidden('status_ketua', '2') !!}
{{ Form::close() }}
<div class="mb-0">
<div>
<button type="button" class="btn btn-primary waves-effect waves-light me-1 btnSimpanPersonil" id="btnSimpanPersonil"> Submit </button>
<a id="btnBatal" class="btn btn-secondary waves-effect" href="{{ url()->previous() }}"> Cancel </a>
</div>
</div>
{{Html::script('js/person.js')}}
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td> <a data-bs-toggle="modal" data-bs-target="#uploadRev" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a> </td>
<td> <a data-bs-toggle="modal" data-bs-target="#uploadRev" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a> </td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">Monev</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__logbook__satu')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__kemajuan__satu')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">Monev</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__logbook__dua')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__kemajuan__dua')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">Monev</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<div class="alert alert-success alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
<strong>Informasi!</strong> Monev Internal II dilaksanakan pada : <strong>Tanggal 20 Maret 2022.</strong>
</div>
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Catatan Harian (Logbook)</th>
<th>Laporan Kemajuan</th>
<th>Laporan Akhir</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->logbook_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__logbook__tiga')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/logbook/{{ $item->rPeriode->nama }}/{{ $item->logbook_file }}" target="_blank" title="Logbook" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_kemajuan_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__kemajuan__tiga')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/kemajuan/{{ $item->rPeriode->nama }}/{{ $item->laporan_kemajuan_file }}" target="_blank" title="Laporan Kemajuan" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
@if(is_null($item->laporan_akhir_file))
<a href="{{ URL::to('mahasiswa/monev-revisi/'.encrypt($item->proposal_id.'__akhir__tiga')) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-file-upload"></i> Upload</a>
@else
<a href="https://statik.unesa.ac.id/simpkm/akhir/{{ $item->rPeriode->nama }}/{{ $item->laporan_akhir_file }}" target="_blank" title="Laporan Akhir" class="btn btn-info btn-sm waves-effect waves-light"> <i class="fas fa-search"></i> Lihat</a>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">Monev</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<form action="{{ route('mahasiswa.monev-revisi-upload') }}" method="POST" enctype="multipart/form-data">
@csrf
<h4 class="card-title">{!! $title !!}</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<input class="form-control" type="hidden" id="proposal_id" name="proposal_id" value="{{ $proposal->proposal_id }}" >
<input class="form-control" type="hidden" id="type" name="type" value="{{ $type }}" >
<input class="form-control" type="hidden" id="monev" name="monev" value="{{ $monev }}" >
<label for="kode" class="col-sm-2 col-form-label">Judul</label>
<label class="col-sm-10 col-form-label">{{ $proposal->judul }}</label>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Jenis PKM</label>
<label class="col-sm-10 col-form-label">{{ $proposal->rJenis->nama }}</label>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Komentar Review</label>
<label class="col-sm-10 col-form-label"></label>
</div>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Revisi Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<iframe id="view-pdf" width="80%" height="80%" src="" frameborder="0"></iframe>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1"> Submit </button>
<button type="reset" class="btn btn-secondary waves-effect"> Cancel </button>
</div>
</div>
</form>
<br>
<h6 class="text-danger">* PASTIKAN FILE PROPOSAL SUDAH BENAR SEBELUM DISUBMIT</h6>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$('#view-pdf').attr('src',url);
$('#view-pdf').attr('height','500px');
})
})
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
@if ($proposal)
{!! Form::model($proposal, ['route' => ['mahasiswa.proposal.update', $proposal->proposal_id], 'method'=>'patch', 'files' => 'true', 'enctype'=>'multipart/form-data']) !!}
@else
{{ Form::open(['url' => route('mahasiswa.proposal.store'), 'method' => 'post', 'id' => 'proposal', 'files' => 'true', 'enctype'=>'multipart/form-data']) }}
@endif
@csrf
<h4 class="card-title">{!! $title !!}</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<label for="kode" class="col-sm-2 col-form-label">Judul</label>
<div class="col-sm-10">
<input class="form-control" type="text" id="judul" name="judul" value="{{ $proposal ? $proposal->judul : '' }}"required>
<input class="form-control" type="hidden" id="kode_kelompok" name="kode_kelompok" value="{{ $proposal ? $proposal->kelompok_id : $kelompok->kelompok_id }}" >
<input class="form-control" type="hidden" id="periode_id" name="periode_id" value="{{ $proposal ? $proposal->periode_id : $periode->periode_id }}" >
</div>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Jenis PKM</label>
<div class="col-sm-10">
<select class="form-select select2" name="jenis">
<option selected>Pilih Jenis</option>
@foreach($jenis as $item => $pkm)
<option value="{{ $item }}" {{ $proposal->jenis_id == $item ? 'selected' : '' }}>{{ $pkm }}</option>
@endforeach
</select>
</div>
</div>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<iframe id="view-pdf" width="80%" height="80%" frameborder="0" src="{{ $proposal ? 'https://statik.unesa.ac.id/simpkm/proposal/'.$proposal->rPeriode->nama.'/'.$proposal->upload_dokumen : '' }} "></iframe>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1"> Submit </button>
<button type="reset" class="btn btn-secondary waves-effect"> Cancel </button>
</div>
</div>
{{ Form::close() }}
<br>
<h6 class="text-danger">* PASTIKAN FILE PROPOSAL SUDAH BENAR SEBELUM DISUBMIT</h6>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$('#view-pdf').attr('src',url);
$('#view-pdf').attr('height','500px');
})
})
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<a href="{{ URL::to('mahasiswa/proposal/create') }}" type="button" class="btn btn-primary waves-effect waves-light"> <i class="fas fa-plus-circle"></i> Tambah Data</a>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Menunggu Persetujuan Dosen</span>
@else
<span class="badge bg-success">Sudah Disetujui Dosen</span>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
@if(is_null($item->status))
<a href="{{ URL::to('mahasiswa/proposal/'.encrypt($item->proposal_id).'/edit') }}" class="btn btn-warning btn-sm">Revisi</a>
<a onclick="hapus('{{ encrypt($item->proposal_id) }}', 'row-{{ $token }}')" class="btn btn-danger btn-sm">Hapus</a>
@endif
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Menunggu Persetujuan Dosen</span>
@else
<span class="badge bg-success">Sudah Disetujui Dosen</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td>
@if($item->upload_dokumen)
<iframe id="view-pdf" width="100%" height="400px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe>
@else
<div class="alert alert-danger alert-dismissible fade show mb-0" role="alert">
<strong>Informasi!</strong> File tidak ditemukan.
</div>
@endif
</td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus usulan ini?',
text: "file yang sudah terupload juga terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->status))
<span class="badge bg-success">Lolos Seleksi Internal</span>
@else
<span class="badge bg-danger">Tidak Lolos Seleksi Internal</span>
@endif
</td>
<td>
@if(is_null($item->revisi_filebelmawa))
<a href="{{ URL::to('mahasiswa/seleksi-belmawa/revisi', $item->proposal_id) }}" type="button" class="btn btn-warning btn-sm waves-effect waves-light"> <i class="fas fa-edit"></i> Edit</a>
@else
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
@endif
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal Seleksi Belmawa</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-success">Lolos Seleksi Internal</span>
@else
<span class="badge bg-danger">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/revisi/{{ $item->rPeriode->nama }}/{{ $item->revisi_filebelmawa }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$("#uploadRev iframe").attr("src", url);
})
})
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<table id="datatable" class="table table-bordered dt-responsive nowrap" style="border-collapse: collapse; border-spacing: 0; width: 100%;">
<thead>
<tr>
<th>No</th>
<th>Kode Kelompok</th>
<th>Identitas Ketua</th>
<th>Identitas Dosen Pembimbing</th>
<th>Jenis PKM</th>
<th>Judul Proposal</th>
<th>Status</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($proposal as $item)
@php $token = Str::random(30); @endphp
<tr id="row-{{ $token }}">
<td>{{ $loop->iteration }}</td>
<td>{{ $item->rKelompok->kode }}</td>
<td>{{ $item->rKelompok->rBiodata->name }} <br> {{ $item->rKelompok->rBiodata->noidentitas }} <br> {{ $item->rKelompok->rBiodata->fakultas }} <br> {{ $item->rKelompok->rBiodata->prodi }}</td>
<td>{{ $item->rKelompok->nama_dosen }} <br> {{ $item->rKelompok->nidn_dosen }}</td>
<td>{{ $item->rJenis->nama }}</td>
<td>{{ $item->judul }}</td>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
<td>
<button data-bs-toggle="modal" data-bs-target="{{ '#lihat'.$item->proposal_id }}" href="{{ URL::to('mahasiswa/kelompok-new', encrypt($item->proposal_id)) }}" class="btn btn-info btn-sm">Lihat</button>
<div id="{{ 'lihat'.$item->proposal_id }}" class="modal fade" tabindex="-1" role="dialog"
aria-labelledby="lihatLabel" aria-hidden="true">
<div class="modal-dialog modal-xl">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="lihatLabel">Detail Proposal </h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<p>
<div class="table-responsive">
<table class="table mb-0">
<tr>
<th>Judul Proposal</th>
<td>{{ $item->judul }}</td>
</tr>
<tr>
<th>Jenis PKM</th>
<td>{{ $item->rJenis->nama }}</td>
</tr>
<tr>
<th>Status</th>
<td>
@if(is_null($item->status))
<span class="badge bg-danger">Lolos Seleksi Internal</span>
@else
<span class="badge bg-success">Tidak Lolos Seleksi Internal</span>
@endif
</td>
</tr>
<tr>
<th>Proposal</th>
<td> <iframe id="view-pdf" width="100%" height="200px" src="https://statik.unesa.ac.id/simpkm/proposal/{{ $item->rPeriode->nama }}/{{ $item->upload_dokumen }}" frameborder="0"></iframe></td>
</tr>
<tr>
<th>Komentar</th>
<td> </td>
</tr>
</table>
</div>
</p>
</div>
</div>
</div>
</div>
</div>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
function hapus(id, rowId){
Swal.fire({
title: 'Apakah anda yakin untuk menghapus Kelompok?',
text: "Semua anggota kelompok juga akan terhapus",
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'OK',
}).then((result) => {
if (result.isConfirmed) {
var token = '{{ csrf_token() }}';
var request = $.ajax({
url: '{{ route('mahasiswa.proposal.hapus') }}',
type: 'POST',
dataType: 'html',
data: {id:id, _token:token},
success: function(data){
Swal.fire({
title: 'Data Berhasil Di Hapus',
icon: 'success',
showConfirmButton: false,
timer: 1500
});
$('#'+rowId).remove();
},
error: function(xhr, status, error){
Swal.fire({
position: 'top-end',
icon: 'error',
title: xhr.responseText,
showConfirmButton: false,
timer: 3500
});
}
});
}
})
}
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<form action="{{ route('mahasiswa.proposal.store') }}" method="POST" enctype="multipart/form-data">
@csrf
<h4 class="card-title">{!! $title !!}</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<label for="kode" class="col-sm-2 col-form-label">Judul</label>
<div class="col-sm-10">
<input class="form-control" type="text" id="judul" name="judul" required>
<input class="form-control" type="hidden" id="kode_kelompok" name="kode_kelompok" value="{{ $kelompok->kelompok_id }}" >
<input class="form-control" type="hidden" id="periode_id" name="periode_id" value="{{ $periode->periode_id }}" >
</div>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Jenis PKM</label>
<div class="col-sm-10">
<select class="form-select select2" name="jenis">
<option selected>Pilih Jenis</option>
@foreach($jenis as $item => $pkm)
<option value="{{ $item }}">{{ $pkm }}</option>
@endforeach
</select>
</div>
</div>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<iframe id="view-pdf" width="80%" height="80%" src="" frameborder="0"></iframe>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1"> Submit </button>
<button type="reset" class="btn btn-secondary waves-effect"> Cancel </button>
</div>
</div>
</form>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$('#view-pdf').attr('src',url);
$('#view-pdf').attr('height','500px');
})
})
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">{!! $title !!}</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item">Mahasiswa</li>
<li class="breadcrumb-item">Seleksi Belmawa</li>
<li class="breadcrumb-item">{!! $title !!}</li>
</ol>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-12">
<div class="card">
<div class="card-body">
<form action="{{ route('mahasiswa.seleksi-belmawa-upload') }}" method="POST" enctype="multipart/form-data">
@csrf
<h4 class="card-title">{!! $title !!}</h4>
<p class="card-title-desc"></p>
<div class="row mb-3">
<input class="form-control" type="hidden" id="proposal_id" name="proposal_id" value="{{ $proposal->proposal_id }}" >
<label for="kode" class="col-sm-2 col-form-label">Judul</label>
<label class="col-sm-10 col-form-label">{{ $proposal->judul }}</label>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Jenis PKM</label>
<label class="col-sm-10 col-form-label">{{ $proposal->rJenis->nama }}</label>
</div>
<div class=" row mb-3">
<label class="col-sm-2 col-form-label">Komentar Review</label>
<label class="col-sm-10 col-form-label"></label>
</div>
<div class="row mb-3" class="dropzone">
<label for="kode" class="col-sm-2 col-form-label">Upload Revisi Proposal</label>
<div class="col-sm-10">
<input type="file" name="file" class="form-control" id="input-file">
<iframe id="view-pdf" width="80%" height="80%" src="" frameborder="0"></iframe>
</div>
</div>
<div class="mb-0">
<div>
<button type="submit" class="btn btn-primary waves-effect waves-light me-1"> Submit </button>
<button type="reset" class="btn btn-secondary waves-effect"> Cancel </button>
</div>
</div>
</form>
<br>
<h6 class="text-danger">* PASTIKAN FILE PROPOSAL SUDAH BENAR SEBELUM DISUBMIT</h6>
</div>
</div>
</div> <!-- end col -->
</div> <!-- end row -->
@endsection
@section('js')
<script>
$(function(){
$('#input-file').change(function(){
var input = this;
var url = window.URL.createObjectURL(this.files[0]);
$('#view-pdf').attr('src',url);
$('#view-pdf').attr('height','500px');
})
})
</script>
@endsection
@extends('layouts.master')
@section('title')
Dashboard
@endsection
@section('header')
<div class="page-title">
<h3>Dashboard</h3>
</div>
@endsection
@section('contents')
@php
$menu = 'dashboard';
@endphp
<!-- start page title -->
<div class="page-title-box">
<div class="row align-items-center">
<div class="col-md-8">
<h6 class="page-title">Dashboard</h6>
<ol class="breadcrumb m-0">
<li class="breadcrumb-item active">Welcome to Veltrix Dashboard</li>
</ol>
</div>
<div class="col-md-4">
<div class="float-end d-none d-md-block">
<div class="dropdown">
<button class="btn btn-primary dropdown-toggle" type="button" id="dropdownMenuButton" data-bs-toggle="dropdown" aria-expanded="false">
<i class="mdi mdi-cog me-2"></i> Settings
</button>
<div class="dropdown-menu dropdown-menu-end">
<a class="dropdown-item" href="#">Action</a>
<a class="dropdown-item" href="#">Another action</a>
<a class="dropdown-item" href="#">Something else here</a>
<div class="dropdown-divider"></div>
<a class="dropdown-item" href="#">Separated link</a>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- end page title -->
<div class="row">
<div class="col-xl-3 col-md-6">
<div class="card mini-stat bg-primary text-white">
<div class="card-body">
<div class="mb-4">
<div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/01.png') }}" alt="">
</div>
<h5 class="font-size-16 text-uppercase text-white-50">Orders</h5>
<h4 class="fw-medium font-size-24">1,685 <i
class="mdi mdi-arrow-up text-success ms-2"></i></h4>
<div class="mini-stat-label bg-success">
<p class="mb-0">+ 12%</p>
</div>
</div>
<div class="pt-2">
<div class="float-end">
<a href="#" class="text-white-50"><i class="mdi mdi-arrow-right h5"></i></a>
</div>
<p class="text-white-50 mb-0 mt-1">Since last month</p>
</div>
</div>
</div>
</div>
<div class="col-xl-3 col-md-6">
<div class="card mini-stat bg-primary text-white">
<div class="card-body">
<div class="mb-4">
<div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/02.png') }}" alt="">
</div>
<h5 class="font-size-16 text-uppercase text-white-50">Revenue</h5>
<h4 class="fw-medium font-size-24">52,368 <i
class="mdi mdi-arrow-down text-danger ms-2"></i></h4>
<div class="mini-stat-label bg-danger">
<p class="mb-0">- 28%</p>
</div>
</div>
<div class="pt-2">
<div class="float-end">
<a href="#" class="text-white-50"><i class="mdi mdi-arrow-right h5"></i></a>
</div>
<p class="text-white-50 mb-0 mt-1">Since last month</p>
</div>
</div>
</div>
</div>
<div class="col-xl-3 col-md-6">
<div class="card mini-stat bg-primary text-white">
<div class="card-body">
<div class="mb-4">
<div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/03.png') }}" alt="">
</div>
<h5 class="font-size-16 text-uppercase text-white-50">Average Price</h5>
<h4 class="fw-medium font-size-24">15.8 <i
class="mdi mdi-arrow-up text-success ms-2"></i></h4>
<div class="mini-stat-label bg-info">
<p class="mb-0"> 00%</p>
</div>
</div>
<div class="pt-2">
<div class="float-end">
<a href="#" class="text-white-50"><i class="mdi mdi-arrow-right h5"></i></a>
</div>
<p class="text-white-50 mb-0 mt-1">Since last month</p>
</div>
</div>
</div>
</div>
<div class="col-xl-3 col-md-6">
<div class="card mini-stat bg-primary text-white">
<div class="card-body">
<div class="mb-4">
<div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/04.png') }}" alt="">
</div>
<h5 class="font-size-16 text-uppercase text-white-50">Product Sold</h5>
<h4 class="fw-medium font-size-24">2436 <i
class="mdi mdi-arrow-up text-success ms-2"></i></h4>
<div class="mini-stat-label bg-warning">
<p class="mb-0">+ 84%</p>
</div>
</div>
<div class="pt-2">
<div class="float-end">
<a href="#" class="text-white-50"><i class="mdi mdi-arrow-right h5"></i></a>
</div>
<p class="text-white-50 mb-0 mt-1">Since last month</p>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
<div class="row">
<div class="col-xl-9">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Monthly Earning</h4>
<div class="row">
<div class="col-lg-7">
<div>
<div id="chart-with-area" class="ct-chart earning ct-golden-section">
</div>
</div>
</div>
<div class="col-lg-5">
<div class="row">
<div class="col-md-6">
<div class="text-center">
<p class="text-muted mb-4">This month</p>
<h3>$34,252</h3>
<p class="text-muted mb-5">It will be as simple as in fact it
will be occidental.</p>
<span class="peity-donut"
data-peity='{ "fill": ["#02a499", "#f2f2f2"], "innerRadius": 28, "radius": 32 }'
data-width="72" data-height="72">4/5</span>
</div>
</div>
<div class="col-md-6">
<div class="text-center">
<p class="text-muted mb-4">Last month</p>
<h3>$36,253</h3>
<p class="text-muted mb-5">It will be as simple as in fact it
will be occidental.</p>
<span class="peity-donut"
data-peity='{ "fill": ["#02a499", "#f2f2f2"], "innerRadius": 28, "radius": 32 }'
data-width="72" data-height="72">3/5</span>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
</div>
</div>
<!-- end card -->
</div>
<div class="col-xl-3">
<div class="card">
<div class="card-body">
<div>
<h4 class="card-title mb-4">Sales Analytics</h4>
</div>
<div class="wid-peity mb-4">
<div class="row">
<div class="col-md-6">
<div>
<p class="text-muted">Online</p>
<h5 class="mb-4">1,542</h5>
</div>
</div>
<div class="col-md-6">
<div class="mb-4">
<span class="peity-line" data-width="100%"
data-peity='{ "fill": ["rgba(2, 164, 153,0.3)"],"stroke": ["rgba(2, 164, 153,0.8)"]}'
data-height="60">6,2,8,4,3,8,1,3,6,5,9,2,8,1,4,8,9,8,2,1</span>
</div>
</div>
</div>
</div>
<div class="wid-peity mb-4">
<div class="row">
<div class="col-md-6">
<div>
<p class="text-muted">Offline</p>
<h5 class="mb-4">6,451</h5>
</div>
</div>
<div class="col-md-6">
<div class="mb-4">
<span class="peity-line" data-width="100%"
data-peity='{ "fill": ["rgba(2, 164, 153,0.3)"],"stroke": ["rgba(2, 164, 153,0.8)"]}'
data-height="60">6,2,8,4,-3,8,1,-3,6,-5,9,2,-8,1,4,8,9,8,2,1</span>
</div>
</div>
</div>
</div>
<div class="">
<div class="row">
<div class="col-md-6">
<div>
<p class="text-muted">Marketing</p>
<h5>84,574</h5>
</div>
</div>
<div class="col-md-6">
<div class="mb-4">
<span class="peity-line" data-width="100%"
data-peity='{ "fill": ["rgba(2, 164, 153,0.3)"],"stroke": ["rgba(2, 164, 153,0.8)"]}'
data-height="60">6,2,8,4,3,8,1,3,6,5,9,2,8,1,4,8,9,8,2,1</span>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
<div class="row">
<div class="col-xl-3">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Sales Report</h4>
<div class="cleafix">
<p class="float-start"><i class="mdi mdi-calendar me-1 text-primary"></i> Jan 01
- Jan 31</p>
<h5 class="font-18 text-end">$4230</h5>
</div>
<div id="ct-donut" class="ct-chart wid"></div>
<div class="mt-4">
<table class="table mb-0">
<tbody>
<tr>
<td><span class="badge bg-primary">Desk</span></td>
<td>Desktop</td>
<td class="text-end">54.5%</td>
</tr>
<tr>
<td><span class="badge bg-success">Mob</span></td>
<td>Mobile</td>
<td class="text-end">28.0%</td>
</tr>
<tr>
<td><span class="badge bg-warning">Tab</span></td>
<td>Tablets</td>
<td class="text-end">17.5%</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
<div class="col-xl-4">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Activity</h4>
<ol class="activity-feed">
<li class="feed-item">
<div class="feed-item-list">
<span class="date">Jan 22</span>
<span class="activity-text">Responded to need “Volunteer
Activities”</span>
</div>
</li>
<li class="feed-item">
<div class="feed-item-list">
<span class="date">Jan 20</span>
<span class="activity-text">At vero eos et accusamus et iusto odio
dignissimos ducimus qui deleniti atque...<a href="#"
class="text-success">Read more</a></span>
</div>
</li>
<li class="feed-item">
<div class="feed-item-list">
<span class="date">Jan 19</span>
<span class="activity-text">Joined the group “Boardsmanship
Forum”</span>
</div>
</li>
<li class="feed-item">
<div class="feed-item-list">
<span class="date">Jan 17</span>
<span class="activity-text">Responded to need “In-Kind
Opportunity”</span>
</div>
</li>
<li class="feed-item">
<div class="feed-item-list">
<span class="date">Jan 16</span>
<span class="activity-text">Sed ut perspiciatis unde omnis iste natus
error sit rem.</span>
</div>
</li>
</ol>
<div class="text-center">
<a href="#" class="btn btn-primary">Load More</a>
</div>
</div>
</div>
</div>
<div class="col-xl-5">
<div class="row">
<div class="col-md-6">
<div class="card text-center">
<div class="card-body">
<div class="py-4">
<i
class="ion ion-ios-checkmark-circle-outline display-4 text-success"></i>
<h5 class="text-primary mt-4">Order Successful</h5>
<p class="text-muted">Thanks you so much for your order.</p>
<div class="mt-4">
<a href="" class="btn btn-primary btn-sm">Chack Status</a>
</div>
</div>
</div>
</div>
</div>
<div class="col-md-6">
<div class="card bg-primary">
<div class="card-body">
<div class="text-center text-white py-4">
<h5 class="mb-4 text-white-50 font-size-16">Top Product Sale</h5>
<h1>1452</h1>
<p class="font-size-14 pt-1">Computer</p>
<p class="text-white-50 mb-0">At solmen va esser necessi far uniform
myth... <a href="#" class="text-white">View more</a></p>
</div>
</div>
</div>
</div>
</div>
<div class="row">
<div class="col-md-12">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Client Reviews</h4>
<p class="text-muted mb-3 pb-4">" Everyone realizes why a new common
language would be desirable one could refuse to pay expensive
translators it would be necessary. "</p>
<div class="float-end mt-2">
<a href="#" class="text-primary">
<i class="mdi mdi-arrow-right h5"></i>
</a>
</div>
<h6 class="mb-0"><img src="{{ asset('theme/images/users/user-3.jpg') }}" alt=""
class="avatar-sm rounded-circle me-2"> James Athey</h6>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
<div class="row">
<div class="col-xl-8">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Latest Transaction</h4>
<div class="table-responsive">
<table class="table table-hover table-centered table-nowrap mb-0">
<thead>
<tr>
<th scope="col">(#) Id</th>
<th scope="col">Name</th>
<th scope="col">Date</th>
<th scope="col">Amount</th>
<th scope="col" colspan="2">Status</th>
</tr>
</thead>
<tbody>
<tr>
<th scope="row">#14256</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-2.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> Philip Smead
</div>
</td>
<td>15/1/2018</td>
<td>$94</td>
<td><span class="badge bg-success">Delivered</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
<tr>
<th scope="row">#14257</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-3.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> Brent Shipley
</div>
</td>
<td>16/1/2019</td>
<td>$112</td>
<td><span class="badge bg-warning">Pending</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
<tr>
<th scope="row">#14258</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-4.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> Robert Sitton
</div>
</td>
<td>17/1/2019</td>
<td>$116</td>
<td><span class="badge bg-success">Delivered</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
<tr>
<th scope="row">#14259</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-5.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> Alberto Jackson
</div>
</td>
<td>18/1/2019</td>
<td>$109</td>
<td><span class="badge bg-danger">Cancel</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
<tr>
<th scope="row">#14260</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-6.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> David Sanchez
</div>
</td>
<td>19/1/2019</td>
<td>$120</td>
<td><span class="badge bg-success">Delivered</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
<tr>
<th scope="row">#14261</th>
<td>
<div>
<img src="{{ asset('theme/images/users/user-2.jpg') }}" alt=""
class="avatar-xs rounded-circle me-2"> Philip Smead
</div>
</td>
<td>15/1/2018</td>
<td>$94</td>
<td><span class="badge bg-warning">Pending</span></td>
<td>
<div>
<a href="#" class="btn btn-primary btn-sm">Edit</a>
</div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
<div class="col-xl-4">
<div class="card">
<div class="card-body">
<h4 class="card-title mb-4">Chat</h4>
<div class="chat-conversation">
<ul class="conversation-list" data-simplebar style="max-height: 367px;">
<li class="clearfix">
<div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-2.jpg') }}"
class="avatar-xs rounded-circle" alt="male">
<span class="time">10:00</span>
</div>
<div class="conversation-text">
<div class="ctext-wrap">
<span class="user-name">John Deo</span>
<p>
Hello!
</p>
</div>
</div>
</li>
<li class="clearfix odd">
<div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}"
class="avatar-xs rounded-circle" alt="Female">
<span class="time">10:01</span>
</div>
<div class="conversation-text">
<div class="ctext-wrap">
<span class="user-name">Smith</span>
<p>
Hi, How are you? What about our next meeting?
</p>
</div>
</div>
</li>
<li class="clearfix">
<div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-2.jpg') }}"
class="avatar-xs rounded-circle" alt="male">
<span class="time">10:04</span>
</div>
<div class="conversation-text">
<div class="ctext-wrap">
<span class="user-name">John Deo</span>
<p>
Yeah everything is fine
</p>
</div>
</div>
</li>
<li class="clearfix odd">
<div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}"
class="avatar-xs rounded-circle" alt="male">
<span class="time">10:05</span>
</div>
<div class="conversation-text">
<div class="ctext-wrap">
<span class="user-name">Smith</span>
<p>
Wow that's great
</p>
</div>
</div>
</li>
<li class="clearfix odd">
<div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}"
class="avatar-xs rounded-circle" alt="male">
<span class="time">10:08</span>
</div>
<div class="conversation-text">
<div class="ctext-wrap">
<span class="user-name mb-2">Smith</span>
<img src="{{ asset('theme/images/small/img-1.jpg') }}" alt="" height="48"
class="rounded me-2">
<img src="{{ asset('theme/images/small/img-2.jpg') }}" alt="" height="48"
class="rounded">
</div>
</div>
</li>
</ul>
<div class="row">
<div class="col-sm-9 col-8 chat-inputbar">
<input type="text" class="form-control chat-input"
placeholder="Enter your text">
</div>
<div class="col-sm-3 col-4 chat-send">
<div class="d-grid">
<button type="submit" class="btn btn-success">Send</button>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- end row -->
@endsection
@section('js')
@endsection
<!doctype html> <!DOCTYPE html>
<html lang="en"> <html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head> <head>
<meta charset="utf-8"> <meta charset="utf-8">
<title>Login | Veltrix - Admin & Dashboard Template</title> <meta name="viewport" content="width=device-width, initial-scale=1">
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="csrf-token" content="{{ csrf_token() }}">
<meta content="Premium Multipurpose Admin & Dashboard Template" name="description">
<meta content="Themesbrand" name="author">
<!-- App favicon -->
<link rel="shortcut icon" href="{{ asset('theme/images/favicon.ico') }}">
<!-- Bootstrap Css -->
<link href="{{ asset('theme/css/bootstrap.min.css') }}" id="bootstrap-style" rel="stylesheet" type="text/css">
<!-- Icons Css -->
<link href="{{ asset('theme/css/icons.min.css') }}" rel="stylesheet" type="text/css">
<!-- App Css-->
<link href="{{ asset('theme/css/app.min.css') }}" id="app-style" rel="stylesheet" type="text/css">
</head> <title>{{ config('app.name', 'Laravel') }}</title>
<body> <!-- Fonts -->
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Nunito:wght@400;600;700&display=swap">
@yield('contents') <!-- Styles -->
@livewireStyles
<!-- JAVASCRIPT --> <!-- Scripts -->
<script src="{{ asset('theme/libs/jquery/jquery.min.js') }}"></script> @vite(['resources/css/app.css', 'resources/js/app.js'])
<script src="{{ asset('theme/libs/bootstrap/js/bootstrap.bundle.min.js') }}"></script> </head>
<script src="{{ asset('theme/libs/metismenu/metisMenu.min.js') }}"></script> <body class="font-sans antialiased">
<script src="{{ asset('theme/libs/simplebar/simplebar.min.js') }}"></script> <x-jet-banner />
<script src="{{ asset('theme/libs/node-waves/waves.min.js') }}"></script>
<div class="min-h-screen bg-gray-100">
<script src="{{ asset('theme/js/app.js') }}"></script> @livewire('navigation-menu')
</body>
<!-- Page Heading -->
@if (isset($header))
<header class="bg-white shadow">
<div class="max-w-7xl mx-auto py-6 px-4 sm:px-6 lg:px-8">
{{ $header }}
</div>
</header>
@endif
<!-- Page Content -->
<main>
{{ $slot }}
</main>
</div>
@stack('modals')
@livewireScripts
</body>
</html> </html>
<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<meta name="csrf-token" content="{{ csrf_token() }}">
<title>{{ config('app.name', 'Laravel') }}</title>
<!-- Fonts -->
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Nunito:wght@400;600;700&display=swap">
<!-- Scripts -->
@vite(['resources/css/app.css', 'resources/js/app.js'])
</head>
<body>
<div class="font-sans text-gray-900 antialiased">
{{ $slot }}
</div>
</body>
</html>
...@@ -4,10 +4,17 @@ ...@@ -4,10 +4,17 @@
<head> <head>
<meta charset="utf-8"> <meta charset="utf-8">
<title>Dashboard | Veltrix - Admin & Dashboard Template</title> <meta name="universitas-negeri-surabaya" content="custom" />
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="viewport" content="width=device-width, initial-scale=1">
<meta content="Premium Multipurpose Admin & Dashboard Template" name="description"> <meta name="description" content="Sistem Informasi Merdeka Belajar Kampus Merdeka">
<meta content="Themesbrand" name="author"> <meta name="author" content="PPTI Unesa Surabaya">
<meta name="keywords" content="sistem, informasi, merdekabelajar, kkn, magang, plp, unesa, inbound, outbound">
<meta name="language" content="id">
<meta name="geo.region" content="ID" />
<meta name="geo.position" content="-7.300818;112.672689">
<meta name="geo.placename" content="Surabaya">
<meta name="geo.region" content="Indonesia">
<title>SIM PKM UNESA | Sistem Informasi Manajemen Program Kreativitas Mahasiswa</title>
<!-- App favicon --> <!-- App favicon -->
<link rel="shortcut icon" href="{{ asset('theme/images/favicon.ico') }}"> <link rel="shortcut icon" href="{{ asset('theme/images/favicon.ico') }}">
...@@ -37,6 +44,8 @@ ...@@ -37,6 +44,8 @@
<!-- Daterangepicker--> <!-- Daterangepicker-->
<link rel="stylesheet" type="text/css" href="{{ asset('theme/libs/bootstrap-daterangepicker/daterangepicker.css') }}" /> <link rel="stylesheet" type="text/css" href="{{ asset('theme/libs/bootstrap-daterangepicker/daterangepicker.css') }}" />
<!-- Plugins css -->
<link href="{{ asset('theme/libs/dropzone/min/dropzone.min.css') }}" rel="stylesheet" type="text/css">
<link href="{{ asset('theme/libs/select2/css/select2.min.css') }}" rel="stylesheet" type="text/css"> <link href="{{ asset('theme/libs/select2/css/select2.min.css') }}" rel="stylesheet" type="text/css">
......
...@@ -9,6 +9,8 @@ ...@@ -9,6 +9,8 @@
<script src="{{ asset('theme/libs/simplebar/simplebar.min.js') }}"></script> <script src="{{ asset('theme/libs/simplebar/simplebar.min.js') }}"></script>
<script src="{{ asset('theme/libs/node-waves/waves.min.js') }}"></script> <script src="{{ asset('theme/libs/node-waves/waves.min.js') }}"></script>
<script src="{{ asset('theme/libs/dropzone/min/dropzone.min.js') }}"></script>
<!-- Peity chart--> <!-- Peity chart-->
<script src="{{ asset('theme/libs/peity/jquery.peity.min.js') }}"></script> <script src="{{ asset('theme/libs/peity/jquery.peity.min.js') }}"></script>
...@@ -35,6 +37,8 @@ ...@@ -35,6 +37,8 @@
<script src="{{ asset('theme/libs/datatables.net-responsive/js/dataTables.responsive.min.js') }}"></script> <script src="{{ asset('theme/libs/datatables.net-responsive/js/dataTables.responsive.min.js') }}"></script>
<script src="{{ asset('theme/libs/datatables.net-responsive-bs4/js/responsive.bootstrap4.min.js') }}"></script> <script src="{{ asset('theme/libs/datatables.net-responsive-bs4/js/responsive.bootstrap4.min.js') }}"></script>
<script src="{{ asset('theme/js/pages/form-advanced.init.js') }}"></script>
{{-- <script src="{{ asset('theme/js/sweetalert.min.js') }}"></script> --}} {{-- <script src="{{ asset('theme/js/sweetalert.min.js') }}"></script> --}}
<script src="{{ asset('theme/libs/sweetalert2/sweetalert2.min.js') }}"></script> <script src="{{ asset('theme/libs/sweetalert2/sweetalert2.min.js') }}"></script>
<script src="{{ asset('theme/libs/inputmask/min/jquery.inputmask.bundle.min.js') }}"></script> <script src="{{ asset('theme/libs/inputmask/min/jquery.inputmask.bundle.min.js') }}"></script>
......
...@@ -12,21 +12,13 @@ ...@@ -12,21 +12,13 @@
<div class="d-flex"> <div class="d-flex">
<!-- LOGO --> <!-- LOGO -->
<div class="navbar-brand-box"> <div class="navbar-brand-box">
<a href="index.html" class="logo logo-dark">
<span class="logo-sm">
<img src="{{ asset('theme/images/logo-sm.png') }}" alt="" height="22">
</span>
<span class="logo-lg">
<img src="{{ asset('theme/images/logo-dark.png') }}" alt="" height="17">
</span>
</a>
<a href="index.html" class="logo logo-light"> <a href="index.html" class="logo logo-light">
<span class="logo-sm"> <span class="logo-sm">
<img src="{{ asset('theme/images/logo-sm.png') }}" alt="" height="22"> <img src="{{ asset('theme/images/logo-sm.png') }}" alt="" height="22">
</span> </span>
<span class="logo-lg"> <span class="logo-lg">
<img src="{{ asset('theme/images/logo-light.png') }}" alt="" height="18"> <img src="{{ asset('theme/images/logo-light.png') }}" alt="" height="44">
</span> </span>
</a> </a>
</div> </div>
...@@ -34,230 +26,38 @@ ...@@ -34,230 +26,38 @@
<button type="button" class="btn btn-sm px-3 font-size-24 header-item waves-effect" id="vertical-menu-btn"> <button type="button" class="btn btn-sm px-3 font-size-24 header-item waves-effect" id="vertical-menu-btn">
<i class="mdi mdi-menu"></i> <i class="mdi mdi-menu"></i>
</button> </button>
<div class="d-none d-sm-block">
<div class="dropdown pt-3 d-inline-block">
<a class="btn btn-secondary dropdown-toggle" href="#" role="button" id="dropdownMenuLink" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Create <i class="mdi mdi-chevron-down"></i>
</a>
<div class="dropdown-menu" aria-labelledby="dropdownMenuLink">
<a class="dropdown-item" href="#">Action</a>
<a class="dropdown-item" href="#">Another action</a>
<a class="dropdown-item" href="#">Something else here</a>
<div class="dropdown-divider"></div>
<a class="dropdown-item" href="#">Separated link</a>
</div>
</div>
</div>
</div>
<div class="d-flex">
<!-- App Search-->
<form class="app-search d-none d-lg-block">
<div class="position-relative">
<input type="text" class="form-control" placeholder="Search...">
<span class="fa fa-search"></span>
</div>
</form>
<div class="dropdown d-inline-block d-lg-none ms-2">
<button type="button" class="btn header-item noti-icon waves-effect" id="page-header-search-dropdown"
data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<i class="mdi mdi-magnify"></i>
</button>
<div class="dropdown-menu dropdown-menu-lg dropdown-menu-end p-0"
aria-labelledby="page-header-search-dropdown">
<form class="p-3">
<div class="form-group m-0">
<div class="input-group">
<input type="text" class="form-control" placeholder="Search ..." aria-label="Recipient's username">
<div class="input-group-append">
<button class="btn btn-primary" type="submit"><i class="mdi mdi-magnify"></i></button>
</div>
</div>
</div>
</form>
</div>
</div>
<div class="dropdown d-none d-md-block ms-2">
<button type="button" class="btn header-item waves-effect"
data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<img class="me-2" src="{{ asset('theme/images/flags/us_flag.jpg') }}" alt="Header Language" height="16"> English <span class="mdi mdi-chevron-down"></span>
</button>
<div class="dropdown-menu dropdown-menu-end">
<!-- item-->
<a href="javascript:void(0);" class="dropdown-item notify-item">
<img src="{{ asset('theme/images/flags/germany_flag.jpg') }}" alt="user-image" class="me-1" height="12"> <span class="align-middle"> German </span>
</a>
<!-- item-->
<a href="javascript:void(0);" class="dropdown-item notify-item">
<img src="{{ asset('theme/images/flags/italy_flag.jpg') }}" alt="user-image" class="me-1" height="12"> <span class="align-middle"> Italian </span>
</a>
<!-- item-->
<a href="javascript:void(0);" class="dropdown-item notify-item">
<img src="{{ asset('theme/images/flags/french_flag.jpg') }}" alt="user-image" class="me-1" height="12"> <span class="align-middle"> French </span>
</a>
<!-- item-->
<a href="javascript:void(0);" class="dropdown-item notify-item">
<img src="{{ asset('theme/images/flags/spain_flag.jpg') }}" alt="user-image" class="me-1" height="12"> <span class="align-middle"> Spanish </span>
</a>
<!-- item-->
<a href="javascript:void(0);" class="dropdown-item notify-item">
<img src="{{ asset('theme/images/flags/russia_flag.jpg') }}" alt="user-image" class="me-1" height="12"> <span class="align-middle"> Russian </span>
</a>
</div>
</div>
<div class="dropdown d-none d-lg-inline-block"> <div class="dropdown d-none d-lg-inline-block">
<button type="button" class="btn header-item noti-icon waves-effect" data-bs-toggle="fullscreen"> <button type="button" class="btn header-item noti-icon waves-effect" data-bs-toggle="fullscreen">
<i class="mdi mdi-fullscreen"></i> <i class="mdi mdi-fullscreen"></i>
</button> </button>
</div> </div>
<div class="dropdown d-inline-block">
<button type="button" class="btn header-item noti-icon waves-effect" id="page-header-notifications-dropdown"
data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<i class="mdi mdi-bell-outline"></i>
<span class="badge bg-danger rounded-pill">3</span>
</button>
<div class="dropdown-menu dropdown-menu-lg dropdown-menu-end p-0" aria-labelledby="page-header-notifications-dropdown">
<div class="p-3">
<div class="row align-items-center">
<div class="col">
<h5 class="m-0 font-size-16"> Notifications (258) </h5>
</div>
</div>
</div>
<div data-simplebar style="max-height: 230px;">
<a href="" class="text-reset notification-item">
<div class="d-flex">
<div class="flex-shrink-0 me-3">
<div class="avatar-xs">
<span class="avatar-title bg-success rounded-circle font-size-16">
<i class="mdi mdi-cart-outline"></i>
</span>
</div>
</div>
<div class="flex-grow-1">
<h6 class="mb-1">Your order is placed</h6>
<div class="font-size-12 text-muted">
<p class="mb-1">Dummy text of the printing and typesetting industry.</p>
</div>
</div>
</div>
</a>
<a href="" class="text-reset notification-item">
<div class="d-flex">
<div class="flex-shrink-0 me-3">
<div class="avatar-xs">
<span class="avatar-title bg-warning rounded-circle font-size-16">
<i class="mdi mdi-message-text-outline"></i>
</span>
</div>
</div> </div>
<div class="flex-grow-1">
<h6 class="mb-1">New Message received</h6>
<div class="font-size-12 text-muted">
<p class="mb-1">You have 87 unread messages</p>
</div>
</div>
</div>
</a>
<a href="" class="text-reset notification-item">
<div class="d-flex"> <div class="d-flex">
<div class="flex-shrink-0 me-3"> <!-- App Search-->
<div class="avatar-xs"> <div class="dropdown pt-3 d-inline-block"> <a class="btn btn-secondary dropdown-toggle" href="#" role="button" id="dropdownMenuLink" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<span class="avatar-title bg-info rounded-circle font-size-16"> {{ Auth::user()->name }}
<i class="mdi mdi-glass-cocktail"></i> </a> </div>
</span>
</div>
</div>
<div class="flex-grow-1">
<h6 class="mb-1">Your item is shipped</h6>
<div class="font-size-12 text-muted">
<p class="mb-1">It is a long established fact that a reader will</p>
</div>
</div>
</div>
</a>
<a href="" class="text-reset notification-item"> <div class="dropdown d-inline-block">
<div class="d-flex"> <button type="button" class="btn header-item waves-effect" id="page-header-user-dropdown" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<div class="flex-shrink-0 me-3">
<div class="avatar-xs">
<span class="avatar-title bg-primary rounded-circle font-size-16">
<i class="mdi mdi-cart-outline"></i>
</span>
</div>
</div>
<div class="flex-grow-1">
<h6 class="mb-1">Your order is placed</h6>
<div class="font-size-12 text-muted">
<p class="mb-1">Dummy text of the printing and typesetting industry.</p>
</div>
</div>
</div>
</a>
<a href="" class="text-reset notification-item"> @if (Auth::user()->roles->first()->name != 'mahasiswa')
<div class="d-flex"> <img src="https://siakadu.unesa.ac.id/photo/fotomhs/{{ Auth::user()->rBiodata->noidentitas }}.jpg" alt="Header Avatar" class="rounded-circle header-profile-user" >
<div class="flex-shrink-0 me-3"> @else
<div class="avatar-xs"> <img src="https://siakadu.unesa.ac.id/photo/{{ Auth::user()->rBiodata->noidentitas }}.jpg" alt="Header Avatar" class="rounded-circle header-profile-user" >
<span class="avatar-title bg-danger rounded-circle font-size-16"> @endif
<i class="mdi mdi-message-text-outline"></i>
</span>
</div>
</div>
<div class="flex-grow-1">
<h6 class="mb-1">New Message received</h6>
<div class="font-size-12 text-muted">
<p class="mb-1">You have 87 unread messages</p>
</div>
</div>
</div>
</a>
</div>
<div class="p-2 border-top">
<div class="d-grid">
<a class="btn btn-sm btn-link font-size-14 text-center" href="javascript:void(0)">
View all
</a>
</div>
</div>
</div>
</div>
<div class="dropdown d-inline-block">
<button type="button" class="btn header-item waves-effect" id="page-header-user-dropdown"
data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<img class="rounded-circle header-profile-user" src="{{ asset('theme/images/users/user-4.jpg') }}"
alt="Header Avatar">
</button> </button>
<div class="dropdown-menu dropdown-menu-end"> <div class="dropdown-menu dropdown-menu-end">
<!-- item--> <!-- item-->
<a class="dropdown-item" href="#"><i class="mdi mdi-account-circle font-size-17 align-middle me-1"></i> Profile</a> {{-- <a class="dropdown-item" href="#"><i class="mdi mdi-account-circle font-size-17 align-middle me-1"></i> Profile</a> --}}
<a class="dropdown-item" href="#"><i class="mdi mdi-wallet font-size-17 align-middle me-1"></i> My Wallet</a>
<a class="dropdown-item d-flex align-items-center" href="#"><i class="mdi mdi-cog font-size-17 align-middle me-1"></i> Settings<span class="badge bg-success ms-auto">11</span></a>
<a class="dropdown-item" href="#"><i class="mdi mdi-lock-open-outline font-size-17 align-middle me-1"></i> Lock screen</a>
<div class="dropdown-divider"></div> <div class="dropdown-divider"></div>
<a class="dropdown-item text-danger" href="#"><i class="bx bx-power-off font-size-17 align-middle me-1 text-danger"></i> Logout</a> <a class="dropdown-item text-danger" href="{{ route('logout') }}" onclick="event.preventDefault();document.getElementById('logout-form').submit();"><i class="bx bx-power-off font-size-17 align-middle me-1 text-danger"></i> Logout</a>
</div> <form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
@csrf
</form>
</div> </div>
<div class="dropdown d-inline-block">
<button type="button" class="btn header-item noti-icon right-bar-toggle waves-effect">
<i class="mdi mdi-cog-outline"></i>
</button>
</div> </div>
</div> </div>
...@@ -288,7 +88,7 @@ ...@@ -288,7 +88,7 @@
<div class="container-fluid"> <div class="container-fluid">
<div class="row"> <div class="row">
<div class="col-12"> <div class="col-12">
© <script>document.write(new Date().getFullYear())</script> Veltrix<span class="d-none d-sm-inline-block"> - Crafted with <i class="mdi mdi-heart text-danger"></i> by Themesbrand.</span> © <script>document.write(new Date().getFullYear())</script> SIM PKM<span class="d-none d-sm-inline-block"> - Crafted with <i class="mdi mdi-heart text-danger"></i> by PPTI.</span>
</div> </div>
</div> </div>
</div> </div>
...@@ -300,57 +100,6 @@ ...@@ -300,57 +100,6 @@
</div> </div>
<!-- END layout-wrapper --> <!-- END layout-wrapper -->
<!-- Right Sidebar -->
<div class="right-bar">
<div data-simplebar class="h-100">
<div class="rightbar-title px-3 py-4">
<a href="javascript:void(0);" class="right-bar-toggle float-end">
<i class="mdi mdi-close noti-icon"></i>
</a>
<h5 class="m-0">Settings</h5>
</div>
<!-- Settings -->
<hr class="mt-0" />
<h6 class="text-center">Choose Layouts</h6>
<div class="p-4">
<div class="mb-2">
<img src="{{ asset('theme/images/layouts/layout-1.jpg') }}" class="img-fluid img-thumbnail" alt="">
</div>
<div class="form-check form-switch mb-3">
<input type="checkbox" class="form-check-input theme-choice" id="light-mode-switch" checked />
<label class="form-check-label" for="light-mode-switch">Light Mode</label>
</div>
<div class="mb-2">
<img src="{{ asset('theme/images/layouts/layout-2.jpg') }}" class="img-fluid img-thumbnail" alt="">
</div>
<div class="form-check form-switch mb-3">
<input type="checkbox" class="form-check-input theme-choice" id="dark-mode-switch" data-bsStyle="assets/css/bootstrap-dark.min.css"
data-appStyle="assets/css/app-dark.min.css" />
<label class="form-check-label" for="dark-mode-switch">Dark Mode</label>
</div>
<div class="mb-2">
<img src="{{ asset('theme/images/layouts/layout-3.jpg') }}" class="img-fluid img-thumbnail" alt="">
</div>
<div class="form-check form-switch mb-5">
<input type="checkbox" class="form-check-input theme-choice" id="rtl-mode-switch" data-appStyle="assets/css/app-rtl.min.css" />
<label class="form-check-label" for="rtl-mode-switch">RTL Mode</label>
</div>
<div class="d-grid">
<a href="https://1.envato.market/grNDB" class="btn btn-primary mt-3" target="_blank"><i class="mdi mdi-cart me-1"></i> Purchase Now</a>
</div>
</div>
</div> <!-- end slimscroll-menu-->
</div>
<!-- /Right-bar -->
<!-- Right bar overlay-->
<div class="rightbar-overlay"></div>
@include('layouts.inijs') @include('layouts.inijs')
</body> </body>
......
...@@ -6,7 +6,9 @@ ...@@ -6,7 +6,9 @@
<div id="sidebar-menu"> <div id="sidebar-menu">
<!-- Left Menu Start --> <!-- Left Menu Start -->
<ul class="metismenu list-unstyled" id="side-menu"> <ul class="metismenu list-unstyled" id="side-menu">
<li class="menu-title">Setting</li>
@if (Auth::user()->hasrole(['operator']))
<li class="menu-title">Menu Operator</li>
<li class="{{ (request()->is('jenis/*')) ? 'mm-active' : '' }}"> <li class="{{ (request()->is('jenis/*')) ? 'mm-active' : '' }}">
<a href="{{ URL::to('jenis') }}" class="waves-effect"> <a href="{{ URL::to('jenis') }}" class="waves-effect">
...@@ -37,254 +39,73 @@ ...@@ -37,254 +39,73 @@
<li><a href="{{ URL::to('seleksi_internal_proposal') }}">Daftar Proposal</a></li> <li><a href="{{ URL::to('seleksi_internal_proposal') }}">Daftar Proposal</a></li>
</ul> </ul>
</li> </li>
@endif
@if (Auth::user()->hasrole(['mahasiswa']))
<li class="menu-title">Menu Mahasiswa</li>
<li> <li>
<a href="calendar.html" class=" waves-effect"> <a href="{{ URL::to('/dashboard') }}" class="waves-effect"><i class="ti-home"></i><span>Dashboard</span></a>
<i class="ti-calendar"></i>
<span>Calendar</span>
</a>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/mahasiswa/biodata') }}" class="waves-effect"><i class="ti-id-badge"></i><span>Biodata</span></a>
<i class="ti-email"></i>
<span>Email</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="email-inbox.html">Inbox</a></li>
<li><a href="email-read.html">Email Read</a></li>
<li><a href="email-compose.html">Email Compose</a></li>
</ul>
</li> </li>
<li class="menu-title">Main</li>
<li> <li>
<a href="index.html" class="waves-effect"> <a href="{{ URL::to('/mahasiswa/kelompok') }}" class="waves-effect"><i class="ti-user"></i><span>Kelompok</span></a>
<i class="ti-home"></i><span class="badge rounded-pill bg-primary float-end">2</span>
<span>Dashboard</span>
</a>
</li> </li>
<li>
<a href="calendar.html" class=" waves-effect">
<i class="ti-calendar"></i>
<span>Calendar</span>
</a>
</li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/mahasiswa/proposal') }}" class="waves-effect"><i class="ti-agenda"></i><span>Proposal</span></a>
<i class="ti-email"></i>
<span>Email</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="email-inbox.html">Inbox</a></li>
<li><a href="email-read.html">Email Read</a></li>
<li><a href="email-compose.html">Email Compose</a></li>
</ul>
</li> </li>
<li class="menu-title">Components</li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/mahasiswa/seleksi-internal') }}" class="waves-effect"><i class="ti-check"></i><span>Seleksi Internal</span></a>
<i class="ti-package"></i>
<span>UI Elements</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="ui-alerts.html">Alerts</a></li>
<li><a href="ui-buttons.html">Buttons</a></li>
<li><a href="ui-cards.html">Cards</a></li>
<li><a href="ui-carousel.html">Carousel</a></li>
<li><a href="ui-dropdowns.html">Dropdowns</a></li>
<li><a href="ui-grid.html">Grid</a></li>
<li><a href="ui-images.html">Images</a></li>
<li><a href="ui-lightbox.html">Lightbox</a></li>
<li><a href="ui-modals.html">Modals</a></li>
<li><a href="ui-offcanvas.html">Offcanvas</a></li>
<li><a href="ui-rangeslider.html">Range Slider</a></li>
<li><a href="ui-session-timeout.html">Session Timeout</a></li>
<li><a href="ui-progressbars.html">Progress Bars</a></li>
<li><a href="ui-sweet-alert.html">SweetAlert 2</a></li>
<li><a href="ui-tabs-accordions.html">Tabs &amp; Accordions</a></li>
<li><a href="ui-typography.html">Typography</a></li>
<li><a href="ui-video.html">Video</a></li>
<li><a href="ui-general.html">General</a></li>
<li><a href="ui-colors.html">Colors</a></li>
<li><a href="ui-rating.html">Rating</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="waves-effect"> <a href="{{ URL::to('/mahasiswa/seleksi-belmawa') }}" class="waves-effect"><i class="ti-check-box"></i><span>Seleksi Belmawa</span></a>
<i class="ti-receipt"></i>
<span class="badge rounded-pill bg-success float-end">6</span>
<span>Forms</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="form-elements.html">Form Elements</a></li>
<li><a href="form-validation.html">Form Validation</a></li>
<li><a href="form-advanced.html">Form Advanced</a></li>
<li><a href="form-editors.html">Form Editors</a></li>
<li><a href="form-uploads.html">Form File Upload</a></li>
<li><a href="form-xeditable.html">Form Xeditable</a></li>
<li><a href="form-repeater.html">Form Repeater</a></li>
<li><a href="form-wizard.html">Form Wizard</a></li>
<li><a href="form-mask.html">Form Mask</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="javascript: void(0);" class="has-arrow waves-effect">
<i class="ti-pie-chart"></i> <i class="ti-layers-alt"></i>
<span>Charts</span> <span>Monev Internal</span>
</a> </a>
<ul class="sub-menu" aria-expanded="false"> <ul class="sub-menu" aria-expanded="false">
<li><a href="charts-morris.html">Morris Chart</a></li> <li><a href="{{ URL::to('/mahasiswa/monev-satu') }}">Monev Internal I</a></li>
<li><a href="charts-chartist.html">Chartist Chart</a></li> <li><a href="{{ URL::to('/mahasiswa/monev-dua') }}">Monev Internal II</a></li>
<li><a href="charts-chartjs.html">Chartjs Chart</a></li> <li><a href="{{ URL::to('/mahasiswa/monev-tiga') }}">Monev Internal III</a></li>
<li><a href="charts-flot.html">Flot Chart</a></li>
<li><a href="charts-knob.html">Jquery Knob Chart</a></li>
<li><a href="charts-sparkline.html">Sparkline Chart</a></li>
</ul> </ul>
</li> </li>
@endif
@if (Auth::user()->hasrole(['dosen']))
<li class="menu-title">Menu Dosen</li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/dashboard') }}" class="waves-effect"><i class="ti-home"></i><span>Dashboard</span></a>
<i class="ti-view-grid"></i>
<span>Tables</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="tables-basic.html">Basic Tables</a></li>
<li><a href="tables-datatable.html">Data Table</a></li>
<li><a href="tables-responsive.html">Responsive Table</a></li>
<li><a href="tables-editable.html">Editable Table</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/dosen/biodata') }}" class="waves-effect"><i class="ti-id-badge"></i><span>Biodata</span></a>
<i class="ti-face-smile"></i>
<span>Icons</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="icons-material.html">Material Design</a></li>
<li><a href="icons-fontawesome.html">Font Awesome</a></li>
<li><a href="icons-ion.html">Ion Icons</a></li>
<li><a href="icons-themify.html">Themify Icons</a></li>
<li><a href="icons-dripicons.html">Dripicons</a></li>
<li><a href="icons-typicons.html">Typicons Icons</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="waves-effect"> <a href="{{ URL::to('/dosen/kelompok') }}" class="waves-effect"><i class="ti-user"></i><span>Kelompok</span></a>
<i class="ti-location-pin"></i>
<span class="badge rounded-pill bg-danger float-end">2</span>
<span>Maps</span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="maps-google.html"> Google Map</a></li>
<li><a href="maps-vector.html"> Vector Map</a></li>
</ul>
</li> </li>
<li class="menu-title">Extras</li>
<li>
<a href="javascript: void(0);" class="has-arrow waves-effect">
<i class="ti-layout"></i>
<span>Layouts</span>
</a>
<ul class="sub-menu" aria-expanded="true">
<li> <li>
<a href="javascript: void(0);" class="has-arrow">Vertical</a> <a href="{{ URL::to('/dosen/proposal') }}" class="waves-effect"><i class="ti-agenda"></i><span>Proposal</span></a>
<ul class="sub-menu" aria-expanded="true">
<li><a href="layouts-light-sidebar.html">Light Sidebar</a></li>
<li><a href="layouts-compact-sidebar.html">Compact Sidebar</a></li>
<li><a href="layouts-icon-sidebar.html">Icon Sidebar</a></li>
<li><a href="layouts-boxed.html">Boxed Layout</a></li>
<li><a href="layouts-colored-sidebar.html">Colored Sidebar</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow">Horizontal</a> <a href="{{ URL::to('/dosen/seleksi-internal') }}" class="waves-effect"><i class="ti-check"></i><span>Seleksi Internal</span></a>
<ul class="sub-menu" aria-expanded="true">
<li><a href="layouts-horizontal.html">Horizontal</a></li>
<li><a href="layouts-hori-topbar-light.html">Light Topbar</a></li>
<li><a href="layouts-hori-boxed.html">Boxed Layout</a></li>
</ul>
</li> </li>
</ul>
</li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="{{ URL::to('/dosen/seleksi-belmawa') }}" class="waves-effect"><i class="ti-check-box"></i><span>Seleksi Belmawa</span></a>
<i class="ti-archive"></i>
<span> Authentication </span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="pages-login.html">Login 1</a></li>
<li><a href="pages-login-2.html">Login 2</a></li>
<li><a href="pages-register.html">Register 1</a></li>
<li><a href="pages-register-2.html">Register 2</a></li>
<li><a href="pages-recoverpw.html">Recover Password 1</a></li>
<li><a href="pages-recoverpw-2.html">Recover Password 2</a></li>
<li><a href="pages-lock-screen.html">Lock Screen 1</a></li>
<li><a href="pages-lock-screen-2.html">Lock Screen 2</a></li>
</ul>
</li>
<li>
<a href="javascript: void(0);" class="has-arrow waves-effect">
<i class="ti-support"></i>
<span> Extra Pages </span>
</a>
<ul class="sub-menu" aria-expanded="false">
<li><a href="pages-timeline.html">Timeline</a></li>
<li><a href="pages-invoice.html">Invoice</a></li>
<li><a href="pages-directory.html">Directory</a></li>
<li><a href="pages-starter.html">Starter Page</a></li>
<li><a href="pages-404.html">Error 404</a></li>
<li><a href="pages-500.html">Error 500</a></li>
<li><a href="pages-pricing.html">Pricing</a></li>
<li><a href="pages-gallery.html">Gallery</a></li>
<li><a href="pages-maintenance.html">Maintenance</a></li>
<li><a href="pages-comingsoon.html">Coming Soon</a></li>
<li><a href="pages-faq.html">FAQs</a></li>
</ul>
</li> </li>
<li> <li>
<a href="javascript: void(0);" class="has-arrow waves-effect"> <a href="javascript: void(0);" class="has-arrow waves-effect">
<i class="ti-bookmark-alt"></i> <i class="ti-layers-alt"></i>
<span> Email Templates </span> <span>Monev Internal</span>
</a> </a>
<ul class="sub-menu" aria-expanded="false"> <ul class="sub-menu" aria-expanded="false">
<li><a href="email-template-basic.html">Basic Action Email</a></li> <li><a href="{{ URL::to('/dosen/monev-satu') }}">Monev Internal I</a></li>
<li><a href="email-template-alert.html">Alert Email</a></li> <li><a href="{{ URL::to('/dosen/monev-dua') }}">Monev Internal II</a></li>
<li><a href="email-template-billing.html">Billing Email</a></li> <li><a href="{{ URL::to('/dosen/monev-tiga') }}">Monev Internal III</a></li>
</ul>
</li>
<li>
<a href="javascript: void(0);" class="has-arrow waves-effect">
<i class="ti-more"></i>
<span>Multi Level</span>
</a>
<ul class="sub-menu" aria-expanded="true">
<li><a href="javascript: void(0);">Level 1.1</a></li>
<li><a href="javascript: void(0);" class="has-arrow">Level 1.2</a>
<ul class="sub-menu" aria-expanded="true">
<li><a href="javascript: void(0);">Level 2.1</a></li>
<li><a href="javascript: void(0);">Level 2.2</a></li>
</ul>
</li>
</ul> </ul>
</li> </li>
@endif
</ul> </ul>
</div> </div>
......
...@@ -50,7 +50,7 @@ ...@@ -50,7 +50,7 @@
<div class="card-body"> <div class="card-body">
<div class="mb-4"> <div class="mb-4">
<div class="float-start mini-stat-img me-4"> <div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/01.png') }}" alt=""> <img src="assets/images/services-icon/01.png" alt="">
</div> </div>
<h5 class="font-size-16 text-uppercase text-white-50">Orders</h5> <h5 class="font-size-16 text-uppercase text-white-50">Orders</h5>
<h4 class="fw-medium font-size-24">1,685 <i <h4 class="fw-medium font-size-24">1,685 <i
...@@ -74,7 +74,7 @@ ...@@ -74,7 +74,7 @@
<div class="card-body"> <div class="card-body">
<div class="mb-4"> <div class="mb-4">
<div class="float-start mini-stat-img me-4"> <div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/02.png') }}" alt=""> <img src="assets/images/services-icon/02.png" alt="">
</div> </div>
<h5 class="font-size-16 text-uppercase text-white-50">Revenue</h5> <h5 class="font-size-16 text-uppercase text-white-50">Revenue</h5>
<h4 class="fw-medium font-size-24">52,368 <i <h4 class="fw-medium font-size-24">52,368 <i
...@@ -98,7 +98,7 @@ ...@@ -98,7 +98,7 @@
<div class="card-body"> <div class="card-body">
<div class="mb-4"> <div class="mb-4">
<div class="float-start mini-stat-img me-4"> <div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/03.png') }}" alt=""> <img src="assets/images/services-icon/03.png" alt="">
</div> </div>
<h5 class="font-size-16 text-uppercase text-white-50">Average Price</h5> <h5 class="font-size-16 text-uppercase text-white-50">Average Price</h5>
<h4 class="fw-medium font-size-24">15.8 <i <h4 class="fw-medium font-size-24">15.8 <i
...@@ -122,7 +122,7 @@ ...@@ -122,7 +122,7 @@
<div class="card-body"> <div class="card-body">
<div class="mb-4"> <div class="mb-4">
<div class="float-start mini-stat-img me-4"> <div class="float-start mini-stat-img me-4">
<img src="{{ asset('theme/images/services-icon/04.png') }}" alt=""> <img src="assets/images/services-icon/04.png" alt="">
</div> </div>
<h5 class="font-size-16 text-uppercase text-white-50">Product Sold</h5> <h5 class="font-size-16 text-uppercase text-white-50">Product Sold</h5>
<h4 class="fw-medium font-size-24">2436 <i <h4 class="fw-medium font-size-24">2436 <i
...@@ -388,7 +388,7 @@ ...@@ -388,7 +388,7 @@
<i class="mdi mdi-arrow-right h5"></i> <i class="mdi mdi-arrow-right h5"></i>
</a> </a>
</div> </div>
<h6 class="mb-0"><img src="{{ asset('theme/images/users/user-3.jpg') }}" alt="" <h6 class="mb-0"><img src="assets/images/users/user-3.jpg" alt=""
class="avatar-sm rounded-circle me-2"> James Athey</h6> class="avatar-sm rounded-circle me-2"> James Athey</h6>
</div> </div>
</div> </div>
...@@ -419,7 +419,7 @@ ...@@ -419,7 +419,7 @@
<th scope="row">#14256</th> <th scope="row">#14256</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-2.jpg') }}" alt="" <img src="assets/images/users/user-2.jpg" alt=""
class="avatar-xs rounded-circle me-2"> Philip Smead class="avatar-xs rounded-circle me-2"> Philip Smead
</div> </div>
</td> </td>
...@@ -436,7 +436,7 @@ ...@@ -436,7 +436,7 @@
<th scope="row">#14257</th> <th scope="row">#14257</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-3.jpg') }}" alt="" <img src="assets/images/users/user-3.jpg" alt=""
class="avatar-xs rounded-circle me-2"> Brent Shipley class="avatar-xs rounded-circle me-2"> Brent Shipley
</div> </div>
</td> </td>
...@@ -453,7 +453,7 @@ ...@@ -453,7 +453,7 @@
<th scope="row">#14258</th> <th scope="row">#14258</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-4.jpg') }}" alt="" <img src="assets/images/users/user-4.jpg" alt=""
class="avatar-xs rounded-circle me-2"> Robert Sitton class="avatar-xs rounded-circle me-2"> Robert Sitton
</div> </div>
</td> </td>
...@@ -470,7 +470,7 @@ ...@@ -470,7 +470,7 @@
<th scope="row">#14259</th> <th scope="row">#14259</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-5.jpg') }}" alt="" <img src="assets/images/users/user-5.jpg" alt=""
class="avatar-xs rounded-circle me-2"> Alberto Jackson class="avatar-xs rounded-circle me-2"> Alberto Jackson
</div> </div>
</td> </td>
...@@ -487,7 +487,7 @@ ...@@ -487,7 +487,7 @@
<th scope="row">#14260</th> <th scope="row">#14260</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-6.jpg') }}" alt="" <img src="assets/images/users/user-6.jpg" alt=""
class="avatar-xs rounded-circle me-2"> David Sanchez class="avatar-xs rounded-circle me-2"> David Sanchez
</div> </div>
</td> </td>
...@@ -504,7 +504,7 @@ ...@@ -504,7 +504,7 @@
<th scope="row">#14261</th> <th scope="row">#14261</th>
<td> <td>
<div> <div>
<img src="{{ asset('theme/images/users/user-2.jpg') }}" alt="" <img src="assets/images/users/user-2.jpg" alt=""
class="avatar-xs rounded-circle me-2"> Philip Smead class="avatar-xs rounded-circle me-2"> Philip Smead
</div> </div>
</td> </td>
...@@ -531,7 +531,7 @@ ...@@ -531,7 +531,7 @@
<ul class="conversation-list" data-simplebar style="max-height: 367px;"> <ul class="conversation-list" data-simplebar style="max-height: 367px;">
<li class="clearfix"> <li class="clearfix">
<div class="chat-avatar"> <div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-2.jpg') }}" <img src="assets/images/users/user-2.jpg"
class="avatar-xs rounded-circle" alt="male"> class="avatar-xs rounded-circle" alt="male">
<span class="time">10:00</span> <span class="time">10:00</span>
</div> </div>
...@@ -546,7 +546,7 @@ ...@@ -546,7 +546,7 @@
</li> </li>
<li class="clearfix odd"> <li class="clearfix odd">
<div class="chat-avatar"> <div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}" <img src="assets/images/users/user-3.jpg"
class="avatar-xs rounded-circle" alt="Female"> class="avatar-xs rounded-circle" alt="Female">
<span class="time">10:01</span> <span class="time">10:01</span>
</div> </div>
...@@ -561,7 +561,7 @@ ...@@ -561,7 +561,7 @@
</li> </li>
<li class="clearfix"> <li class="clearfix">
<div class="chat-avatar"> <div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-2.jpg') }}" <img src="assets/images/users/user-2.jpg"
class="avatar-xs rounded-circle" alt="male"> class="avatar-xs rounded-circle" alt="male">
<span class="time">10:04</span> <span class="time">10:04</span>
</div> </div>
...@@ -576,7 +576,7 @@ ...@@ -576,7 +576,7 @@
</li> </li>
<li class="clearfix odd"> <li class="clearfix odd">
<div class="chat-avatar"> <div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}" <img src="assets/images/users/user-3.jpg"
class="avatar-xs rounded-circle" alt="male"> class="avatar-xs rounded-circle" alt="male">
<span class="time">10:05</span> <span class="time">10:05</span>
</div> </div>
...@@ -591,7 +591,7 @@ ...@@ -591,7 +591,7 @@
</li> </li>
<li class="clearfix odd"> <li class="clearfix odd">
<div class="chat-avatar"> <div class="chat-avatar">
<img src="{{ asset('theme/images/users/user-3.jpg') }}" <img src="assets/images/users/user-3.jpg"
class="avatar-xs rounded-circle" alt="male"> class="avatar-xs rounded-circle" alt="male">
<span class="time">10:08</span> <span class="time">10:08</span>
</div> </div>
...@@ -599,9 +599,9 @@ ...@@ -599,9 +599,9 @@
<div class="ctext-wrap"> <div class="ctext-wrap">
<span class="user-name mb-2">Smith</span> <span class="user-name mb-2">Smith</span>
<img src="{{ asset('theme/images/small/img-1.jpg') }}" alt="" height="48" <img src="assets/images/small/img-1.jpg" alt="" height="48"
class="rounded me-2"> class="rounded me-2">
<img src="{{ asset('theme/images/small/img-2.jpg') }}" alt="" height="48" <img src="assets/images/small/img-2.jpg" alt="" height="48"
class="rounded"> class="rounded">
</div> </div>
</div> </div>
......
<nav x-data="{ open: false }" class="bg-white border-b border-gray-100">
<!-- Primary Navigation Menu -->
<div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
<div class="flex justify-between h-16">
<div class="flex">
<!-- Logo -->
<div class="flex-shrink-0 flex items-center">
<a href="{{ route('dashboard') }}">
<x-jet-application-mark class="block h-9 w-auto" />
</a>
</div>
<!-- Navigation Links -->
<div class="hidden space-x-8 sm:-my-px sm:ml-10 sm:flex">
<x-jet-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-jet-nav-link>
</div>
</div>
<!-- Settings Dropdown -->
<div class="hidden sm:flex sm:items-center sm:ml-6">
<x-jet-dropdown align="right" width="48">
<x-slot name="trigger">
@if (Laravel\Jetstream\Jetstream::managesProfilePhotos())
<button class="flex text-sm border-2 border-transparent rounded-full focus:outline-none focus:border-gray-300 transition duration-150 ease-in-out">
<img class="h-8 w-8 rounded-full object-cover" src="{{ Auth::user()->profile_photo_url }}" alt="{{ Auth::user()->name }}" />
</button>
@else
<button class="flex items-center text-sm font-medium text-gray-500 hover:text-gray-700 hover:border-gray-300 focus:outline-none focus:text-gray-700 focus:border-gray-300 transition duration-150 ease-in-out">
<div>{{ Auth::user()->name }}</div>
<div class="ml-1">
<svg class="fill-current h-4 w-4" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20">
<path fill-rule="evenodd" d="M5.293 7.293a1 1 0 011.414 0L10 10.586l3.293-3.293a1 1 0 111.414 1.414l-4 4a1 1 0 01-1.414 0l-4-4a1 1 0 010-1.414z" clip-rule="evenodd" />
</svg>
</div>
</button>
@endif
</x-slot>
<x-slot name="content">
<!-- Account Management -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Account') }}
</div>
<x-jet-dropdown-link href="{{ route('profile.show') }}">
{{ __('Profile') }}
</x-jet-dropdown-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-jet-dropdown-link href="{{ route('api-tokens.index') }}">
{{ __('API Tokens') }}
</x-jet-dropdown-link>
@endif
<div class="border-t border-gray-100"></div>
<!-- Team Management -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Team') }}
</div>
<!-- Team Settings -->
<x-jet-dropdown-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}">
{{ __('Team Settings') }}
</x-jet-dropdown-link>
@can('create', Laravel\Jetstream\Jetstream::newTeamModel())
<x-jet-dropdown-link href="{{ route('teams.create') }}">
{{ __('Create New Team') }}
</x-jet-dropdown-link>
@endcan
<div class="border-t border-gray-100"></div>
<!-- Team Switcher -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-jet-switchable-team :team="$team" />
@endforeach
<div class="border-t border-gray-100"></div>
@endif
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}">
@csrf
<x-jet-dropdown-link href="{{ route('logout') }}"
onclick="event.preventDefault();
this.closest('form').submit();">
{{ __('Logout') }}
</x-jet-dropdown-link>
</form>
</x-slot>
</x-jet-dropdown>
</div>
<!-- Hamburger -->
<div class="-mr-2 flex items-center sm:hidden">
<button @click="open = ! open" class="inline-flex items-center justify-center p-2 rounded-md text-gray-400 hover:text-gray-500 hover:bg-gray-100 focus:outline-none focus:bg-gray-100 focus:text-gray-500 transition duration-150 ease-in-out">
<svg class="h-6 w-6" stroke="currentColor" fill="none" viewBox="0 0 24 24">
<path :class="{'hidden': open, 'inline-flex': ! open }" class="inline-flex" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
<path :class="{'hidden': ! open, 'inline-flex': open }" class="hidden" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12" />
</svg>
</button>
</div>
</div>
</div>
<!-- Responsive Navigation Menu -->
<div :class="{'block': open, 'hidden': ! open}" class="hidden sm:hidden">
<div class="pt-2 pb-3 space-y-1">
<x-jet-responsive-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-jet-responsive-nav-link>
</div>
<!-- Responsive Settings Options -->
<div class="pt-4 pb-1 border-t border-gray-200">
<div class="flex items-center px-4">
<div class="flex-shrink-0">
<img class="h-10 w-10 rounded-full" src="{{ Auth::user()->profile_photo_url }}" alt="{{ Auth::user()->name }}" />
</div>
<div class="ml-3">
<div class="font-medium text-base text-gray-800">{{ Auth::user()->name }}</div>
<div class="font-medium text-sm text-gray-500">{{ Auth::user()->email }}</div>
</div>
</div>
<div class="mt-3 space-y-1">
<!-- Account Management -->
<x-jet-responsive-nav-link href="{{ route('profile.show') }}" :active="request()->routeIs('profile.show')">
{{ __('Profile') }}
</x-jet-responsive-nav-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-jet-responsive-nav-link href="{{ route('api-tokens.index') }}" :active="request()->routeIs('api-tokens.index')">
{{ __('API Tokens') }}
</x-jet-responsive-nav-link>
@endif
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}">
@csrf
<x-jet-responsive-nav-link href="{{ route('logout') }}"
onclick="event.preventDefault();
this.closest('form').submit();">
{{ __('Logout') }}
</x-jet-responsive-nav-link>
</form>
<!-- Team Management -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="border-t border-gray-200"></div>
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Team') }}
</div>
<!-- Team Settings -->
<x-jet-responsive-nav-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}" :active="request()->routeIs('teams.show')">
{{ __('Team Settings') }}
</x-jet-responsive-nav-link>
<x-jet-responsive-nav-link href="{{ route('teams.create') }}" :active="request()->routeIs('teams.create')">
{{ __('Create New Team') }}
</x-jet-responsive-nav-link>
<div class="border-t border-gray-200"></div>
<!-- Team Switcher -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-jet-switchable-team :team="$team" component="jet-responsive-nav-link" />
@endforeach
@endif
</div>
</div>
</div>
</nav>
<nav x-data="{ open: false }" class="bg-white border-b border-gray-100">
<!-- Primary Navigation Menu -->
<div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
<div class="flex justify-between h-16">
<div class="flex">
<!-- Logo -->
<div class="shrink-0 flex items-center">
<a href="{{ route('dashboard') }}">
<x-jet-application-mark class="block h-9 w-auto" />
</a>
</div>
<!-- Navigation Links -->
<div class="hidden space-x-8 sm:-my-px sm:ml-10 sm:flex">
<x-jet-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-jet-nav-link>
</div>
</div>
<div class="hidden sm:flex sm:items-center sm:ml-6">
<!-- Teams Dropdown -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="ml-3 relative">
<x-jet-dropdown align="right" width="60">
<x-slot name="trigger">
<span class="inline-flex rounded-md">
<button type="button" class="inline-flex items-center px-3 py-2 border border-transparent text-sm leading-4 font-medium rounded-md text-gray-500 bg-white hover:bg-gray-50 hover:text-gray-700 focus:outline-none focus:bg-gray-50 active:bg-gray-50 transition">
{{ Auth::user()->currentTeam->name }}
<svg class="ml-2 -mr-0.5 h-4 w-4" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" fill="currentColor">
<path fill-rule="evenodd" d="M10 3a1 1 0 01.707.293l3 3a1 1 0 01-1.414 1.414L10 5.414 7.707 7.707a1 1 0 01-1.414-1.414l3-3A1 1 0 0110 3zm-3.707 9.293a1 1 0 011.414 0L10 14.586l2.293-2.293a1 1 0 011.414 1.414l-3 3a1 1 0 01-1.414 0l-3-3a1 1 0 010-1.414z" clip-rule="evenodd" />
</svg>
</button>
</span>
</x-slot>
<x-slot name="content">
<div class="w-60">
<!-- Team Management -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Team') }}
</div>
<!-- Team Settings -->
<x-jet-dropdown-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}">
{{ __('Team Settings') }}
</x-jet-dropdown-link>
@can('create', Laravel\Jetstream\Jetstream::newTeamModel())
<x-jet-dropdown-link href="{{ route('teams.create') }}">
{{ __('Create New Team') }}
</x-jet-dropdown-link>
@endcan
<div class="border-t border-gray-100"></div>
<!-- Team Switcher -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-jet-switchable-team :team="$team" />
@endforeach
</div>
</x-slot>
</x-jet-dropdown>
</div>
@endif
<!-- Settings Dropdown -->
<div class="ml-3 relative">
<x-jet-dropdown align="right" width="48">
<x-slot name="trigger">
@if (Laravel\Jetstream\Jetstream::managesProfilePhotos())
<button class="flex text-sm border-2 border-transparent rounded-full focus:outline-none focus:border-gray-300 transition">
<img class="h-8 w-8 rounded-full object-cover" src="{{ Auth::user()->profile_photo_url }}" alt="{{ Auth::user()->name }}" />
</button>
@else
<span class="inline-flex rounded-md">
<button type="button" class="inline-flex items-center px-3 py-2 border border-transparent text-sm leading-4 font-medium rounded-md text-gray-500 bg-white hover:text-gray-700 focus:outline-none transition">
{{ Auth::user()->name }}
<svg class="ml-2 -mr-0.5 h-4 w-4" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" fill="currentColor">
<path fill-rule="evenodd" d="M5.293 7.293a1 1 0 011.414 0L10 10.586l3.293-3.293a1 1 0 111.414 1.414l-4 4a1 1 0 01-1.414 0l-4-4a1 1 0 010-1.414z" clip-rule="evenodd" />
</svg>
</button>
</span>
@endif
</x-slot>
<x-slot name="content">
<!-- Account Management -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Account') }}
</div>
<x-jet-dropdown-link href="{{ route('profile.show') }}">
{{ __('Profile') }}
</x-jet-dropdown-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-jet-dropdown-link href="{{ route('api-tokens.index') }}">
{{ __('API Tokens') }}
</x-jet-dropdown-link>
@endif
<div class="border-t border-gray-100"></div>
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}" x-data>
@csrf
<x-jet-dropdown-link href="{{ route('logout') }}"
@click.prevent="$root.submit();">
{{ __('Log Out') }}
</x-jet-dropdown-link>
</form>
</x-slot>
</x-jet-dropdown>
</div>
</div>
<!-- Hamburger -->
<div class="-mr-2 flex items-center sm:hidden">
<button @click="open = ! open" class="inline-flex items-center justify-center p-2 rounded-md text-gray-400 hover:text-gray-500 hover:bg-gray-100 focus:outline-none focus:bg-gray-100 focus:text-gray-500 transition">
<svg class="h-6 w-6" stroke="currentColor" fill="none" viewBox="0 0 24 24">
<path :class="{'hidden': open, 'inline-flex': ! open }" class="inline-flex" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
<path :class="{'hidden': ! open, 'inline-flex': open }" class="hidden" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12" />
</svg>
</button>
</div>
</div>
</div>
<!-- Responsive Navigation Menu -->
<div :class="{'block': open, 'hidden': ! open}" class="hidden sm:hidden">
<div class="pt-2 pb-3 space-y-1">
<x-jet-responsive-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-jet-responsive-nav-link>
</div>
<!-- Responsive Settings Options -->
<div class="pt-4 pb-1 border-t border-gray-200">
<div class="flex items-center px-4">
@if (Laravel\Jetstream\Jetstream::managesProfilePhotos())
<div class="shrink-0 mr-3">
<img class="h-10 w-10 rounded-full object-cover" src="{{ Auth::user()->profile_photo_url }}" alt="{{ Auth::user()->name }}" />
</div>
@endif
<div>
<div class="font-medium text-base text-gray-800">{{ Auth::user()->name }}</div>
<div class="font-medium text-sm text-gray-500">{{ Auth::user()->email }}</div>
</div>
</div>
<div class="mt-3 space-y-1">
<!-- Account Management -->
<x-jet-responsive-nav-link href="{{ route('profile.show') }}" :active="request()->routeIs('profile.show')">
{{ __('Profile') }}
</x-jet-responsive-nav-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-jet-responsive-nav-link href="{{ route('api-tokens.index') }}" :active="request()->routeIs('api-tokens.index')">
{{ __('API Tokens') }}
</x-jet-responsive-nav-link>
@endif
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}" x-data>
@csrf
<x-jet-responsive-nav-link href="{{ route('logout') }}"
@click.prevent="$root.submit();">
{{ __('Log Out') }}
</x-jet-responsive-nav-link>
</form>
<!-- Team Management -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="border-t border-gray-200"></div>
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Team') }}
</div>
<!-- Team Settings -->
<x-jet-responsive-nav-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}" :active="request()->routeIs('teams.show')">
{{ __('Team Settings') }}
</x-jet-responsive-nav-link>
@can('create', Laravel\Jetstream\Jetstream::newTeamModel())
<x-jet-responsive-nav-link href="{{ route('teams.create') }}" :active="request()->routeIs('teams.create')">
{{ __('Create New Team') }}
</x-jet-responsive-nav-link>
@endcan
<div class="border-t border-gray-200"></div>
<!-- Team Switcher -->
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-jet-switchable-team :team="$team" component="jet-responsive-nav-link" />
@endforeach
@endif
</div>
</div>
</div>
</nav>
<x-guest-layout>
<div class="pt-4 bg-gray-100">
<div class="min-h-screen flex flex-col items-center pt-6 sm:pt-0">
<div>
<x-jet-authentication-card-logo />
</div>
<div class="w-full sm:max-w-2xl mt-6 p-6 bg-white shadow-md overflow-hidden sm:rounded-lg prose">
{!! $policy !!}
</div>
</div>
</div>
</x-guest-layout>
<x-jet-action-section>
<x-slot name="title">
{{ __('Delete Account') }}
</x-slot>
<x-slot name="description">
{{ __('Permanently delete your account.') }}
</x-slot>
<x-slot name="content">
<div class="max-w-xl text-sm text-gray-600">
{{ __('Once your account is deleted, all of its resources and data will be permanently deleted. Before deleting your account, please download any data or information that you wish to retain.') }}
</div>
<div class="mt-5">
<x-jet-danger-button wire:click="confirmUserDeletion" wire:loading.attr="disabled">
{{ __('Delete Account') }}
</x-jet-danger-button>
</div>
<!-- Delete User Confirmation Modal -->
<x-jet-dialog-modal wire:model="confirmingUserDeletion">
<x-slot name="title">
{{ __('Delete Account') }}
</x-slot>
<x-slot name="content">
{{ __('Are you sure you want to delete your account? Once your account is deleted, all of its resources and data will be permanently deleted. Please enter your password to confirm you would like to permanently delete your account.') }}
<div class="mt-4" x-data="{}" x-on:confirming-delete-user.window="setTimeout(() => $refs.password.focus(), 250)">
<x-jet-input type="password" class="mt-1 block w-3/4"
placeholder="{{ __('Password') }}"
x-ref="password"
wire:model.defer="password"
wire:keydown.enter="deleteUser" />
<x-jet-input-error for="password" class="mt-2" />
</div>
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingUserDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-danger-button class="ml-3" wire:click="deleteUser" wire:loading.attr="disabled">
{{ __('Delete Account') }}
</x-jet-danger-button>
</x-slot>
</x-jet-dialog-modal>
</x-slot>
</x-jet-action-section>
<x-jet-action-section>
<x-slot name="title">
{{ __('Browser Sessions') }}
</x-slot>
<x-slot name="description">
{{ __('Manage and log out your active sessions on other browsers and devices.') }}
</x-slot>
<x-slot name="content">
<div class="max-w-xl text-sm text-gray-600">
{{ __('If necessary, you may log out of all of your other browser sessions across all of your devices. Some of your recent sessions are listed below; however, this list may not be exhaustive. If you feel your account has been compromised, you should also update your password.') }}
</div>
@if (count($this->sessions) > 0)
<div class="mt-5 space-y-6">
<!-- Other Browser Sessions -->
@foreach ($this->sessions as $session)
<div class="flex items-center">
<div>
@if ($session->agent->isDesktop())
<svg fill="none" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" viewBox="0 0 24 24" stroke="currentColor" class="w-8 h-8 text-gray-500">
<path d="M9.75 17L9 20l-1 1h8l-1-1-.75-3M3 13h18M5 17h14a2 2 0 002-2V5a2 2 0 00-2-2H5a2 2 0 00-2 2v10a2 2 0 002 2z"></path>
</svg>
@else
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" stroke-width="2" stroke="currentColor" fill="none" stroke-linecap="round" stroke-linejoin="round" class="w-8 h-8 text-gray-500">
<path d="M0 0h24v24H0z" stroke="none"></path><rect x="7" y="4" width="10" height="16" rx="1"></rect><path d="M11 5h2M12 17v.01"></path>
</svg>
@endif
</div>
<div class="ml-3">
<div class="text-sm text-gray-600">
{{ $session->agent->platform() ? $session->agent->platform() : 'Unknown' }} - {{ $session->agent->browser() ? $session->agent->browser() : 'Unknown' }}
</div>
<div>
<div class="text-xs text-gray-500">
{{ $session->ip_address }},
@if ($session->is_current_device)
<span class="text-green-500 font-semibold">{{ __('This device') }}</span>
@else
{{ __('Last active') }} {{ $session->last_active }}
@endif
</div>
</div>
</div>
</div>
@endforeach
</div>
@endif
<div class="flex items-center mt-5">
<x-jet-button wire:click="confirmLogout" wire:loading.attr="disabled">
{{ __('Log Out Other Browser Sessions') }}
</x-jet-button>
<x-jet-action-message class="ml-3" on="loggedOut">
{{ __('Done.') }}
</x-jet-action-message>
</div>
<!-- Log Out Other Devices Confirmation Modal -->
<x-jet-dialog-modal wire:model="confirmingLogout">
<x-slot name="title">
{{ __('Log Out Other Browser Sessions') }}
</x-slot>
<x-slot name="content">
{{ __('Please enter your password to confirm you would like to log out of your other browser sessions across all of your devices.') }}
<div class="mt-4" x-data="{}" x-on:confirming-logout-other-browser-sessions.window="setTimeout(() => $refs.password.focus(), 250)">
<x-jet-input type="password" class="mt-1 block w-3/4"
placeholder="{{ __('Password') }}"
x-ref="password"
wire:model.defer="password"
wire:keydown.enter="logoutOtherBrowserSessions" />
<x-jet-input-error for="password" class="mt-2" />
</div>
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingLogout')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-button class="ml-3"
wire:click="logoutOtherBrowserSessions"
wire:loading.attr="disabled">
{{ __('Log Out Other Browser Sessions') }}
</x-jet-button>
</x-slot>
</x-jet-dialog-modal>
</x-slot>
</x-jet-action-section>
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 leading-tight">
{{ __('Profile') }}
</h2>
</x-slot>
<div>
<div class="max-w-7xl mx-auto py-10 sm:px-6 lg:px-8">
@if (Laravel\Fortify\Features::canUpdateProfileInformation())
@livewire('profile.update-profile-information-form')
<x-jet-section-border />
@endif
@if (Laravel\Fortify\Features::enabled(Laravel\Fortify\Features::updatePasswords()))
<div class="mt-10 sm:mt-0">
@livewire('profile.update-password-form')
</div>
<x-jet-section-border />
@endif
@if (Laravel\Fortify\Features::canManageTwoFactorAuthentication())
<div class="mt-10 sm:mt-0">
@livewire('profile.two-factor-authentication-form')
</div>
<x-jet-section-border />
@endif
<div class="mt-10 sm:mt-0">
@livewire('profile.logout-other-browser-sessions-form')
</div>
@if (Laravel\Jetstream\Jetstream::hasAccountDeletionFeatures())
<x-jet-section-border />
<div class="mt-10 sm:mt-0">
@livewire('profile.delete-user-form')
</div>
@endif
</div>
</div>
</x-app-layout>
<x-jet-action-section>
<x-slot name="title">
{{ __('Two Factor Authentication') }}
</x-slot>
<x-slot name="description">
{{ __('Add additional security to your account using two factor authentication.') }}
</x-slot>
<x-slot name="content">
<h3 class="text-lg font-medium text-gray-900">
@if ($this->enabled)
@if ($showingConfirmation)
{{ __('Finish enabling two factor authentication.') }}
@else
{{ __('You have enabled two factor authentication.') }}
@endif
@else
{{ __('You have not enabled two factor authentication.') }}
@endif
</h3>
<div class="mt-3 max-w-xl text-sm text-gray-600">
<p>
{{ __('When two factor authentication is enabled, you will be prompted for a secure, random token during authentication. You may retrieve this token from your phone\'s Google Authenticator application.') }}
</p>
</div>
@if ($this->enabled)
@if ($showingQrCode)
<div class="mt-4 max-w-xl text-sm text-gray-600">
<p class="font-semibold">
@if ($showingConfirmation)
{{ __('To finish enabling two factor authentication, scan the following QR code using your phone\'s authenticator application or enter the setup key and provide the generated OTP code.') }}
@else
{{ __('Two factor authentication is now enabled. Scan the following QR code using your phone\'s authenticator application or enter the setup key.') }}
@endif
</p>
</div>
<div class="mt-4">
{!! $this->user->twoFactorQrCodeSvg() !!}
</div>
<div class="mt-4 max-w-xl text-sm text-gray-600">
<p class="font-semibold">
{{ __('Setup Key') }}: {{ decrypt($this->user->two_factor_secret) }}
</p>
</div>
@if ($showingConfirmation)
<div class="mt-4">
<x-jet-label for="code" value="{{ __('Code') }}" />
<x-jet-input id="code" type="text" name="code" class="block mt-1 w-1/2" inputmode="numeric" autofocus autocomplete="one-time-code"
wire:model.defer="code"
wire:keydown.enter="confirmTwoFactorAuthentication" />
<x-jet-input-error for="code" class="mt-2" />
</div>
@endif
@endif
@if ($showingRecoveryCodes)
<div class="mt-4 max-w-xl text-sm text-gray-600">
<p class="font-semibold">
{{ __('Store these recovery codes in a secure password manager. They can be used to recover access to your account if your two factor authentication device is lost.') }}
</p>
</div>
<div class="grid gap-1 max-w-xl mt-4 px-4 py-4 font-mono text-sm bg-gray-100 rounded-lg">
@foreach (json_decode(decrypt($this->user->two_factor_recovery_codes), true) as $code)
<div>{{ $code }}</div>
@endforeach
</div>
@endif
@endif
<div class="mt-5">
@if (! $this->enabled)
<x-jet-confirms-password wire:then="enableTwoFactorAuthentication">
<x-jet-button type="button" wire:loading.attr="disabled">
{{ __('Enable') }}
</x-jet-button>
</x-jet-confirms-password>
@else
@if ($showingRecoveryCodes)
<x-jet-confirms-password wire:then="regenerateRecoveryCodes">
<x-jet-secondary-button class="mr-3">
{{ __('Regenerate Recovery Codes') }}
</x-jet-secondary-button>
</x-jet-confirms-password>
@elseif ($showingConfirmation)
<x-jet-confirms-password wire:then="confirmTwoFactorAuthentication">
<x-jet-button type="button" class="mr-3" wire:loading.attr="disabled">
{{ __('Confirm') }}
</x-jet-button>
</x-jet-confirms-password>
@else
<x-jet-confirms-password wire:then="showRecoveryCodes">
<x-jet-secondary-button class="mr-3">
{{ __('Show Recovery Codes') }}
</x-jet-secondary-button>
</x-jet-confirms-password>
@endif
@if ($showingConfirmation)
<x-jet-confirms-password wire:then="disableTwoFactorAuthentication">
<x-jet-secondary-button wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
</x-jet-confirms-password>
@else
<x-jet-confirms-password wire:then="disableTwoFactorAuthentication">
<x-jet-danger-button wire:loading.attr="disabled">
{{ __('Disable') }}
</x-jet-danger-button>
</x-jet-confirms-password>
@endif
@endif
</div>
</x-slot>
</x-jet-action-section>
<x-jet-form-section submit="updatePassword">
<x-slot name="title">
{{ __('Update Password') }}
</x-slot>
<x-slot name="description">
{{ __('Ensure your account is using a long, random password to stay secure.') }}
</x-slot>
<x-slot name="form">
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="current_password" value="{{ __('Current Password') }}" />
<x-jet-input id="current_password" type="password" class="mt-1 block w-full" wire:model.defer="state.current_password" autocomplete="current-password" />
<x-jet-input-error for="current_password" class="mt-2" />
</div>
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="password" value="{{ __('New Password') }}" />
<x-jet-input id="password" type="password" class="mt-1 block w-full" wire:model.defer="state.password" autocomplete="new-password" />
<x-jet-input-error for="password" class="mt-2" />
</div>
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-jet-input id="password_confirmation" type="password" class="mt-1 block w-full" wire:model.defer="state.password_confirmation" autocomplete="new-password" />
<x-jet-input-error for="password_confirmation" class="mt-2" />
</div>
</x-slot>
<x-slot name="actions">
<x-jet-action-message class="mr-3" on="saved">
{{ __('Saved.') }}
</x-jet-action-message>
<x-jet-button>
{{ __('Save') }}
</x-jet-button>
</x-slot>
</x-jet-form-section>
<x-jet-form-section submit="updateProfileInformation">
<x-slot name="title">
{{ __('Profile Information') }}
</x-slot>
<x-slot name="description">
{{ __('Update your account\'s profile information and email address.') }}
</x-slot>
<x-slot name="form">
<!-- Profile Photo -->
@if (Laravel\Jetstream\Jetstream::managesProfilePhotos())
<div x-data="{photoName: null, photoPreview: null}" class="col-span-6 sm:col-span-4">
<!-- Profile Photo File Input -->
<input type="file" class="hidden"
wire:model="photo"
x-ref="photo"
x-on:change="
photoName = $refs.photo.files[0].name;
const reader = new FileReader();
reader.onload = (e) => {
photoPreview = e.target.result;
};
reader.readAsDataURL($refs.photo.files[0]);
" />
<x-jet-label for="photo" value="{{ __('Photo') }}" />
<!-- Current Profile Photo -->
<div class="mt-2" x-show="! photoPreview">
<img src="{{ $this->user->profile_photo_url }}" alt="{{ $this->user->name }}" class="rounded-full h-20 w-20 object-cover">
</div>
<!-- New Profile Photo Preview -->
<div class="mt-2" x-show="photoPreview" style="display: none;">
<span class="block rounded-full w-20 h-20 bg-cover bg-no-repeat bg-center"
x-bind:style="'background-image: url(\'' + photoPreview + '\');'">
</span>
</div>
<x-jet-secondary-button class="mt-2 mr-2" type="button" x-on:click.prevent="$refs.photo.click()">
{{ __('Select A New Photo') }}
</x-jet-secondary-button>
@if ($this->user->profile_photo_path)
<x-jet-secondary-button type="button" class="mt-2" wire:click="deleteProfilePhoto">
{{ __('Remove Photo') }}
</x-jet-secondary-button>
@endif
<x-jet-input-error for="photo" class="mt-2" />
</div>
@endif
<!-- Name -->
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="name" value="{{ __('Name') }}" />
<x-jet-input id="name" type="text" class="mt-1 block w-full" wire:model.defer="state.name" autocomplete="name" />
<x-jet-input-error for="name" class="mt-2" />
</div>
<!-- Email -->
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" type="email" class="mt-1 block w-full" wire:model.defer="state.email" />
<x-jet-input-error for="email" class="mt-2" />
@if (Laravel\Fortify\Features::enabled(Laravel\Fortify\Features::emailVerification()) && ! $this->user->hasVerifiedEmail())
<p class="text-sm mt-2">
{{ __('Your email address is unverified.') }}
<button type="button" class="underline text-sm text-gray-600 hover:text-gray-900" wire:click.prevent="sendEmailVerification">
{{ __('Click here to re-send the verification email.') }}
</button>
</p>
@if ($this->verificationLinkSent)
<p v-show="verificationLinkSent" class="mt-2 font-medium text-sm text-green-600">
{{ __('A new verification link has been sent to your email address.') }}
</p>
@endif
@endif
</div>
</x-slot>
<x-slot name="actions">
<x-jet-action-message class="mr-3" on="saved">
{{ __('Saved.') }}
</x-jet-action-message>
<x-jet-button wire:loading.attr="disabled" wire:target="photo">
{{ __('Save') }}
</x-jet-button>
</x-slot>
</x-jet-form-section>
<x-jet-form-section submit="createTeam">
<x-slot name="title">
{{ __('Team Details') }}
</x-slot>
<x-slot name="description">
{{ __('Create a new team to collaborate with others on projects.') }}
</x-slot>
<x-slot name="form">
<div class="col-span-6">
<x-jet-label value="{{ __('Team Owner') }}" />
<div class="flex items-center mt-2">
<img class="w-12 h-12 rounded-full object-cover" src="{{ $this->user->profile_photo_url }}" alt="{{ $this->user->name }}">
<div class="ml-4 leading-tight">
<div>{{ $this->user->name }}</div>
<div class="text-gray-700 text-sm">{{ $this->user->email }}</div>
</div>
</div>
</div>
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="name" value="{{ __('Team Name') }}" />
<x-jet-input id="name" type="text" class="mt-1 block w-full" wire:model.defer="state.name" autofocus />
<x-jet-input-error for="name" class="mt-2" />
</div>
</x-slot>
<x-slot name="actions">
<x-jet-button>
{{ __('Create') }}
</x-jet-button>
</x-slot>
</x-jet-form-section>
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 leading-tight">
{{ __('Create Team') }}
</h2>
</x-slot>
<div>
<div class="max-w-7xl mx-auto py-10 sm:px-6 lg:px-8">
@livewire('teams.create-team-form')
</div>
</div>
</x-app-layout>
<x-jet-action-section>
<x-slot name="title">
{{ __('Delete Team') }}
</x-slot>
<x-slot name="description">
{{ __('Permanently delete this team.') }}
</x-slot>
<x-slot name="content">
<div class="max-w-xl text-sm text-gray-600">
{{ __('Once a team is deleted, all of its resources and data will be permanently deleted. Before deleting this team, please download any data or information regarding this team that you wish to retain.') }}
</div>
<div class="mt-5">
<x-jet-danger-button wire:click="$toggle('confirmingTeamDeletion')" wire:loading.attr="disabled">
{{ __('Delete Team') }}
</x-jet-danger-button>
</div>
<!-- Delete Team Confirmation Modal -->
<x-jet-confirmation-modal wire:model="confirmingTeamDeletion">
<x-slot name="title">
{{ __('Delete Team') }}
</x-slot>
<x-slot name="content">
{{ __('Are you sure you want to delete this team? Once a team is deleted, all of its resources and data will be permanently deleted.') }}
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingTeamDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-danger-button class="ml-3" wire:click="deleteTeam" wire:loading.attr="disabled">
{{ __('Delete Team') }}
</x-jet-danger-button>
</x-slot>
</x-jet-confirmation-modal>
</x-slot>
</x-jet-action-section>
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 leading-tight">
{{ __('Team Settings') }}
</h2>
</x-slot>
<div>
<div class="max-w-7xl mx-auto py-10 sm:px-6 lg:px-8">
@livewire('teams.update-team-name-form', ['team' => $team])
@livewire('teams.team-member-manager', ['team' => $team])
@if (Gate::check('delete', $team) && ! $team->personal_team)
<x-jet-section-border />
<div class="mt-10 sm:mt-0">
@livewire('teams.delete-team-form', ['team' => $team])
</div>
@endif
</div>
</div>
</x-app-layout>
<div>
@if (Gate::check('addTeamMember', $team))
<x-jet-section-border />
<!-- Add Team Member -->
<div class="mt-10 sm:mt-0">
<x-jet-form-section submit="addTeamMember">
<x-slot name="title">
{{ __('Add Team Member') }}
</x-slot>
<x-slot name="description">
{{ __('Add a new team member to your team, allowing them to collaborate with you.') }}
</x-slot>
<x-slot name="form">
<div class="col-span-6">
<div class="max-w-xl text-sm text-gray-600">
{{ __('Please provide the email address of the person you would like to add to this team.') }}
</div>
</div>
<!-- Member Email -->
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="email" value="{{ __('Email') }}" />
<x-jet-input id="email" type="email" class="mt-1 block w-full" wire:model.defer="addTeamMemberForm.email" />
<x-jet-input-error for="email" class="mt-2" />
</div>
<!-- Role -->
@if (count($this->roles) > 0)
<div class="col-span-6 lg:col-span-4">
<x-jet-label for="role" value="{{ __('Role') }}" />
<x-jet-input-error for="role" class="mt-2" />
<div class="relative z-0 mt-1 border border-gray-200 rounded-lg cursor-pointer">
@foreach ($this->roles as $index => $role)
<button type="button" class="relative px-4 py-3 inline-flex w-full rounded-lg focus:z-10 focus:outline-none focus:border-blue-300 focus:ring focus:ring-blue-200 {{ $index > 0 ? 'border-t border-gray-200 rounded-t-none' : '' }} {{ ! $loop->last ? 'rounded-b-none' : '' }}"
wire:click="$set('addTeamMemberForm.role', '{{ $role->key }}')">
<div class="{{ isset($addTeamMemberForm['role']) && $addTeamMemberForm['role'] !== $role->key ? 'opacity-50' : '' }}">
<!-- Role Name -->
<div class="flex items-center">
<div class="text-sm text-gray-600 {{ $addTeamMemberForm['role'] == $role->key ? 'font-semibold' : '' }}">
{{ $role->name }}
</div>
@if ($addTeamMemberForm['role'] == $role->key)
<svg class="ml-2 h-5 w-5 text-green-400" fill="none" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" stroke="currentColor" viewBox="0 0 24 24"><path d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z"></path></svg>
@endif
</div>
<!-- Role Description -->
<div class="mt-2 text-xs text-gray-600 text-left">
{{ $role->description }}
</div>
</div>
</button>
@endforeach
</div>
</div>
@endif
</x-slot>
<x-slot name="actions">
<x-jet-action-message class="mr-3" on="saved">
{{ __('Added.') }}
</x-jet-action-message>
<x-jet-button>
{{ __('Add') }}
</x-jet-button>
</x-slot>
</x-jet-form-section>
</div>
@endif
@if ($team->teamInvitations->isNotEmpty() && Gate::check('addTeamMember', $team))
<x-jet-section-border />
<!-- Team Member Invitations -->
<div class="mt-10 sm:mt-0">
<x-jet-action-section>
<x-slot name="title">
{{ __('Pending Team Invitations') }}
</x-slot>
<x-slot name="description">
{{ __('These people have been invited to your team and have been sent an invitation email. They may join the team by accepting the email invitation.') }}
</x-slot>
<x-slot name="content">
<div class="space-y-6">
@foreach ($team->teamInvitations as $invitation)
<div class="flex items-center justify-between">
<div class="text-gray-600">{{ $invitation->email }}</div>
<div class="flex items-center">
@if (Gate::check('removeTeamMember', $team))
<!-- Cancel Team Invitation -->
<button class="cursor-pointer ml-6 text-sm text-red-500 focus:outline-none"
wire:click="cancelTeamInvitation({{ $invitation->id }})">
{{ __('Cancel') }}
</button>
@endif
</div>
</div>
@endforeach
</div>
</x-slot>
</x-jet-action-section>
</div>
@endif
@if ($team->users->isNotEmpty())
<x-jet-section-border />
<!-- Manage Team Members -->
<div class="mt-10 sm:mt-0">
<x-jet-action-section>
<x-slot name="title">
{{ __('Team Members') }}
</x-slot>
<x-slot name="description">
{{ __('All of the people that are part of this team.') }}
</x-slot>
<!-- Team Member List -->
<x-slot name="content">
<div class="space-y-6">
@foreach ($team->users->sortBy('name') as $user)
<div class="flex items-center justify-between">
<div class="flex items-center">
<img class="w-8 h-8 rounded-full" src="{{ $user->profile_photo_url }}" alt="{{ $user->name }}">
<div class="ml-4">{{ $user->name }}</div>
</div>
<div class="flex items-center">
<!-- Manage Team Member Role -->
@if (Gate::check('addTeamMember', $team) && Laravel\Jetstream\Jetstream::hasRoles())
<button class="ml-2 text-sm text-gray-400 underline" wire:click="manageRole('{{ $user->id }}')">
{{ Laravel\Jetstream\Jetstream::findRole($user->membership->role)->name }}
</button>
@elseif (Laravel\Jetstream\Jetstream::hasRoles())
<div class="ml-2 text-sm text-gray-400">
{{ Laravel\Jetstream\Jetstream::findRole($user->membership->role)->name }}
</div>
@endif
<!-- Leave Team -->
@if ($this->user->id === $user->id)
<button class="cursor-pointer ml-6 text-sm text-red-500" wire:click="$toggle('confirmingLeavingTeam')">
{{ __('Leave') }}
</button>
<!-- Remove Team Member -->
@elseif (Gate::check('removeTeamMember', $team))
<button class="cursor-pointer ml-6 text-sm text-red-500" wire:click="confirmTeamMemberRemoval('{{ $user->id }}')">
{{ __('Remove') }}
</button>
@endif
</div>
</div>
@endforeach
</div>
</x-slot>
</x-jet-action-section>
</div>
@endif
<!-- Role Management Modal -->
<x-jet-dialog-modal wire:model="currentlyManagingRole">
<x-slot name="title">
{{ __('Manage Role') }}
</x-slot>
<x-slot name="content">
<div class="relative z-0 mt-1 border border-gray-200 rounded-lg cursor-pointer">
@foreach ($this->roles as $index => $role)
<button type="button" class="relative px-4 py-3 inline-flex w-full rounded-lg focus:z-10 focus:outline-none focus:border-blue-300 focus:ring focus:ring-blue-200 {{ $index > 0 ? 'border-t border-gray-200 rounded-t-none' : '' }} {{ ! $loop->last ? 'rounded-b-none' : '' }}"
wire:click="$set('currentRole', '{{ $role->key }}')">
<div class="{{ $currentRole !== $role->key ? 'opacity-50' : '' }}">
<!-- Role Name -->
<div class="flex items-center">
<div class="text-sm text-gray-600 {{ $currentRole == $role->key ? 'font-semibold' : '' }}">
{{ $role->name }}
</div>
@if ($currentRole == $role->key)
<svg class="ml-2 h-5 w-5 text-green-400" fill="none" stroke-linecap="round" stroke-linejoin="round" stroke-width="2" stroke="currentColor" viewBox="0 0 24 24"><path d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z"></path></svg>
@endif
</div>
<!-- Role Description -->
<div class="mt-2 text-xs text-gray-600">
{{ $role->description }}
</div>
</div>
</button>
@endforeach
</div>
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="stopManagingRole" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-button class="ml-3" wire:click="updateRole" wire:loading.attr="disabled">
{{ __('Save') }}
</x-jet-button>
</x-slot>
</x-jet-dialog-modal>
<!-- Leave Team Confirmation Modal -->
<x-jet-confirmation-modal wire:model="confirmingLeavingTeam">
<x-slot name="title">
{{ __('Leave Team') }}
</x-slot>
<x-slot name="content">
{{ __('Are you sure you would like to leave this team?') }}
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingLeavingTeam')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-danger-button class="ml-3" wire:click="leaveTeam" wire:loading.attr="disabled">
{{ __('Leave') }}
</x-jet-danger-button>
</x-slot>
</x-jet-confirmation-modal>
<!-- Remove Team Member Confirmation Modal -->
<x-jet-confirmation-modal wire:model="confirmingTeamMemberRemoval">
<x-slot name="title">
{{ __('Remove Team Member') }}
</x-slot>
<x-slot name="content">
{{ __('Are you sure you would like to remove this person from the team?') }}
</x-slot>
<x-slot name="footer">
<x-jet-secondary-button wire:click="$toggle('confirmingTeamMemberRemoval')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-jet-secondary-button>
<x-jet-danger-button class="ml-3" wire:click="removeTeamMember" wire:loading.attr="disabled">
{{ __('Remove') }}
</x-jet-danger-button>
</x-slot>
</x-jet-confirmation-modal>
</div>
<x-jet-form-section submit="updateTeamName">
<x-slot name="title">
{{ __('Team Name') }}
</x-slot>
<x-slot name="description">
{{ __('The team\'s name and owner information.') }}
</x-slot>
<x-slot name="form">
<!-- Team Owner Information -->
<div class="col-span-6">
<x-jet-label value="{{ __('Team Owner') }}" />
<div class="flex items-center mt-2">
<img class="w-12 h-12 rounded-full object-cover" src="{{ $team->owner->profile_photo_url }}" alt="{{ $team->owner->name }}">
<div class="ml-4 leading-tight">
<div>{{ $team->owner->name }}</div>
<div class="text-gray-700 text-sm">{{ $team->owner->email }}</div>
</div>
</div>
</div>
<!-- Team Name -->
<div class="col-span-6 sm:col-span-4">
<x-jet-label for="name" value="{{ __('Team Name') }}" />
<x-jet-input id="name"
type="text"
class="mt-1 block w-full"
wire:model.defer="state.name"
:disabled="! Gate::check('update', $team)" />
<x-jet-input-error for="name" class="mt-2" />
</div>
</x-slot>
@if (Gate::check('update', $team))
<x-slot name="actions">
<x-jet-action-message class="mr-3" on="saved">
{{ __('Saved.') }}
</x-jet-action-message>
<x-jet-button>
{{ __('Save') }}
</x-jet-button>
</x-slot>
@endif
</x-jet-form-section>
<x-guest-layout>
<div class="pt-4 bg-gray-100">
<div class="min-h-screen flex flex-col items-center pt-6 sm:pt-0">
<div>
<x-jet-authentication-card-logo />
</div>
<div class="w-full sm:max-w-2xl mt-6 p-6 bg-white shadow-md overflow-hidden sm:rounded-lg prose">
{!! $terms !!}
</div>
</div>
</div>
</x-guest-layout>
...@@ -25,7 +25,7 @@ ...@@ -25,7 +25,7 @@
@if (Route::has('login')) @if (Route::has('login'))
<div class="hidden fixed top-0 right-0 px-6 py-4 sm:block"> <div class="hidden fixed top-0 right-0 px-6 py-4 sm:block">
@auth @auth
<a href="{{ asset('/home') }}" class="text-sm text-gray-700 underline">Home</a> <a href="{{ asset('/dashboard') }}" class="text-sm text-gray-700 underline">Dashboard</a>
@else @else
<a href="{{ route('login') }}" class="text-sm text-gray-700 underline">Login</a> <a href="{{ route('login') }}" class="text-sm text-gray-700 underline">Login</a>
......
File added
...@@ -14,6 +14,6 @@ use Illuminate\Support\Facades\Route; ...@@ -14,6 +14,6 @@ use Illuminate\Support\Facades\Route;
| |
*/ */
Route::middleware('auth:api')->get('/user', function (Request $request) { Route::middleware('auth:sanctum')->get('/user', function (Request $request) {
return $request->user(); return $request->user();
}); });
<?php <?php
use Illuminate\Support\Facades\Route; use Illuminate\Support\Facades\Route;
use App\Http\Controllers\Authentication\LoginController;
use App\Http\Controllers\DashboardController;
use App\Http\Controllers\JenisController; use App\Http\Controllers\JenisController;
use App\Http\Controllers\ReviewerController; use App\Http\Controllers\ReviewerController;
use App\Http\Controllers\DaftarProposalController; use App\Http\Controllers\DaftarProposalController;
use App\Http\Controllers\JadwalKegiatanController; use App\Http\Controllers\JadwalKegiatanController;
use App\Http\Controllers\JenisPenilaianMonevController; use App\Http\Controllers\JenisPenilaianMonevController;
use App\Http\Controllers\SelectController;
use App\Http\Controllers\Mahasiswa\KelompokController as MahasiswaKelompok;
use App\Http\Controllers\Mahasiswa\AnggotaController;
use App\Http\Controllers\Mahasiswa\ProposalController as MahasiswaProposal;
use App\Http\Controllers\Mahasiswa\BiodataController as BiodataMahasiswa;
use App\Http\Controllers\Mahasiswa\SeleksiController as SeleksiMahasiswa;
use App\Http\Controllers\Mahasiswa\MonevController as MonevMahasiswa;
use App\Http\Controllers\Dosen\KelompokController as DosenKelompok;
use App\Http\Controllers\Dosen\BiodataController as DosenBiodata;
use App\Http\Controllers\Dosen\ProposalController as DosenProposal;
use App\Http\Controllers\Dosen\SeleksiController as DosenSeleksi;
use App\Http\Controllers\Dosen\MonevController as DosenMonev;
/* /*
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------
...@@ -18,8 +36,87 @@ use App\Http\Controllers\JenisPenilaianMonevController; ...@@ -18,8 +36,87 @@ use App\Http\Controllers\JenisPenilaianMonevController;
| |
*/ */
// Route::get('/', function () {
// return view('mahasiswa.index');
// });
Route::get('/', function () { Route::get('/', function () {
return view('mahasiswa.index'); return view('auth.login');
});
Route::group(['namespace' => 'Authentication'], function () {
Route::get('sso/{email}/{sessionid}', [LoginController::class, 'sso']);
});
Route::group(['middleware' => ['auth:sanctum', 'verified']], function () {
Route::resource('dashboard', DashboardController::class);
Route::post('selectmahasiswa', [SelectController::class, 'mahasiswa'])->name('mahasiswa-select');
Route::name('mahasiswa.')->prefix('mahasiswa')->middleware(['role:admin|mahasiswa|tendik'])->group(function () {
//biodata
Route::resource('biodata', BiodataMahasiswa::class);
//kelompok
Route::resource('kelompok', MahasiswaKelompok::class);
Route::get('/kelompok-new/{id}', [MahasiswaKelompok::class, 'newkelompok'])->name('kelompok.createnew');
Route::post('/kelompok-kirim', [MahasiswaKelompok::class, 'kirim'])->name('kelompok.kirim');
Route::post('/kelompok-hapus', [MahasiswaKelompok::class, 'hapus'])->name('kelompok.hapus');
Route::resource('anggota', AnggotaController::class);
//proposal
Route::resource('proposal', MahasiswaProposal::class);
Route::post('/proposal-hapus', [MahasiswaProposal::class, 'hapus'])->name('proposal.hapus');
//seleksi
Route::resource('seleksi', SeleksiMahasiswa::class);
Route::get('/seleksi-internal', [SeleksiMahasiswa::class, 'seleksiInternal'])->name('seleksi-internal');
Route::get('/seleksi-belmawa', [SeleksiMahasiswa::class, 'seleksiBelmawa'])->name('seleksi-belmawa');
Route::get('/seleksi-internal-revisi', [SeleksiMahasiswa::class, 'internalRevisi'])->name('seleksi-internal-revisi');
Route::get('/seleksi-belmawa/revisi/{id}', [SeleksiMahasiswa::class, 'editBelmawa'])->name('seleksi-belmawa-revisi');
Route::post('/seleksi-belmawa/upload', [SeleksiMahasiswa::class, 'uploadBelmawa'])->name('seleksi-belmawa-upload');
//seleksi
Route::get('/monev-satu', [MonevMahasiswa::class, 'monevsatu'])->name('monev-satu');
Route::get('/monev-dua', [MonevMahasiswa::class, 'monevdua'])->name('monev-dua');
Route::get('/monev-tiga', [MonevMahasiswa::class, 'monevtiga'])->name('monev-tiga');
Route::get('/monev-revisi/{id}', [MonevMahasiswa::class, 'revisiMonev'])->name('monev-revisi');
Route::post('/monev-revisi/upload', [MonevMahasiswa::class, 'uploadMonev'])->name('monev-revisi-upload');
});
Route::name('dosen.')->prefix('dosen')->middleware(['role:admin|dosen|tendik'])->group(function () {
//biodata
Route::resource('biodata', DosenBiodata::class);
//kelompok
Route::resource('kelompok', DosenKelompok::class);
Route::get('/kelompok-new/{id}', [DosenKelompok::class, 'newkelompok'])->name('kelompok.createnew');
Route::post('/kelompok-tolak', [DosenKelompok::class, 'tolak'])->name('kelompok.tolak');
Route::post('/kelompok-terima', [DosenKelompok::class, 'terima'])->name('kelompok.terima');
//proposal
Route::resource('proposal', DosenProposal::class);
Route::post('/proposal-setuju', [DosenProposal::class, 'setuju'])->name('proposal.setuju');
//seleksi
Route::resource('seleksi', DosenSeleksi::class);
Route::get('/seleksi-internal', [DosenSeleksi::class, 'seleksiInternal'])->name('seleksi-internal');
Route::get('/seleksi-belmawa', [DosenSeleksi::class, 'seleksiBelmawa'])->name('seleksi-belmawa');
Route::get('/seleksi-internal-revisi', [DosenSeleksi::class, 'internalRevisi'])->name('seleksi-internal-revisi');
//seleksi
Route::get('/monev-satu', [DosenMonev::class, 'monevsatu'])->name('monev-satu');
Route::get('/monev-dua', [DosenMonev::class, 'monevdua'])->name('monev-duaa');
Route::get('/monev-tiga', [DosenMonev::class, 'monevtiga'])->name('monev-tiga');
});
}); });
Route::resource('jenis', JenisController::class); Route::resource('jenis', JenisController::class);
...@@ -42,3 +139,7 @@ Route::get('getDaftarProposal', [DaftarProposalController::class, 'getData'])->n ...@@ -42,3 +139,7 @@ Route::get('getDaftarProposal', [DaftarProposalController::class, 'getData'])->n
Auth::routes(); Auth::routes();
Route::get('/home', [App\Http\Controllers\HomeController::class, 'index'])->name('home'); Route::get('/home', [App\Http\Controllers\HomeController::class, 'index'])->name('home');
File added
const defaultTheme = require('tailwindcss/defaultTheme');
/** @type {import('tailwindcss').Config} */
module.exports = {
content: [
'./vendor/laravel/framework/src/Illuminate/Pagination/resources/views/*.blade.php',
'./vendor/laravel/jetstream/**/*.blade.php',
'./storage/framework/views/*.php',
'./resources/views/**/*.blade.php',
],
theme: {
extend: {
fontFamily: {
sans: ['Nunito', ...defaultTheme.fontFamily.sans],
},
},
},
plugins: [require('@tailwindcss/forms'), require('@tailwindcss/typography')],
};
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Str;
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Livewire\ApiTokenManager;
use Livewire\Livewire;
use Tests\TestCase;
class ApiTokenPermissionsTest extends TestCase
{
use RefreshDatabase;
public function test_api_token_permissions_can_be_updated()
{
if (! Features::hasApiFeatures()) {
return $this->markTestSkipped('API support is not enabled.');
}
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$token = $user->tokens()->create([
'name' => 'Test Token',
'token' => Str::random(40),
'abilities' => ['create', 'read'],
]);
Livewire::test(ApiTokenManager::class)
->set(['managingPermissionsFor' => $token])
->set(['updateApiTokenForm' => [
'permissions' => [
'delete',
'missing-permission',
],
]])
->call('updateApiToken');
$this->assertTrue($user->fresh()->tokens->first()->can('delete'));
$this->assertFalse($user->fresh()->tokens->first()->can('read'));
$this->assertFalse($user->fresh()->tokens->first()->can('missing-permission'));
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use App\Providers\RouteServiceProvider;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Tests\TestCase;
class AuthenticationTest extends TestCase
{
use RefreshDatabase;
public function test_login_screen_can_be_rendered()
{
$response = $this->get('/login');
$response->assertStatus(200);
}
public function test_users_can_authenticate_using_the_login_screen()
{
$user = User::factory()->create();
$response = $this->post('/login', [
'email' => $user->email,
'password' => 'password',
]);
$this->assertAuthenticated();
$response->assertRedirect(RouteServiceProvider::HOME);
}
public function test_users_can_not_authenticate_with_invalid_password()
{
$user = User::factory()->create();
$this->post('/login', [
'email' => $user->email,
'password' => 'wrong-password',
]);
$this->assertGuest();
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\LogoutOtherBrowserSessionsForm;
use Livewire\Livewire;
use Tests\TestCase;
class BrowserSessionsTest extends TestCase
{
use RefreshDatabase;
public function test_other_browser_sessions_can_be_logged_out()
{
$this->actingAs($user = User::factory()->create());
Livewire::test(LogoutOtherBrowserSessionsForm::class)
->set('password', 'password')
->call('logoutOtherBrowserSessions');
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Livewire\ApiTokenManager;
use Livewire\Livewire;
use Tests\TestCase;
class CreateApiTokenTest extends TestCase
{
use RefreshDatabase;
public function test_api_tokens_can_be_created()
{
if (! Features::hasApiFeatures()) {
return $this->markTestSkipped('API support is not enabled.');
}
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
Livewire::test(ApiTokenManager::class)
->set(['createApiTokenForm' => [
'name' => 'Test Token',
'permissions' => [
'read',
'update',
],
]])
->call('createApiToken');
$this->assertCount(1, $user->fresh()->tokens);
$this->assertEquals('Test Token', $user->fresh()->tokens->first()->name);
$this->assertTrue($user->fresh()->tokens->first()->can('read'));
$this->assertFalse($user->fresh()->tokens->first()->can('delete'));
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\CreateTeamForm;
use Livewire\Livewire;
use Tests\TestCase;
class CreateTeamTest extends TestCase
{
use RefreshDatabase;
public function test_teams_can_be_created()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
Livewire::test(CreateTeamForm::class)
->set(['state' => ['name' => 'Test Team']])
->call('createTeam');
$this->assertCount(2, $user->fresh()->ownedTeams);
$this->assertEquals('Test Team', $user->fresh()->ownedTeams()->latest('id')->first()->name);
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Livewire\DeleteUserForm;
use Livewire\Livewire;
use Tests\TestCase;
class DeleteAccountTest extends TestCase
{
use RefreshDatabase;
public function test_user_accounts_can_be_deleted()
{
if (! Features::hasAccountDeletionFeatures()) {
return $this->markTestSkipped('Account deletion is not enabled.');
}
$this->actingAs($user = User::factory()->create());
$component = Livewire::test(DeleteUserForm::class)
->set('password', 'password')
->call('deleteUser');
$this->assertNull($user->fresh());
}
public function test_correct_password_must_be_provided_before_account_can_be_deleted()
{
if (! Features::hasAccountDeletionFeatures()) {
return $this->markTestSkipped('Account deletion is not enabled.');
}
$this->actingAs($user = User::factory()->create());
Livewire::test(DeleteUserForm::class)
->set('password', 'wrong-password')
->call('deleteUser')
->assertHasErrors(['password']);
$this->assertNotNull($user->fresh());
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Str;
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Livewire\ApiTokenManager;
use Livewire\Livewire;
use Tests\TestCase;
class DeleteApiTokenTest extends TestCase
{
use RefreshDatabase;
public function test_api_tokens_can_be_deleted()
{
if (! Features::hasApiFeatures()) {
return $this->markTestSkipped('API support is not enabled.');
}
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$token = $user->tokens()->create([
'name' => 'Test Token',
'token' => Str::random(40),
'abilities' => ['create', 'read'],
]);
Livewire::test(ApiTokenManager::class)
->set(['apiTokenIdBeingDeleted' => $token->id])
->call('deleteApiToken');
$this->assertCount(0, $user->fresh()->tokens);
}
}
<?php
namespace Tests\Feature;
use App\Models\Team;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\DeleteTeamForm;
use Livewire\Livewire;
use Tests\TestCase;
class DeleteTeamTest extends TestCase
{
use RefreshDatabase;
public function test_teams_can_be_deleted()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$user->ownedTeams()->save($team = Team::factory()->make([
'personal_team' => false,
]));
$team->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'test-role']
);
$component = Livewire::test(DeleteTeamForm::class, ['team' => $team->fresh()])
->call('deleteTeam');
$this->assertNull($team->fresh());
$this->assertCount(0, $otherUser->fresh()->teams);
}
public function test_personal_teams_cant_be_deleted()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$component = Livewire::test(DeleteTeamForm::class, ['team' => $user->currentTeam])
->call('deleteTeam')
->assertHasErrors(['team']);
$this->assertNotNull($user->currentTeam->fresh());
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use App\Providers\RouteServiceProvider;
use Illuminate\Auth\Events\Verified;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Facades\Event;
use Illuminate\Support\Facades\URL;
use Laravel\Fortify\Features;
use Tests\TestCase;
class EmailVerificationTest extends TestCase
{
use RefreshDatabase;
public function test_email_verification_screen_can_be_rendered()
{
if (! Features::enabled(Features::emailVerification())) {
return $this->markTestSkipped('Email verification not enabled.');
}
$user = User::factory()->withPersonalTeam()->unverified()->create();
$response = $this->actingAs($user)->get('/email/verify');
$response->assertStatus(200);
}
public function test_email_can_be_verified()
{
if (! Features::enabled(Features::emailVerification())) {
return $this->markTestSkipped('Email verification not enabled.');
}
Event::fake();
$user = User::factory()->unverified()->create();
$verificationUrl = URL::temporarySignedRoute(
'verification.verify',
now()->addMinutes(60),
['id' => $user->id, 'hash' => sha1($user->email)]
);
$response = $this->actingAs($user)->get($verificationUrl);
Event::assertDispatched(Verified::class);
$this->assertTrue($user->fresh()->hasVerifiedEmail());
$response->assertRedirect(RouteServiceProvider::HOME.'?verified=1');
}
public function test_email_can_not_verified_with_invalid_hash()
{
if (! Features::enabled(Features::emailVerification())) {
return $this->markTestSkipped('Email verification not enabled.');
}
$user = User::factory()->unverified()->create();
$verificationUrl = URL::temporarySignedRoute(
'verification.verify',
now()->addMinutes(60),
['id' => $user->id, 'hash' => sha1('wrong-email')]
);
$this->actingAs($user)->get($verificationUrl);
$this->assertFalse($user->fresh()->hasVerifiedEmail());
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Facades\Mail;
use Laravel\Jetstream\Features;
use Laravel\Jetstream\Http\Livewire\TeamMemberManager;
use Laravel\Jetstream\Mail\TeamInvitation;
use Livewire\Livewire;
use Tests\TestCase;
class InviteTeamMemberTest extends TestCase
{
use RefreshDatabase;
public function test_team_members_can_be_invited_to_team()
{
if (! Features::sendsTeamInvitations()) {
return $this->markTestSkipped('Team invitations not enabled.');
}
Mail::fake();
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('addTeamMemberForm', [
'email' => 'test@example.com',
'role' => 'admin',
])->call('addTeamMember');
Mail::assertSent(TeamInvitation::class);
$this->assertCount(1, $user->currentTeam->fresh()->teamInvitations);
}
public function test_team_member_invitations_can_be_cancelled()
{
if (! Features::sendsTeamInvitations()) {
return $this->markTestSkipped('Team invitations not enabled.');
}
Mail::fake();
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
// Add the team member...
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('addTeamMemberForm', [
'email' => 'test@example.com',
'role' => 'admin',
])->call('addTeamMember');
$invitationId = $user->currentTeam->fresh()->teamInvitations->first()->id;
// Cancel the team invitation...
$component->call('cancelTeamInvitation', $invitationId);
$this->assertCount(0, $user->currentTeam->fresh()->teamInvitations);
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\TeamMemberManager;
use Livewire\Livewire;
use Tests\TestCase;
class LeaveTeamTest extends TestCase
{
use RefreshDatabase;
public function test_users_can_leave_teams()
{
$user = User::factory()->withPersonalTeam()->create();
$user->currentTeam->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'admin']
);
$this->actingAs($otherUser);
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->call('leaveTeam');
$this->assertCount(0, $user->currentTeam->fresh()->users);
}
public function test_team_owners_cant_leave_their_own_team()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->call('leaveTeam')
->assertHasErrors(['team']);
$this->assertNotNull($user->currentTeam->fresh());
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Features;
use Tests\TestCase;
class PasswordConfirmationTest extends TestCase
{
use RefreshDatabase;
public function test_confirm_password_screen_can_be_rendered()
{
$user = User::factory()->withPersonalTeam()->create();
$response = $this->actingAs($user)->get('/user/confirm-password');
$response->assertStatus(200);
}
public function test_password_can_be_confirmed()
{
$user = User::factory()->create();
$response = $this->actingAs($user)->post('/user/confirm-password', [
'password' => 'password',
]);
$response->assertRedirect();
$response->assertSessionHasNoErrors();
}
public function test_password_is_not_confirmed_with_invalid_password()
{
$user = User::factory()->create();
$response = $this->actingAs($user)->post('/user/confirm-password', [
'password' => 'wrong-password',
]);
$response->assertSessionHasErrors();
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Auth\Notifications\ResetPassword;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Facades\Notification;
use Laravel\Fortify\Features;
use Tests\TestCase;
class PasswordResetTest extends TestCase
{
use RefreshDatabase;
public function test_reset_password_link_screen_can_be_rendered()
{
if (! Features::enabled(Features::resetPasswords())) {
return $this->markTestSkipped('Password updates are not enabled.');
}
$response = $this->get('/forgot-password');
$response->assertStatus(200);
}
public function test_reset_password_link_can_be_requested()
{
if (! Features::enabled(Features::resetPasswords())) {
return $this->markTestSkipped('Password updates are not enabled.');
}
Notification::fake();
$user = User::factory()->create();
$response = $this->post('/forgot-password', [
'email' => $user->email,
]);
Notification::assertSentTo($user, ResetPassword::class);
}
public function test_reset_password_screen_can_be_rendered()
{
if (! Features::enabled(Features::resetPasswords())) {
return $this->markTestSkipped('Password updates are not enabled.');
}
Notification::fake();
$user = User::factory()->create();
$response = $this->post('/forgot-password', [
'email' => $user->email,
]);
Notification::assertSentTo($user, ResetPassword::class, function ($notification) {
$response = $this->get('/reset-password/'.$notification->token);
$response->assertStatus(200);
return true;
});
}
public function test_password_can_be_reset_with_valid_token()
{
if (! Features::enabled(Features::resetPasswords())) {
return $this->markTestSkipped('Password updates are not enabled.');
}
Notification::fake();
$user = User::factory()->create();
$response = $this->post('/forgot-password', [
'email' => $user->email,
]);
Notification::assertSentTo($user, ResetPassword::class, function ($notification) use ($user) {
$response = $this->post('/reset-password', [
'token' => $notification->token,
'email' => $user->email,
'password' => 'password',
'password_confirmation' => 'password',
]);
$response->assertSessionHasNoErrors();
return true;
});
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\UpdateProfileInformationForm;
use Livewire\Livewire;
use Tests\TestCase;
class ProfileInformationTest extends TestCase
{
use RefreshDatabase;
public function test_current_profile_information_is_available()
{
$this->actingAs($user = User::factory()->create());
$component = Livewire::test(UpdateProfileInformationForm::class);
$this->assertEquals($user->name, $component->state['name']);
$this->assertEquals($user->email, $component->state['email']);
}
public function test_profile_information_can_be_updated()
{
$this->actingAs($user = User::factory()->create());
Livewire::test(UpdateProfileInformationForm::class)
->set('state', ['name' => 'Test Name', 'email' => 'test@example.com'])
->call('updateProfileInformation');
$this->assertEquals('Test Name', $user->fresh()->name);
$this->assertEquals('test@example.com', $user->fresh()->email);
}
}
<?php
namespace Tests\Feature;
use App\Providers\RouteServiceProvider;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Fortify\Features;
use Laravel\Jetstream\Jetstream;
use Tests\TestCase;
class RegistrationTest extends TestCase
{
use RefreshDatabase;
public function test_registration_screen_can_be_rendered()
{
if (! Features::enabled(Features::registration())) {
return $this->markTestSkipped('Registration support is not enabled.');
}
$response = $this->get('/register');
$response->assertStatus(200);
}
public function test_registration_screen_cannot_be_rendered_if_support_is_disabled()
{
if (Features::enabled(Features::registration())) {
return $this->markTestSkipped('Registration support is enabled.');
}
$response = $this->get('/register');
$response->assertStatus(404);
}
public function test_new_users_can_register()
{
if (! Features::enabled(Features::registration())) {
return $this->markTestSkipped('Registration support is not enabled.');
}
$response = $this->post('/register', [
'name' => 'Test User',
'email' => 'test@example.com',
'password' => 'password',
'password_confirmation' => 'password',
'terms' => Jetstream::hasTermsAndPrivacyPolicyFeature(),
]);
$this->assertAuthenticated();
$response->assertRedirect(RouteServiceProvider::HOME);
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\TeamMemberManager;
use Livewire\Livewire;
use Tests\TestCase;
class RemoveTeamMemberTest extends TestCase
{
use RefreshDatabase;
public function test_team_members_can_be_removed_from_teams()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$user->currentTeam->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'admin']
);
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('teamMemberIdBeingRemoved', $otherUser->id)
->call('removeTeamMember');
$this->assertCount(0, $user->currentTeam->fresh()->users);
}
public function test_only_team_owner_can_remove_team_members()
{
$user = User::factory()->withPersonalTeam()->create();
$user->currentTeam->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'admin']
);
$this->actingAs($otherUser);
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('teamMemberIdBeingRemoved', $user->id)
->call('removeTeamMember')
->assertStatus(403);
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\TwoFactorAuthenticationForm;
use Livewire\Livewire;
use Tests\TestCase;
class TwoFactorAuthenticationSettingsTest extends TestCase
{
use RefreshDatabase;
public function test_two_factor_authentication_can_be_enabled()
{
$this->actingAs($user = User::factory()->create());
$this->withSession(['auth.password_confirmed_at' => time()]);
Livewire::test(TwoFactorAuthenticationForm::class)
->call('enableTwoFactorAuthentication');
$user = $user->fresh();
$this->assertNotNull($user->two_factor_secret);
$this->assertCount(8, $user->recoveryCodes());
}
public function test_recovery_codes_can_be_regenerated()
{
$this->actingAs($user = User::factory()->create());
$this->withSession(['auth.password_confirmed_at' => time()]);
$component = Livewire::test(TwoFactorAuthenticationForm::class)
->call('enableTwoFactorAuthentication')
->call('regenerateRecoveryCodes');
$user = $user->fresh();
$component->call('regenerateRecoveryCodes');
$this->assertCount(8, $user->recoveryCodes());
$this->assertCount(8, array_diff($user->recoveryCodes(), $user->fresh()->recoveryCodes()));
}
public function test_two_factor_authentication_can_be_disabled()
{
$this->actingAs($user = User::factory()->create());
$this->withSession(['auth.password_confirmed_at' => time()]);
$component = Livewire::test(TwoFactorAuthenticationForm::class)
->call('enableTwoFactorAuthentication');
$this->assertNotNull($user->fresh()->two_factor_secret);
$component->call('disableTwoFactorAuthentication');
$this->assertNull($user->fresh()->two_factor_secret);
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Support\Facades\Hash;
use Laravel\Jetstream\Http\Livewire\UpdatePasswordForm;
use Livewire\Livewire;
use Tests\TestCase;
class UpdatePasswordTest extends TestCase
{
use RefreshDatabase;
public function test_password_can_be_updated()
{
$this->actingAs($user = User::factory()->create());
Livewire::test(UpdatePasswordForm::class)
->set('state', [
'current_password' => 'password',
'password' => 'new-password',
'password_confirmation' => 'new-password',
])
->call('updatePassword');
$this->assertTrue(Hash::check('new-password', $user->fresh()->password));
}
public function test_current_password_must_be_correct()
{
$this->actingAs($user = User::factory()->create());
Livewire::test(UpdatePasswordForm::class)
->set('state', [
'current_password' => 'wrong-password',
'password' => 'new-password',
'password_confirmation' => 'new-password',
])
->call('updatePassword')
->assertHasErrors(['current_password']);
$this->assertTrue(Hash::check('password', $user->fresh()->password));
}
public function test_new_passwords_must_match()
{
$this->actingAs($user = User::factory()->create());
Livewire::test(UpdatePasswordForm::class)
->set('state', [
'current_password' => 'password',
'password' => 'new-password',
'password_confirmation' => 'wrong-password',
])
->call('updatePassword')
->assertHasErrors(['password']);
$this->assertTrue(Hash::check('password', $user->fresh()->password));
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\TeamMemberManager;
use Livewire\Livewire;
use Tests\TestCase;
class UpdateTeamMemberRoleTest extends TestCase
{
use RefreshDatabase;
public function test_team_member_roles_can_be_updated()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
$user->currentTeam->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'admin']
);
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('managingRoleFor', $otherUser)
->set('currentRole', 'editor')
->call('updateRole');
$this->assertTrue($otherUser->fresh()->hasTeamRole(
$user->currentTeam->fresh(), 'editor'
));
}
public function test_only_team_owner_can_update_team_member_roles()
{
$user = User::factory()->withPersonalTeam()->create();
$user->currentTeam->users()->attach(
$otherUser = User::factory()->create(), ['role' => 'admin']
);
$this->actingAs($otherUser);
$component = Livewire::test(TeamMemberManager::class, ['team' => $user->currentTeam])
->set('managingRoleFor', $otherUser)
->set('currentRole', 'editor')
->call('updateRole')
->assertStatus(403);
$this->assertTrue($otherUser->fresh()->hasTeamRole(
$user->currentTeam->fresh(), 'admin'
));
}
}
<?php
namespace Tests\Feature;
use App\Models\User;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Laravel\Jetstream\Http\Livewire\UpdateTeamNameForm;
use Livewire\Livewire;
use Tests\TestCase;
class UpdateTeamNameTest extends TestCase
{
use RefreshDatabase;
public function test_team_names_can_be_updated()
{
$this->actingAs($user = User::factory()->withPersonalTeam()->create());
Livewire::test(UpdateTeamNameForm::class, ['team' => $user->currentTeam])
->set(['state' => ['name' => 'Test Team']])
->call('updateTeamName');
$this->assertCount(1, $user->fresh()->ownedTeams);
$this->assertEquals('Test Team', $user->currentTeam->fresh()->name);
}
}
import { defineConfig } from 'vite';
import laravel from 'laravel-vite-plugin';
export default defineConfig({
plugins: [
laravel([
'resources/css/app.css',
'resources/js/app.js',
]),
],
});
const path = require('path');
module.exports = {
resolve: {
alias: {
'@': path.resolve('resources/js'),
},
},
};
...@@ -6,11 +6,14 @@ const mix = require('laravel-mix'); ...@@ -6,11 +6,14 @@ const mix = require('laravel-mix');
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------
| |
| Mix provides a clean, fluent API for defining some Webpack build steps | Mix provides a clean, fluent API for defining some Webpack build steps
| for your Laravel application. By default, we are compiling the Sass | for your Laravel applications. By default, we are compiling the CSS
| file for the application as well as bundling up all the JS files. | file for the application as well as bundling up all the JS files.
| |
*/ */
mix.js('resources/js/app.js', 'public/js') mix.js('resources/js/app.js', 'public/js')
.sass('resources/sass/app.scss', 'public/css') .postCss('resources/css/app.css', 'public/css', [
.sourceMaps(); require('postcss-import'),
require('tailwindcss'),
])
.webpackConfig(require('./webpack.config'));
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment