tipo: modificación del cpanel y gitignore de la carpeta vendor

This commit is contained in:
2026-07-07 11:35:09 -06:00
parent a0c91dc567
commit 676ef0d506
8510 changed files with 1132803 additions and 4 deletions
@@ -0,0 +1,17 @@
<?php
namespace App\View\Components;
use Illuminate\View\Component;
use Illuminate\View\View;
class AppLayout extends Component
{
/**
* Get the view / contents that represents the component.
*/
public function render(): View
{
return view('layouts.app');
}
}
@@ -0,0 +1,17 @@
<?php
namespace App\View\Components;
use Illuminate\View\Component;
use Illuminate\View\View;
class GuestLayout extends Component
{
/**
* Get the view / contents that represents the component.
*/
public function render(): View
{
return view('layouts.guest');
}
}
@@ -0,0 +1,6 @@
export default {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
};
@@ -0,0 +1,169 @@
<div>
<!-- Generate API Token -->
<x-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-label for="name" value="{{ __('Token Name') }}" />
<x-input id="name" type="text" class="mt-1 block w-full" wire:model="createApiTokenForm.name" autofocus />
<x-input-error for="name" class="mt-2" />
</div>
<!-- Token Permissions -->
@if (Laravel\Jetstream\Jetstream::hasPermissions())
<div class="col-span-6">
<x-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-checkbox wire:model="createApiTokenForm.permissions" :value="$permission"/>
<span class="ms-2 text-sm text-gray-600 dark:text-gray-400">{{ $permission }}</span>
</label>
@endforeach
</div>
</div>
@endif
</x-slot>
<x-slot name="actions">
<x-action-message class="me-3" on="created">
{{ __('Created.') }}
</x-action-message>
<x-button>
{{ __('Create') }}
</x-button>
</x-slot>
</x-form-section>
@if ($this->user->tokens->isNotEmpty())
<x-section-border />
<!-- Manage API Tokens -->
<div class="mt-10 sm:mt-0">
<x-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 class="break-all dark:text-white">
{{ $token->name }}
</div>
<div class="flex items-center ms-2">
@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 ms-6 text-sm text-gray-400 underline" wire:click="manageApiTokenPermissions({{ $token->id }})">
{{ __('Permissions') }}
</button>
@endif
<button class="cursor-pointer ms-6 text-sm text-red-500" wire:click="confirmApiTokenDeletion({{ $token->id }})">
{{ __('Delete') }}
</button>
</div>
</div>
@endforeach
</div>
</x-slot>
</x-action-section>
</div>
@endif
<!-- Token Value Modal -->
<x-dialog-modal wire:model.live="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-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 break-all"
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-secondary-button wire:click="$set('displayingToken', false)" wire:loading.attr="disabled">
{{ __('Close') }}
</x-secondary-button>
</x-slot>
</x-dialog-modal>
<!-- API Token Permissions Modal -->
<x-dialog-modal wire:model.live="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-checkbox wire:model="updateApiTokenForm.permissions" :value="$permission"/>
<span class="ms-2 text-sm text-gray-600 dark:text-gray-400">{{ $permission }}</span>
</label>
@endforeach
</div>
</x-slot>
<x-slot name="footer">
<x-secondary-button wire:click="$set('managingApiTokenPermissions', false)" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-button class="ms-3" wire:click="updateApiToken" wire:loading.attr="disabled">
{{ __('Save') }}
</x-button>
</x-slot>
</x-dialog-modal>
<!-- Delete Token Confirmation Modal -->
<x-confirmation-modal wire:model.live="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-secondary-button wire:click="$toggle('confirmingApiTokenDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-danger-button class="ms-3" wire:click="deleteApiToken" wire:loading.attr="disabled">
{{ __('Delete') }}
</x-danger-button>
</x-slot>
</x-confirmation-modal>
</div>
@@ -0,0 +1,13 @@
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 dark:text-gray-200 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>
@@ -0,0 +1,28 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600 dark:text-gray-400">
{{ __('This is a secure area of the application. Please confirm your password before continuing.') }}
</div>
<x-validation-errors class="mb-4" />
<form method="POST" action="{{ route('password.confirm') }}">
@csrf
<div>
<x-label for="password" value="{{ __('Password') }}" />
<x-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-button class="ms-4">
{{ __('Confirm') }}
</x-button>
</div>
</form>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,34 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600 dark:text-gray-400">
{{ __('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>
@session('status')
<div class="mb-4 font-medium text-sm text-green-600 dark:text-green-400">
{{ $value }}
</div>
@endsession
<x-validation-errors class="mb-4" />
<form method="POST" action="{{ route('password.email') }}">
@csrf
<div class="block">
<x-label for="email" value="{{ __('Email') }}" />
<x-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required autofocus autocomplete="username" />
</div>
<div class="flex items-center justify-end mt-4">
<x-button>
{{ __('Email Password Reset Link') }}
</x-button>
</div>
</form>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,48 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<x-validation-errors class="mb-4" />
@session('status')
<div class="mb-4 font-medium text-sm text-green-600 dark:text-green-400">
{{ $value }}
</div>
@endsession
<form method="POST" action="{{ route('login') }}">
@csrf
<div>
<x-label for="email" value="{{ __('Email') }}" />
<x-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required autofocus autocomplete="username" />
</div>
<div class="mt-4">
<x-label for="password" value="{{ __('Password') }}" />
<x-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-checkbox id="remember_me" name="remember" />
<span class="ms-2 text-sm text-gray-600 dark:text-gray-400">{{ __('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 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800" href="{{ route('password.request') }}">
{{ __('Forgot your password?') }}
</a>
@endif
<x-button class="ms-4">
{{ __('Log in') }}
</x-button>
</div>
</form>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,60 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<x-validation-errors class="mb-4" />
<form method="POST" action="{{ route('register') }}">
@csrf
<div>
<x-label for="name" value="{{ __('Name') }}" />
<x-input id="name" class="block mt-1 w-full" type="text" name="name" :value="old('name')" required autofocus autocomplete="name" />
</div>
<div class="mt-4">
<x-label for="email" value="{{ __('Email') }}" />
<x-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email')" required autocomplete="username" />
</div>
<div class="mt-4">
<x-label for="password" value="{{ __('Password') }}" />
<x-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="new-password" />
</div>
<div class="mt-4">
<x-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-input id="password_confirmation" class="block mt-1 w-full" type="password" name="password_confirmation" required autocomplete="new-password" />
</div>
@if (Laravel\Jetstream\Jetstream::hasTermsAndPrivacyPolicyFeature())
<div class="mt-4">
<x-label for="terms">
<div class="flex items-center">
<x-checkbox name="terms" id="terms" required />
<div class="ms-2">
{!! __('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 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800">'.__('Terms of Service').'</a>',
'privacy_policy' => '<a target="_blank" href="'.route('policy.show').'" class="underline text-sm text-gray-600 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800">'.__('Privacy Policy').'</a>',
]) !!}
</div>
</div>
</x-label>
</div>
@endif
<div class="flex items-center justify-end mt-4">
<a class="underline text-sm text-gray-600 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800" href="{{ route('login') }}">
{{ __('Already registered?') }}
</a>
<x-button class="ms-4">
{{ __('Register') }}
</x-button>
</div>
</form>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,36 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<x-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-label for="email" value="{{ __('Email') }}" />
<x-input id="email" class="block mt-1 w-full" type="email" name="email" :value="old('email', $request->email)" required autofocus autocomplete="username" />
</div>
<div class="mt-4">
<x-label for="password" value="{{ __('Password') }}" />
<x-input id="password" class="block mt-1 w-full" type="password" name="password" required autocomplete="new-password" />
</div>
<div class="mt-4">
<x-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-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-button>
{{ __('Reset Password') }}
</x-button>
</div>
</form>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,58 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<div x-data="{ recovery: false }">
<div class="mb-4 text-sm text-gray-600 dark:text-gray-400" 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 dark:text-gray-400" x-cloak x-show="recovery">
{{ __('Please confirm access to your account by entering one of your emergency recovery codes.') }}
</div>
<x-validation-errors class="mb-4" />
<form method="POST" action="{{ route('two-factor.login') }}">
@csrf
<div class="mt-4" x-show="! recovery">
<x-label for="code" value="{{ __('Code') }}" />
<x-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-cloak x-show="recovery">
<x-label for="recovery_code" value="{{ __('Recovery Code') }}" />
<x-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 dark:text-gray-400 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 dark:text-gray-400 hover:text-gray-900 underline cursor-pointer"
x-cloak
x-show="recovery"
x-on:click="
recovery = false;
$nextTick(() => { $refs.code.focus() })
">
{{ __('Use an authentication code') }}
</button>
<x-button class="ms-4">
{{ __('Log in') }}
</x-button>
</div>
</form>
</div>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,45 @@
<x-guest-layout>
<x-authentication-card>
<x-slot name="logo">
<x-authentication-card-logo />
</x-slot>
<div class="mb-4 text-sm text-gray-600 dark:text-gray-400">
{{ __('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 dark:text-green-400">
{{ __('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-button type="submit">
{{ __('Resend Verification Email') }}
</x-button>
</div>
</form>
<div>
<a
href="{{ route('profile.show') }}"
class="underline text-sm text-gray-600 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800"
>
{{ __('Edit Profile') }}</a>
<form method="POST" action="{{ route('logout') }}" class="inline">
@csrf
<button type="submit" class="underline text-sm text-gray-600 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800 ms-2">
{{ __('Log Out') }}
</button>
</form>
</div>
</div>
</x-authentication-card>
</x-guest-layout>
@@ -0,0 +1,10 @@
@props(['on'])
<div x-data="{ shown: false, timeout: null }"
x-init="@this.on('{{ $on }}', () => { clearTimeout(timeout); shown = true; timeout = setTimeout(() => { shown = false }, 2000); })"
x-show.transition.out.opacity.duration.1500ms="shown"
x-transition:leave.opacity.duration.1500ms
style="display: none;"
{{ $attributes->merge(['class' => 'text-sm text-gray-600 dark:text-gray-400']) }}>
{{ $slot->isEmpty() ? 'Saved.' : $slot }}
</div>
@@ -0,0 +1,12 @@
<div {{ $attributes->merge(['class' => 'md:grid md:grid-cols-3 md:gap-6']) }}>
<x-section-title>
<x-slot name="title">{{ $title }}</x-slot>
<x-slot name="description">{{ $description }}</x-slot>
</x-section-title>
<div class="mt-5 md:mt-0 md:col-span-2">
<div class="px-4 py-5 sm:p-6 bg-white dark:bg-gray-800 shadow sm:rounded-lg">
{{ $content }}
</div>
</div>
</div>
@@ -0,0 +1,5 @@
<svg viewBox="0 0 317 48" fill="none" xmlns="http://www.w3.org/2000/svg" {{ $attributes }}>
<path d="M74.09 30.04V13h-4.14v21H82.1v-3.96h-8.01zM95.379 19v1.77c-1.08-1.35-2.7-2.19-4.89-2.19-3.99 0-7.29 3.45-7.29 7.92s3.3 7.92 7.29 7.92c2.19 0 3.81-.84 4.89-2.19V34h3.87V19h-3.87zm-4.17 11.73c-2.37 0-4.14-1.71-4.14-4.23 0-2.52 1.77-4.23 4.14-4.23 2.4 0 4.17 1.71 4.17 4.23 0 2.52-1.77 4.23-4.17 4.23zM106.628 21.58V19h-3.87v15h3.87v-7.17c0-3.15 2.55-4.05 4.56-3.81V18.7c-1.89 0-3.78.84-4.56 2.88zM124.295 19v1.77c-1.08-1.35-2.7-2.19-4.89-2.19-3.99 0-7.29 3.45-7.29 7.92s3.3 7.92 7.29 7.92c2.19 0 3.81-.84 4.89-2.19V34h3.87V19h-3.87zm-4.17 11.73c-2.37 0-4.14-1.71-4.14-4.23 0-2.52 1.77-4.23 4.14-4.23 2.4 0 4.17 1.71 4.17 4.23 0 2.52-1.77 4.23-4.17 4.23zM141.544 19l-3.66 10.5-3.63-10.5h-4.26l5.7 15h4.41l5.7-15h-4.26zM150.354 28.09h11.31c.09-.51.15-1.02.15-1.59 0-4.41-3.15-7.92-7.59-7.92-4.71 0-7.92 3.45-7.92 7.92s3.18 7.92 8.22 7.92c2.88 0 5.13-1.17 6.54-3.21l-3.12-1.8c-.66.87-1.86 1.5-3.36 1.5-2.04 0-3.69-.84-4.23-2.82zm-.06-3c.45-1.92 1.86-3.03 3.93-3.03 1.62 0 3.24.87 3.72 3.03h-7.65zM164.516 34h3.87V12.1h-3.87V34zM185.248 34.36c3.69 0 6.9-2.01 6.9-6.3V13h-2.1v15.06c0 3.03-2.07 4.26-4.8 4.26-2.19 0-3.93-.78-4.62-2.61l-1.77 1.05c1.05 2.43 3.57 3.6 6.39 3.6zM203.124 18.64c-4.65 0-7.83 3.45-7.83 7.86 0 4.53 3.24 7.86 7.98 7.86 3.03 0 5.34-1.41 6.6-3.45l-1.74-1.02c-.81 1.44-2.46 2.55-4.83 2.55-3.18 0-5.55-1.89-5.97-4.95h13.17c.03-.3.06-.63.06-.93 0-4.11-2.85-7.92-7.44-7.92zm0 1.92c2.58 0 4.98 1.71 5.4 5.01h-11.19c.39-2.94 2.64-5.01 5.79-5.01zM221.224 20.92V19h-4.32v-4.2l-1.98.6V19h-3.15v1.92h3.15v9.09c0 3.6 2.25 4.59 6.3 3.99v-1.74c-2.91.12-4.32.33-4.32-2.25v-9.09h4.32zM225.176 22.93c0-1.62 1.59-2.37 3.15-2.37 1.44 0 2.97.57 3.6 2.1l1.65-.96c-.87-1.86-2.79-3.06-5.25-3.06-3 0-5.13 1.89-5.13 4.29 0 5.52 8.76 3.39 8.76 7.11 0 1.77-1.68 2.4-3.45 2.4-2.01 0-3.57-.99-4.11-2.52l-1.68.99c.75 1.92 2.79 3.45 5.79 3.45 3.21 0 5.43-1.77 5.43-4.32 0-5.52-8.76-3.39-8.76-7.11zM244.603 20.92V19h-4.32v-4.2l-1.98.6V19h-3.15v1.92h3.15v9.09c0 3.6 2.25 4.59 6.3 3.99v-1.74c-2.91.12-4.32.33-4.32-2.25v-9.09h4.32zM249.883 21.49V19h-1.98v15h1.98v-8.34c0-3.72 2.34-4.98 4.74-4.98v-1.92c-1.92 0-3.69.63-4.74 2.73zM263.358 18.64c-4.65 0-7.83 3.45-7.83 7.86 0 4.53 3.24 7.86 7.98 7.86 3.03 0 5.34-1.41 6.6-3.45l-1.74-1.02c-.81 1.44-2.46 2.55-4.83 2.55-3.18 0-5.55-1.89-5.97-4.95h13.17c.03-.3.06-.63.06-.93 0-4.11-2.85-7.92-7.44-7.92zm0 1.92c2.58 0 4.98 1.71 5.4 5.01h-11.19c.39-2.94 2.64-5.01 5.79-5.01zM286.848 19v2.94c-1.26-2.01-3.39-3.3-6.06-3.3-4.23 0-7.74 3.42-7.74 7.86s3.51 7.86 7.74 7.86c2.67 0 4.8-1.29 6.06-3.3V34h1.98V19h-1.98zm-5.91 13.44c-3.33 0-5.91-2.61-5.91-5.94 0-3.33 2.58-5.94 5.91-5.94s5.91 2.61 5.91 5.94c0 3.33-2.58 5.94-5.91 5.94zM309.01 18.64c-1.92 0-3.75.87-4.86 2.73-.84-1.74-2.46-2.73-4.56-2.73-1.8 0-3.42.72-4.59 2.55V19h-1.98v15H295v-8.31c0-3.72 2.16-5.13 4.32-5.13 2.13 0 3.51 1.41 3.51 4.08V34h1.98v-8.31c0-3.72 1.86-5.13 4.17-5.13 2.13 0 3.66 1.41 3.66 4.08V34h1.98v-9.36c0-3.75-2.31-6-5.61-6z" class="fill-black dark:fill-white"/>
<path d="M11.395 44.428C4.557 40.198 0 32.632 0 24 0 10.745 10.745 0 24 0a23.891 23.891 0 0113.997 4.502c-.2 17.907-11.097 33.245-26.602 39.926z" fill="#6875F5"/>
<path d="M14.134 45.885A23.914 23.914 0 0024 48c13.255 0 24-10.745 24-24 0-3.516-.756-6.856-2.115-9.866-4.659 15.143-16.608 27.092-31.75 31.751z" fill="#6875F5"/>
</svg>

After

Width:  |  Height:  |  Size: 3.3 KiB

@@ -0,0 +1,4 @@
<svg viewBox="0 0 48 48" fill="none" xmlns="http://www.w3.org/2000/svg" {{ $attributes }}>
<path d="M11.395 44.428C4.557 40.198 0 32.632 0 24 0 10.745 10.745 0 24 0a23.891 23.891 0 0113.997 4.502c-.2 17.907-11.097 33.245-26.602 39.926z" fill="#6875F5"/>
<path d="M14.134 45.885A23.914 23.914 0 0024 48c13.255 0 24-10.745 24-24 0-3.516-.756-6.856-2.115-9.866-4.659 15.143-16.608 27.092-31.75 31.751z" fill="#6875F5"/>
</svg>

After

Width:  |  Height:  |  Size: 428 B

@@ -0,0 +1,6 @@
<a href="/">
<svg class="size-16" viewbox="0 0 48 48" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M11.395 44.428C4.557 40.198 0 32.632 0 24 0 10.745 10.745 0 24 0a23.891 23.891 0 0113.997 4.502c-.2 17.907-11.097 33.245-26.602 39.926z" fill="#6875F5"/>
<path d="M14.134 45.885A23.914 23.914 0 0024 48c13.255 0 24-10.745 24-24 0-3.516-.756-6.856-2.115-9.866-4.659 15.143-16.608 27.092-31.75 31.751z" fill="#6875F5"/>
</svg>
</a>
@@ -0,0 +1,9 @@
<div class="min-h-screen flex flex-col sm:justify-center items-center pt-6 sm:pt-0 bg-gray-100 dark:bg-gray-900">
<div>
{{ $logo }}
</div>
<div class="w-full sm:max-w-md mt-6 px-6 py-4 bg-white dark:bg-gray-800 shadow-md overflow-hidden sm:rounded-lg">
{{ $slot }}
</div>
</div>
@@ -0,0 +1,48 @@
@props(['style' => session('flash.bannerStyle', 'success'), 'message' => session('flash.banner')])
<div x-data="{{ json_encode(['show' => true, 'style' => $style, 'message' => $message]) }}"
:class="{ 'bg-indigo-500': style == 'success', 'bg-red-700': style == 'danger', 'bg-yellow-500': style == 'warning', 'bg-gray-500': style != 'success' && style != 'danger' && style != 'warning'}"
style="display: none;"
x-show="show && message"
x-on:banner-message.window="
style = event.detail.style;
message = event.detail.message;
show = true;
">
<div class="max-w-screen-xl mx-auto py-2 px-3 sm:px-6 lg:px-8">
<div class="flex items-center justify-between flex-wrap">
<div class="w-0 flex-1 flex items-center min-w-0">
<span class="flex p-2 rounded-lg" :class="{ 'bg-indigo-600': style == 'success', 'bg-red-600': style == 'danger', 'bg-yellow-600': style == 'warning' }">
<svg x-show="style == 'success'" class="size-5 text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M9 12.75L11.25 15 15 9.75M21 12a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
<svg x-show="style == 'danger'" class="size-5 text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M12 9v3.75m9-.75a9 9 0 11-18 0 9 9 0 0118 0zm-9 3.75h.008v.008H12v-.008z" />
</svg>
<svg x-show="style != 'success' && style != 'danger' && style != 'warning'" class="size-5 text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M11.25 11.25l.041-.02a.75.75 0 011.063.852l-.708 2.836a.75.75 0 001.063.853l.041-.021M21 12a9 9 0 11-18 0 9 9 0 0118 0zm-9-3.75h.008v.008H12V8.25z" />
</svg>
<svg x-show="style == 'warning'" class="size-5 text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<circle cx="12" cy="12" r="10" stroke="currentColor" stroke-width="1.5" fill="none" />
<path stroke-linecap="round" stroke-linejoin="round" d="M12 8v4m0 4v.01 0 0 " />
</svg>
</span>
<p class="ms-3 font-medium text-sm text-white truncate" x-text="message"></p>
</div>
<div class="shrink-0 sm:ms-3">
<button
type="button"
class="-me-1 flex p-2 rounded-md focus:outline-none sm:-me-2 transition"
:class="{ 'hover:bg-indigo-600 focus:bg-indigo-600': style == 'success', 'hover:bg-red-600 focus:bg-red-600': style == 'danger', 'hover:bg-yellow-600 focus:bg-yellow-600': style == 'warning'}"
aria-label="Dismiss"
x-on:click="show = false">
<svg class="size-5 text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M6 18L18 6M6 6l12 12" />
</svg>
</button>
</div>
</div>
</div>
</div>
@@ -0,0 +1,3 @@
<button {{ $attributes->merge(['type' => 'submit', 'class' => 'inline-flex items-center px-4 py-2 bg-gray-800 dark:bg-gray-200 border border-transparent rounded-md font-semibold text-xs text-white dark:text-gray-800 uppercase tracking-widest hover:bg-gray-700 dark:hover:bg-white focus:bg-gray-700 dark:focus:bg-white active:bg-gray-900 dark:active:bg-gray-300 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2 dark:focus:ring-offset-gray-800 disabled:opacity-50 transition ease-in-out duration-150']) }}>
{{ $slot }}
</button>
@@ -0,0 +1 @@
<input type="checkbox" {!! $attributes->merge(['class' => 'rounded dark:bg-gray-900 border-gray-300 dark:border-gray-700 text-indigo-600 shadow-sm focus:ring-indigo-500 dark:focus:ring-indigo-600 dark:focus:ring-offset-gray-800']) !!}>
@@ -0,0 +1,27 @@
@props(['id' => null, 'maxWidth' => null])
<x-modal :id="$id" :maxWidth="$maxWidth" {{ $attributes }}>
<div class="bg-white dark:bg-gray-800 px-4 pt-5 pb-4 sm:p-6 sm:pb-4">
<div class="sm:flex sm:items-start">
<div class="mx-auto shrink-0 flex items-center justify-center size-12 rounded-full bg-red-100 sm:mx-0 sm:size-10">
<svg class="size-6 text-red-600 dark:text-red-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M12 9v3.75m-9.303 3.376c-.866 1.5.217 3.374 1.948 3.374h14.71c1.73 0 2.813-1.874 1.948-3.374L13.949 3.378c-.866-1.5-3.032-1.5-3.898 0L2.697 16.126zM12 15.75h.007v.008H12v-.008z" />
</svg>
</div>
<div class="mt-3 text-center sm:mt-0 sm:ms-4 sm:text-start">
<h3 class="text-lg font-medium text-gray-900 dark:text-gray-100">
{{ $title }}
</h3>
<div class="mt-4 text-sm text-gray-600 dark:text-gray-400">
{{ $content }}
</div>
</div>
</div>
</div>
<div class="flex flex-row justify-end px-6 py-4 bg-gray-100 dark:bg-gray-800 text-end">
{{ $footer }}
</div>
</x-modal>
@@ -0,0 +1,46 @@
@props(['title' => __('Confirm Password'), 'content' => __('For your security, please confirm your password to continue.'), 'button' => __('Confirm')])
@php
$confirmableId = md5($attributes->wire('then'));
@endphp
<span
{{ $attributes->wire('then') }}
x-data
x-ref="span"
x-on:click="$wire.startConfirmingPassword('{{ $confirmableId }}')"
x-on:password-confirmed.window="setTimeout(() => $event.detail.id === '{{ $confirmableId }}' && $refs.span.dispatchEvent(new CustomEvent('then', { bubbles: false })), 250);"
>
{{ $slot }}
</span>
@once
<x-dialog-modal wire:model.live="confirmingPassword">
<x-slot name="title">
{{ $title }}
</x-slot>
<x-slot name="content">
{{ $content }}
<div class="mt-4" x-data="{}" x-on:confirming-password.window="setTimeout(() => $refs.confirmable_password.focus(), 250)">
<x-input type="password" class="mt-1 block w-3/4" placeholder="{{ __('Password') }}" autocomplete="current-password"
x-ref="confirmable_password"
wire:model="confirmablePassword"
wire:keydown.enter="confirmPassword" />
<x-input-error for="confirmable_password" class="mt-2" />
</div>
</x-slot>
<x-slot name="footer">
<x-secondary-button wire:click="stopConfirmingPassword" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-button class="ms-3" dusk="confirm-password-button" wire:click="confirmPassword" wire:loading.attr="disabled">
{{ $button }}
</x-button>
</x-slot>
</x-dialog-modal>
@endonce
@@ -0,0 +1,3 @@
<button {{ $attributes->merge(['type' => 'button', 'class' => 'inline-flex items-center justify-center px-4 py-2 bg-red-600 border border-transparent rounded-md font-semibold text-xs text-white uppercase tracking-widest hover:bg-red-500 active:bg-red-700 focus:outline-none focus:ring-2 focus:ring-red-500 focus:ring-offset-2 dark:focus:ring-offset-gray-800 transition ease-in-out duration-150']) }}>
{{ $slot }}
</button>
@@ -0,0 +1,17 @@
@props(['id' => null, 'maxWidth' => null])
<x-modal :id="$id" :maxWidth="$maxWidth" {{ $attributes }}>
<div class="px-6 py-4">
<div class="text-lg font-medium text-gray-900 dark:text-gray-100">
{{ $title }}
</div>
<div class="mt-4 text-sm text-gray-600 dark:text-gray-400">
{{ $content }}
</div>
</div>
<div class="flex flex-row justify-end px-6 py-4 bg-gray-100 dark:bg-gray-800 text-end">
{{ $footer }}
</div>
</x-modal>
@@ -0,0 +1 @@
<a {{ $attributes->merge(['class' => 'block w-full px-4 py-2 text-start text-sm leading-5 text-gray-700 dark:text-gray-300 hover:bg-gray-100 dark:hover:bg-gray-800 focus:outline-none focus:bg-gray-100 dark:focus:bg-gray-800 transition duration-150 ease-in-out']) }}>{{ $slot }}</a>
@@ -0,0 +1,37 @@
@props(['align' => 'right', 'width' => '48', 'contentClasses' => 'py-1 bg-white dark:bg-gray-700', 'dropdownClasses' => ''])
@php
$alignmentClasses = match ($align) {
'left' => 'ltr:origin-top-left rtl:origin-top-right start-0',
'top' => 'origin-top',
'none', 'false' => '',
default => 'ltr:origin-top-right rtl:origin-top-left end-0',
};
$width = match ($width) {
'48' => 'w-48',
'60' => 'w-60',
default => 'w-48',
};
@endphp
<div class="relative" x-data="{ open: false }" @click.away="open = false" @close.stop="open = false">
<div @click="open = ! open">
{{ $trigger }}
</div>
<div x-show="open"
x-transition:enter="transition ease-out duration-200"
x-transition:enter-start="transform opacity-0 scale-95"
x-transition:enter-end="transform opacity-100 scale-100"
x-transition:leave="transition ease-in duration-75"
x-transition:leave-start="transform opacity-100 scale-100"
x-transition:leave-end="transform opacity-0 scale-95"
class="absolute z-50 mt-2 {{ $width }} rounded-md shadow-lg {{ $alignmentClasses }} {{ $dropdownClasses }}"
style="display: none;"
@click="open = false">
<div class="rounded-md ring-1 ring-black ring-opacity-5 {{ $contentClasses }}">
{{ $content }}
</div>
</div>
</div>
@@ -0,0 +1,24 @@
@props(['submit'])
<div {{ $attributes->merge(['class' => 'md:grid md:grid-cols-3 md:gap-6']) }}>
<x-section-title>
<x-slot name="title">{{ $title }}</x-slot>
<x-slot name="description">{{ $description }}</x-slot>
</x-section-title>
<div class="mt-5 md:mt-0 md:col-span-2">
<form wire:submit="{{ $submit }}">
<div class="px-4 py-5 bg-white dark:bg-gray-800 sm:p-6 shadow {{ isset($actions) ? 'sm:rounded-tl-md sm:rounded-tr-md' : 'sm:rounded-md' }}">
<div class="grid grid-cols-6 gap-6">
{{ $form }}
</div>
</div>
@if (isset($actions))
<div class="flex items-center justify-end px-4 py-3 bg-gray-50 dark:bg-gray-800 text-end sm:px-6 shadow sm:rounded-bl-md sm:rounded-br-md">
{{ $actions }}
</div>
@endif
</form>
</div>
</div>
@@ -0,0 +1,5 @@
@props(['for'])
@error($for)
<p {{ $attributes->merge(['class' => 'text-sm text-red-600 dark:text-red-400']) }}>{{ $message }}</p>
@enderror
@@ -0,0 +1,3 @@
@props(['disabled' => false])
<input {{ $disabled ? 'disabled' : '' }} {!! $attributes->merge(['class' => 'border-gray-300 dark:border-gray-700 dark:bg-gray-900 dark:text-gray-300 focus:border-indigo-500 dark:focus:border-indigo-600 focus:ring-indigo-500 dark:focus:ring-indigo-600 rounded-md shadow-sm']) !!}>
@@ -0,0 +1,5 @@
@props(['value'])
<label {{ $attributes->merge(['class' => 'block font-medium text-sm text-gray-700 dark:text-gray-300']) }}>
{{ $value ?? $slot }}
</label>
@@ -0,0 +1,43 @@
@props(['id', 'maxWidth'])
@php
$id = $id ?? md5($attributes->wire('model'));
$maxWidth = [
'sm' => 'sm:max-w-sm',
'md' => 'sm:max-w-md',
'lg' => 'sm:max-w-lg',
'xl' => 'sm:max-w-xl',
'2xl' => 'sm:max-w-2xl',
][$maxWidth ?? '2xl'];
@endphp
<div
x-data="{ show: @entangle($attributes->wire('model')) }"
x-on:close.stop="show = false"
x-on:keydown.escape.window="show = false"
x-show="show"
id="{{ $id }}"
class="jetstream-modal fixed inset-0 overflow-y-auto px-4 py-6 sm:px-0 z-50"
style="display: none;"
>
<div x-show="show" class="fixed inset-0 transform transition-all" x-on:click="show = false" x-transition:enter="ease-out duration-300"
x-transition:enter-start="opacity-0"
x-transition:enter-end="opacity-100"
x-transition:leave="ease-in duration-200"
x-transition:leave-start="opacity-100"
x-transition:leave-end="opacity-0">
<div class="absolute inset-0 bg-gray-500 dark:bg-gray-900 opacity-75"></div>
</div>
<div x-show="show" class="mb-6 bg-white dark:bg-gray-800 rounded-lg overflow-hidden shadow-xl transform transition-all sm:w-full {{ $maxWidth }} sm:mx-auto"
x-trap.inert.noscroll="show"
x-transition:enter="ease-out duration-300"
x-transition:enter-start="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
x-transition:enter-end="opacity-100 translate-y-0 sm:scale-100"
x-transition:leave="ease-in duration-200"
x-transition:leave-start="opacity-100 translate-y-0 sm:scale-100"
x-transition:leave-end="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95">
{{ $slot }}
</div>
</div>
@@ -0,0 +1,11 @@
@props(['active'])
@php
$classes = ($active ?? false)
? 'inline-flex items-center px-1 pt-1 border-b-2 border-indigo-400 dark:border-indigo-600 text-sm font-medium leading-5 text-gray-900 dark:text-gray-100 focus:outline-none focus:border-indigo-700 transition duration-150 ease-in-out'
: 'inline-flex items-center px-1 pt-1 border-b-2 border-transparent text-sm font-medium leading-5 text-gray-500 dark:text-gray-400 hover:text-gray-700 dark:hover:text-gray-300 hover:border-gray-300 dark:hover:border-gray-700 focus:outline-none focus:text-gray-700 dark:focus:text-gray-300 focus:border-gray-300 dark:focus:border-gray-700 transition duration-150 ease-in-out';
@endphp
<a {{ $attributes->merge(['class' => $classes]) }}>
{{ $slot }}
</a>
@@ -0,0 +1,11 @@
@props(['active'])
@php
$classes = ($active ?? false)
? 'block w-full ps-3 pe-4 py-2 border-l-4 border-indigo-400 dark:border-indigo-600 text-start text-base font-medium text-indigo-700 dark:text-indigo-300 bg-indigo-50 dark:bg-indigo-900/50 focus:outline-none focus:text-indigo-800 dark:focus:text-indigo-200 focus:bg-indigo-100 dark:focus:bg-indigo-900 focus:border-indigo-700 dark:focus:border-indigo-300 transition duration-150 ease-in-out'
: 'block w-full ps-3 pe-4 py-2 border-l-4 border-transparent text-start text-base font-medium text-gray-600 dark:text-gray-400 hover:text-gray-800 dark:hover:text-gray-200 hover:bg-gray-50 dark:hover:bg-gray-700 hover:border-gray-300 dark:hover:border-gray-600 focus:outline-none focus:text-gray-800 dark:focus:text-gray-200 focus:bg-gray-50 dark:focus:bg-gray-700 focus:border-gray-300 dark:focus:border-gray-600 transition duration-150 ease-in-out';
@endphp
<a {{ $attributes->merge(['class' => $classes]) }}>
{{ $slot }}
</a>
@@ -0,0 +1,3 @@
<button {{ $attributes->merge(['type' => 'button', 'class' => 'inline-flex items-center px-4 py-2 bg-white dark:bg-gray-800 border border-gray-300 dark:border-gray-500 rounded-md font-semibold text-xs text-gray-700 dark:text-gray-300 uppercase tracking-widest shadow-sm hover:bg-gray-50 dark:hover:bg-gray-700 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2 dark:focus:ring-offset-gray-800 disabled:opacity-25 transition ease-in-out duration-150']) }}>
{{ $slot }}
</button>
@@ -0,0 +1,5 @@
<div class="hidden sm:block">
<div class="py-8">
<div class="border-t border-gray-200 dark:border-gray-700"></div>
</div>
</div>
@@ -0,0 +1,13 @@
<div class="md:col-span-1 flex justify-between">
<div class="px-4 sm:px-0">
<h3 class="text-lg font-medium text-gray-900 dark:text-gray-100">{{ $title }}</h3>
<p class="mt-1 text-sm text-gray-600 dark:text-gray-400">
{{ $description }}
</p>
</div>
<div class="px-4 sm:px-0">
{{ $aside ?? '' }}
</div>
</div>
@@ -0,0 +1,21 @@
@props(['team', 'component' => 'dropdown-link'])
<form method="POST" action="{{ route('current-team.update') }}" x-data>
@method('PUT')
@csrf
<!-- Hidden Team ID -->
<input type="hidden" name="team_id" value="{{ $team->id }}">
<x-dynamic-component :component="$component" href="#" x-on:click.prevent="$root.submit();">
<div class="flex items-center">
@if (Auth::user()->isCurrentTeam($team))
<svg class="me-2 size-5 text-green-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M9 12.75L11.25 15 15 9.75M21 12a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
@endif
<div class="truncate">{{ $team->name }}</div>
</div>
</x-dynamic-component>
</form>
@@ -0,0 +1,11 @@
@if ($errors->any())
<div {{ $attributes }}>
<div class="font-medium text-red-600 dark:text-red-400">{{ __('Whoops! Something went wrong.') }}</div>
<ul class="mt-3 list-disc list-inside text-sm text-red-600 dark:text-red-400">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
@@ -0,0 +1,96 @@
<div class="p-6 lg:p-8 bg-white dark:bg-gray-800 dark:bg-gradient-to-bl dark:from-gray-700/50 dark:via-transparent border-b border-gray-200 dark:border-gray-700">
<x-application-logo class="block h-12 w-auto" />
<h1 class="mt-8 text-2xl font-medium text-gray-900 dark:text-white">
Welcome to your Jetstream application!
</h1>
<p class="mt-6 text-gray-500 dark:text-gray-400 leading-relaxed">
Laravel Jetstream provides a beautiful, robust starting point for your next Laravel application. Laravel is designed
to help you build your application using a development environment that is simple, powerful, and enjoyable. We believe
you should love expressing your creativity through programming, so we have spent time carefully crafting the Laravel
ecosystem to be a breath of fresh air. We hope you love it.
</p>
</div>
<div class="bg-gray-200 dark:bg-gray-800 bg-opacity-25 grid grid-cols-1 md:grid-cols-2 gap-6 lg:gap-8 p-6 lg:p-8">
<div>
<div class="flex items-center">
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" class="size-6 stroke-gray-400">
<path stroke-linecap="round" stroke-linejoin="round" d="M12 6.042A8.967 8.967 0 006 3.75c-1.052 0-2.062.18-3 .512v14.25A8.987 8.987 0 016 18c2.305 0 4.408.867 6 2.292m0-14.25a8.966 8.966 0 016-2.292c1.052 0 2.062.18 3 .512v14.25A8.987 8.987 0 0018 18a8.967 8.967 0 00-6 2.292m0-14.25v14.25" />
</svg>
<h2 class="ms-3 text-xl font-semibold text-gray-900 dark:text-white">
<a href="https://laravel.com/docs">Documentation</a>
</h2>
</div>
<p class="mt-4 text-gray-500 dark:text-gray-400 text-sm leading-relaxed">
Laravel has wonderful documentation covering every aspect of the framework. Whether you're new to the framework or have previous experience, we recommend reading all of the documentation from beginning to end.
</p>
<p class="mt-4 text-sm">
<a href="https://laravel.com/docs" class="inline-flex items-center font-semibold text-indigo-700 dark:text-indigo-300">
Explore the documentation
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" class="ms-1 size-5 fill-indigo-500 dark:fill-indigo-200">
<path fill-rule="evenodd" d="M5 10a.75.75 0 01.75-.75h6.638L10.23 7.29a.75.75 0 111.04-1.08l3.5 3.25a.75.75 0 010 1.08l-3.5 3.25a.75.75 0 11-1.04-1.08l2.158-1.96H5.75A.75.75 0 015 10z" clip-rule="evenodd" />
</svg>
</a>
</p>
</div>
<div>
<div class="flex items-center">
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" class="size-6 stroke-gray-400">
<path stroke-linecap="round" d="M15.75 10.5l4.72-4.72a.75.75 0 011.28.53v11.38a.75.75 0 01-1.28.53l-4.72-4.72M4.5 18.75h9a2.25 2.25 0 002.25-2.25v-9a2.25 2.25 0 00-2.25-2.25h-9A2.25 2.25 0 002.25 7.5v9a2.25 2.25 0 002.25 2.25z" />
</svg>
<h2 class="ms-3 text-xl font-semibold text-gray-900 dark:text-white">
<a href="https://laracasts.com">Laracasts</a>
</h2>
</div>
<p class="mt-4 text-gray-500 dark:text-gray-400 text-sm leading-relaxed">
Laracasts offers thousands of video tutorials on Laravel, PHP, and JavaScript development. Check them out, see for yourself, and massively level up your development skills in the process.
</p>
<p class="mt-4 text-sm">
<a href="https://laracasts.com" class="inline-flex items-center font-semibold text-indigo-700 dark:text-indigo-300">
Start watching Laracasts
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" class="ms-1 size-5 fill-indigo-500 dark:fill-indigo-200">
<path fill-rule="evenodd" d="M5 10a.75.75 0 01.75-.75h6.638L10.23 7.29a.75.75 0 111.04-1.08l3.5 3.25a.75.75 0 010 1.08l-3.5 3.25a.75.75 0 11-1.04-1.08l2.158-1.96H5.75A.75.75 0 015 10z" clip-rule="evenodd" />
</svg>
</a>
</p>
</div>
<div>
<div class="flex items-center">
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" class="size-6 stroke-gray-400">
<path stroke-linecap="round" stroke-linejoin="round" d="M2.25 15.75l5.159-5.159a2.25 2.25 0 013.182 0l5.159 5.159m-1.5-1.5l1.409-1.409a2.25 2.25 0 013.182 0l2.909 2.909m-18 3.75h16.5a1.5 1.5 0 001.5-1.5V6a1.5 1.5 0 00-1.5-1.5H3.75A1.5 1.5 0 002.25 6v12a1.5 1.5 0 001.5 1.5zm10.5-11.25h.008v.008h-.008V8.25zm.375 0a.375.375 0 11-.75 0 .375.375 0 01.75 0z" />
</svg>
<h2 class="ms-3 text-xl font-semibold text-gray-900 dark:text-white">
<a href="https://tailwindcss.com/">Tailwind</a>
</h2>
</div>
<p class="mt-4 text-gray-500 dark:text-gray-400 text-sm leading-relaxed">
Laravel Jetstream is built with Tailwind, an amazing utility first CSS framework that doesn't get in your way. You'll be amazed how easily you can build and maintain fresh, modern designs with this wonderful framework at your fingertips.
</p>
</div>
<div>
<div class="flex items-center">
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" class="size-6 stroke-gray-400">
<path stroke-linecap="round" stroke-linejoin="round" d="M16.5 10.5V6.75a4.5 4.5 0 10-9 0v3.75m-.75 11.25h10.5a2.25 2.25 0 002.25-2.25v-6.75a2.25 2.25 0 00-2.25-2.25H6.75a2.25 2.25 0 00-2.25 2.25v6.75a2.25 2.25 0 002.25 2.25z" />
</svg>
<h2 class="ms-3 text-xl font-semibold text-gray-900 dark:text-white">
Authentication
</h2>
</div>
<p class="mt-4 text-gray-500 dark:text-gray-400 text-sm leading-relaxed">
Authentication and registration views are included with Laravel Jetstream, as well as support for user email verification and resetting forgotten passwords. So, you're free to get started with what matters most: building your application.
</p>
</div>
</div>
@@ -0,0 +1,15 @@
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 dark:text-gray-200 leading-tight">
{{ __('Dashboard') }}
</h2>
</x-slot>
<div class="py-12">
<div class="max-w-7xl mx-auto sm:px-6 lg:px-8">
<div class="bg-white dark:bg-gray-800 overflow-hidden shadow-xl sm:rounded-lg">
<x-welcome />
</div>
</div>
</div>
</x-app-layout>
@@ -0,0 +1,45 @@
<!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="preconnect" href="https://fonts.bunny.net">
<link href="https://fonts.bunny.net/css?family=figtree:400,500,600&display=swap" rel="stylesheet" />
<!-- Scripts -->
@vite(['resources/css/app.css', 'resources/js/app.js'])
<!-- Styles -->
@livewireStyles
</head>
<body class="font-sans antialiased">
<x-banner />
<div class="min-h-screen bg-gray-100 dark:bg-gray-900">
@livewire('navigation-menu')
<!-- Page Heading -->
@if (isset($header))
<header class="bg-white dark:bg-gray-800 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>
@@ -0,0 +1,27 @@
<!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="preconnect" href="https://fonts.bunny.net">
<link href="https://fonts.bunny.net/css?family=figtree:400,500,600&display=swap" rel="stylesheet" />
<!-- Scripts -->
@vite(['resources/css/app.css', 'resources/js/app.js'])
<!-- Styles -->
@livewireStyles
</head>
<body>
<div class="font-sans text-gray-900 dark:text-gray-100 antialiased">
{{ $slot }}
</div>
@livewireScripts
</body>
</html>
@@ -0,0 +1,219 @@
<nav x-data="{ open: false }" class="bg-white dark:bg-gray-800 border-b border-gray-100 dark:border-gray-700">
<!-- 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-application-mark class="block h-9 w-auto" />
</a>
</div>
<!-- Navigation Links -->
<div class="hidden space-x-8 sm:-my-px sm:ms-10 sm:flex">
<x-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-nav-link>
</div>
</div>
<div class="hidden sm:flex sm:items-center sm:ms-6">
<!-- Teams Dropdown -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="ms-3 relative">
<x-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 dark:text-gray-400 bg-white dark:bg-gray-800 hover:text-gray-700 dark:hover:text-gray-300 focus:outline-none focus:bg-gray-50 dark:focus:bg-gray-700 active:bg-gray-50 dark:active:bg-gray-700 transition ease-in-out duration-150">
{{ Auth::user()->currentTeam->name }}
<svg class="ms-2 -me-0.5 size-4" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M8.25 15L12 18.75 15.75 15m-7.5-6L12 5.25 15.75 9" />
</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-dropdown-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}">
{{ __('Team Settings') }}
</x-dropdown-link>
@can('create', Laravel\Jetstream\Jetstream::newTeamModel())
<x-dropdown-link href="{{ route('teams.create') }}">
{{ __('Create New Team') }}
</x-dropdown-link>
@endcan
<!-- Team Switcher -->
@if (Auth::user()->allTeams()->count() > 1)
<div class="border-t border-gray-200 dark:border-gray-600"></div>
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-switchable-team :team="$team" />
@endforeach
@endif
</div>
</x-slot>
</x-dropdown>
</div>
@endif
<!-- Settings Dropdown -->
<div class="ms-3 relative">
<x-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="size-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 dark:text-gray-400 bg-white dark:bg-gray-800 hover:text-gray-700 dark:hover:text-gray-300 focus:outline-none focus:bg-gray-50 dark:focus:bg-gray-700 active:bg-gray-50 dark:active:bg-gray-700 transition ease-in-out duration-150">
{{ Auth::user()->name }}
<svg class="ms-2 -me-0.5 size-4" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M19.5 8.25l-7.5 7.5-7.5-7.5" />
</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-dropdown-link href="{{ route('profile.show') }}">
{{ __('Profile') }}
</x-dropdown-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-dropdown-link href="{{ route('api-tokens.index') }}">
{{ __('API Tokens') }}
</x-dropdown-link>
@endif
<div class="border-t border-gray-200 dark:border-gray-600"></div>
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}" x-data>
@csrf
<x-dropdown-link href="{{ route('logout') }}"
@click.prevent="$root.submit();">
{{ __('Log Out') }}
</x-dropdown-link>
</form>
</x-slot>
</x-dropdown>
</div>
</div>
<!-- Hamburger -->
<div class="-me-2 flex items-center sm:hidden">
<button @click="open = ! open" class="inline-flex items-center justify-center p-2 rounded-md text-gray-400 dark:text-gray-500 hover:text-gray-500 dark:hover:text-gray-400 hover:bg-gray-100 dark:hover:bg-gray-900 focus:outline-none focus:bg-gray-100 dark:focus:bg-gray-900 focus:text-gray-500 dark:focus:text-gray-400 transition duration-150 ease-in-out">
<svg class="size-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-responsive-nav-link href="{{ route('dashboard') }}" :active="request()->routeIs('dashboard')">
{{ __('Dashboard') }}
</x-responsive-nav-link>
</div>
<!-- Responsive Settings Options -->
<div class="pt-4 pb-1 border-t border-gray-200 dark:border-gray-600">
<div class="flex items-center px-4">
@if (Laravel\Jetstream\Jetstream::managesProfilePhotos())
<div class="shrink-0 me-3">
<img class="size-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 dark:text-gray-200">{{ 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-responsive-nav-link href="{{ route('profile.show') }}" :active="request()->routeIs('profile.show')">
{{ __('Profile') }}
</x-responsive-nav-link>
@if (Laravel\Jetstream\Jetstream::hasApiFeatures())
<x-responsive-nav-link href="{{ route('api-tokens.index') }}" :active="request()->routeIs('api-tokens.index')">
{{ __('API Tokens') }}
</x-responsive-nav-link>
@endif
<!-- Authentication -->
<form method="POST" action="{{ route('logout') }}" x-data>
@csrf
<x-responsive-nav-link href="{{ route('logout') }}"
@click.prevent="$root.submit();">
{{ __('Log Out') }}
</x-responsive-nav-link>
</form>
<!-- Team Management -->
@if (Laravel\Jetstream\Jetstream::hasTeamFeatures())
<div class="border-t border-gray-200 dark:border-gray-600"></div>
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Manage Team') }}
</div>
<!-- Team Settings -->
<x-responsive-nav-link href="{{ route('teams.show', Auth::user()->currentTeam->id) }}" :active="request()->routeIs('teams.show')">
{{ __('Team Settings') }}
</x-responsive-nav-link>
@can('create', Laravel\Jetstream\Jetstream::newTeamModel())
<x-responsive-nav-link href="{{ route('teams.create') }}" :active="request()->routeIs('teams.create')">
{{ __('Create New Team') }}
</x-responsive-nav-link>
@endcan
<!-- Team Switcher -->
@if (Auth::user()->allTeams()->count() > 1)
<div class="border-t border-gray-200 dark:border-gray-600"></div>
<div class="block px-4 py-2 text-xs text-gray-400">
{{ __('Switch Teams') }}
</div>
@foreach (Auth::user()->allTeams() as $team)
<x-switchable-team :team="$team" component="responsive-nav-link" />
@endforeach
@endif
@endif
</div>
</div>
</div>
</nav>
@@ -0,0 +1,13 @@
<x-guest-layout>
<div class="pt-4 bg-gray-100 dark:bg-gray-900">
<div class="min-h-screen flex flex-col items-center pt-6 sm:pt-0">
<div>
<x-authentication-card-logo />
</div>
<div class="w-full sm:max-w-2xl mt-6 p-6 bg-white dark:bg-gray-800 shadow-md overflow-hidden sm:rounded-lg prose dark:prose-invert">
{!! $policy !!}
</div>
</div>
</div>
</x-guest-layout>
@@ -0,0 +1,53 @@
<x-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 dark:text-gray-400">
{{ __('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-danger-button wire:click="confirmUserDeletion" wire:loading.attr="disabled">
{{ __('Delete Account') }}
</x-danger-button>
</div>
<!-- Delete User Confirmation Modal -->
<x-dialog-modal wire:model.live="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-input type="password" class="mt-1 block w-3/4"
autocomplete="current-password"
placeholder="{{ __('Password') }}"
x-ref="password"
wire:model="password"
wire:keydown.enter="deleteUser" />
<x-input-error for="password" class="mt-2" />
</div>
</x-slot>
<x-slot name="footer">
<x-secondary-button wire:click="$toggle('confirmingUserDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-danger-button class="ms-3" wire:click="deleteUser" wire:loading.attr="disabled">
{{ __('Delete Account') }}
</x-danger-button>
</x-slot>
</x-dialog-modal>
</x-slot>
</x-action-section>
@@ -0,0 +1,98 @@
<x-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 dark:text-gray-400">
{{ __('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 xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="size-8 text-gray-500">
<path stroke-linecap="round" stroke-linejoin="round" d="M9 17.25v1.007a3 3 0 01-.879 2.122L7.5 21h9l-.621-.621A3 3 0 0115 18.257V17.25m6-12V15a2.25 2.25 0 01-2.25 2.25H5.25A2.25 2.25 0 013 15V5.25m18 0A2.25 2.25 0 0018.75 3H5.25A2.25 2.25 0 003 5.25m18 0V12a2.25 2.25 0 01-2.25 2.25H5.25A2.25 2.25 0 013 12V5.25" />
</svg>
@else
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="size-8 text-gray-500">
<path stroke-linecap="round" stroke-linejoin="round" d="M10.5 1.5H8.25A2.25 2.25 0 006 3.75v16.5a2.25 2.25 0 002.25 2.25h7.5A2.25 2.25 0 0018 20.25V3.75a2.25 2.25 0 00-2.25-2.25H13.5m-3 0V3h3V1.5m-3 0h3m-3 18.75h3" />
</svg>
@endif
</div>
<div class="ms-3">
<div class="text-sm text-gray-600 dark:text-gray-400">
{{ $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-button wire:click="confirmLogout" wire:loading.attr="disabled">
{{ __('Log Out Other Browser Sessions') }}
</x-button>
<x-action-message class="ms-3" on="loggedOut">
{{ __('Done.') }}
</x-action-message>
</div>
<!-- Log Out Other Devices Confirmation Modal -->
<x-dialog-modal wire:model.live="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-input type="password" class="mt-1 block w-3/4"
autocomplete="current-password"
placeholder="{{ __('Password') }}"
x-ref="password"
wire:model="password"
wire:keydown.enter="logoutOtherBrowserSessions" />
<x-input-error for="password" class="mt-2" />
</div>
</x-slot>
<x-slot name="footer">
<x-secondary-button wire:click="$toggle('confirmingLogout')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-button class="ms-3"
wire:click="logoutOtherBrowserSessions"
wire:loading.attr="disabled">
{{ __('Log Out Other Browser Sessions') }}
</x-button>
</x-slot>
</x-dialog-modal>
</x-slot>
</x-action-section>
@@ -0,0 +1,45 @@
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 dark:text-gray-200 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-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-section-border />
@endif
@if (Laravel\Fortify\Features::canManageTwoFactorAuthentication())
<div class="mt-10 sm:mt-0">
@livewire('profile.two-factor-authentication-form')
</div>
<x-section-border />
@endif
<div class="mt-10 sm:mt-0">
@livewire('profile.logout-other-browser-sessions-form')
</div>
@if (Laravel\Jetstream\Jetstream::hasAccountDeletionFeatures())
<x-section-border />
<div class="mt-10 sm:mt-0">
@livewire('profile.delete-user-form')
</div>
@endif
</div>
</div>
</x-app-layout>
@@ -0,0 +1,124 @@
<x-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 dark:text-gray-100">
@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 dark:text-gray-400">
<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 dark:text-gray-400">
<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 p-2 inline-block bg-white">
{!! $this->user->twoFactorQrCodeSvg() !!}
</div>
<div class="mt-4 max-w-xl text-sm text-gray-600 dark:text-gray-400">
<p class="font-semibold">
{{ __('Setup Key') }}: {{ decrypt($this->user->two_factor_secret) }}
</p>
</div>
@if ($showingConfirmation)
<div class="mt-4">
<x-label for="code" value="{{ __('Code') }}" />
<x-input id="code" type="text" name="code" class="block mt-1 w-1/2" inputmode="numeric" autofocus autocomplete="one-time-code"
wire:model="code"
wire:keydown.enter="confirmTwoFactorAuthentication" />
<x-input-error for="code" class="mt-2" />
</div>
@endif
@endif
@if ($showingRecoveryCodes)
<div class="mt-4 max-w-xl text-sm text-gray-600 dark:text-gray-400">
<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 dark:bg-gray-900 dark:text-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-confirms-password wire:then="enableTwoFactorAuthentication">
<x-button type="button" wire:loading.attr="disabled">
{{ __('Enable') }}
</x-button>
</x-confirms-password>
@else
@if ($showingRecoveryCodes)
<x-confirms-password wire:then="regenerateRecoveryCodes">
<x-secondary-button class="me-3">
{{ __('Regenerate Recovery Codes') }}
</x-secondary-button>
</x-confirms-password>
@elseif ($showingConfirmation)
<x-confirms-password wire:then="confirmTwoFactorAuthentication">
<x-button type="button" class="me-3" wire:loading.attr="disabled">
{{ __('Confirm') }}
</x-button>
</x-confirms-password>
@else
<x-confirms-password wire:then="showRecoveryCodes">
<x-secondary-button class="me-3">
{{ __('Show Recovery Codes') }}
</x-secondary-button>
</x-confirms-password>
@endif
@if ($showingConfirmation)
<x-confirms-password wire:then="disableTwoFactorAuthentication">
<x-secondary-button wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
</x-confirms-password>
@else
<x-confirms-password wire:then="disableTwoFactorAuthentication">
<x-danger-button wire:loading.attr="disabled">
{{ __('Disable') }}
</x-danger-button>
</x-confirms-password>
@endif
@endif
</div>
</x-slot>
</x-action-section>
@@ -0,0 +1,39 @@
<x-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-label for="current_password" value="{{ __('Current Password') }}" />
<x-input id="current_password" type="password" class="mt-1 block w-full" wire:model="state.current_password" autocomplete="current-password" />
<x-input-error for="current_password" class="mt-2" />
</div>
<div class="col-span-6 sm:col-span-4">
<x-label for="password" value="{{ __('New Password') }}" />
<x-input id="password" type="password" class="mt-1 block w-full" wire:model="state.password" autocomplete="new-password" />
<x-input-error for="password" class="mt-2" />
</div>
<div class="col-span-6 sm:col-span-4">
<x-label for="password_confirmation" value="{{ __('Confirm Password') }}" />
<x-input id="password_confirmation" type="password" class="mt-1 block w-full" wire:model="state.password_confirmation" autocomplete="new-password" />
<x-input-error for="password_confirmation" class="mt-2" />
</div>
</x-slot>
<x-slot name="actions">
<x-action-message class="me-3" on="saved">
{{ __('Saved.') }}
</x-action-message>
<x-button>
{{ __('Save') }}
</x-button>
</x-slot>
</x-form-section>
@@ -0,0 +1,95 @@
<x-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" id="photo" class="hidden"
wire:model.live="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-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 size-20 object-cover">
</div>
<!-- New Profile Photo Preview -->
<div class="mt-2" x-show="photoPreview" style="display: none;">
<span class="block rounded-full size-20 bg-cover bg-no-repeat bg-center"
x-bind:style="'background-image: url(\'' + photoPreview + '\');'">
</span>
</div>
<x-secondary-button class="mt-2 me-2" type="button" x-on:click.prevent="$refs.photo.click()">
{{ __('Select A New Photo') }}
</x-secondary-button>
@if ($this->user->profile_photo_path)
<x-secondary-button type="button" class="mt-2" wire:click="deleteProfilePhoto">
{{ __('Remove Photo') }}
</x-secondary-button>
@endif
<x-input-error for="photo" class="mt-2" />
</div>
@endif
<!-- Name -->
<div class="col-span-6 sm:col-span-4">
<x-label for="name" value="{{ __('Name') }}" />
<x-input id="name" type="text" class="mt-1 block w-full" wire:model="state.name" required autocomplete="name" />
<x-input-error for="name" class="mt-2" />
</div>
<!-- Email -->
<div class="col-span-6 sm:col-span-4">
<x-label for="email" value="{{ __('Email') }}" />
<x-input id="email" type="email" class="mt-1 block w-full" wire:model="state.email" required autocomplete="username" />
<x-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 dark:text-white">
{{ __('Your email address is unverified.') }}
<button type="button" class="underline text-sm text-gray-600 dark:text-gray-400 hover:text-gray-900 dark:hover:text-gray-100 rounded-md focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 dark:focus:ring-offset-gray-800" wire:click.prevent="sendEmailVerification">
{{ __('Click here to re-send the verification email.') }}
</button>
</p>
@if ($this->verificationLinkSent)
<p class="mt-2 font-medium text-sm text-green-600 dark:text-green-400">
{{ __('A new verification link has been sent to your email address.') }}
</p>
@endif
@endif
</div>
</x-slot>
<x-slot name="actions">
<x-action-message class="me-3" on="saved">
{{ __('Saved.') }}
</x-action-message>
<x-button wire:loading.attr="disabled" wire:target="photo">
{{ __('Save') }}
</x-button>
</x-slot>
</x-form-section>
@@ -0,0 +1,36 @@
<x-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-label value="{{ __('Team Owner') }}" />
<div class="flex items-center mt-2">
<img class="size-12 rounded-full object-cover" src="{{ $this->user->profile_photo_url }}" alt="{{ $this->user->name }}">
<div class="ms-4 leading-tight">
<div class="text-gray-900 dark:text-white">{{ $this->user->name }}</div>
<div class="text-gray-700 dark:text-gray-300 text-sm">{{ $this->user->email }}</div>
</div>
</div>
</div>
<div class="col-span-6 sm:col-span-4">
<x-label for="name" value="{{ __('Team Name') }}" />
<x-input id="name" type="text" class="mt-1 block w-full" wire:model="state.name" autofocus />
<x-input-error for="name" class="mt-2" />
</div>
</x-slot>
<x-slot name="actions">
<x-button>
{{ __('Create') }}
</x-button>
</x-slot>
</x-form-section>
@@ -0,0 +1,13 @@
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 dark:text-gray-200 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>
@@ -0,0 +1,42 @@
<x-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 dark:text-gray-400">
{{ __('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-danger-button wire:click="$toggle('confirmingTeamDeletion')" wire:loading.attr="disabled">
{{ __('Delete Team') }}
</x-danger-button>
</div>
<!-- Delete Team Confirmation Modal -->
<x-confirmation-modal wire:model.live="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-secondary-button wire:click="$toggle('confirmingTeamDeletion')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-danger-button class="ms-3" wire:click="deleteTeam" wire:loading.attr="disabled">
{{ __('Delete Team') }}
</x-danger-button>
</x-slot>
</x-confirmation-modal>
</x-slot>
</x-action-section>
@@ -0,0 +1,23 @@
<x-app-layout>
<x-slot name="header">
<h2 class="font-semibold text-xl text-gray-800 dark:text-gray-200 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-section-border />
<div class="mt-10 sm:mt-0">
@livewire('teams.delete-team-form', ['team' => $team])
</div>
@endif
</div>
</div>
</x-app-layout>
@@ -0,0 +1,260 @@
<div>
@if (Gate::check('addTeamMember', $team))
<x-section-border />
<!-- Add Team Member -->
<div class="mt-10 sm:mt-0">
<x-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 dark:text-gray-400">
{{ __('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-label for="email" value="{{ __('Email') }}" />
<x-input id="email" type="email" class="mt-1 block w-full" wire:model="addTeamMemberForm.email" />
<x-input-error for="email" class="mt-2" />
</div>
<!-- Role -->
@if (count($this->roles) > 0)
<div class="col-span-6 lg:col-span-4">
<x-label for="role" value="{{ __('Role') }}" />
<x-input-error for="role" class="mt-2" />
<div class="relative z-0 mt-1 border border-gray-200 dark:border-gray-700 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-indigo-500 dark:focus:border-indigo-600 focus:ring-2 focus:ring-indigo-500 dark:focus:ring-indigo-600 {{ $index > 0 ? 'border-t border-gray-200 dark:border-gray-700 focus:border-none 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 dark:text-gray-400 {{ $addTeamMemberForm['role'] == $role->key ? 'font-semibold' : '' }}">
{{ $role->name }}
</div>
@if ($addTeamMemberForm['role'] == $role->key)
<svg class="ms-2 size-5 text-green-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M9 12.75L11.25 15 15 9.75M21 12a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
@endif
</div>
<!-- Role Description -->
<div class="mt-2 text-xs text-gray-600 dark:text-gray-400 text-start">
{{ $role->description }}
</div>
</div>
</button>
@endforeach
</div>
</div>
@endif
</x-slot>
<x-slot name="actions">
<x-action-message class="me-3" on="saved">
{{ __('Added.') }}
</x-action-message>
<x-button>
{{ __('Add') }}
</x-button>
</x-slot>
</x-form-section>
</div>
@endif
@if ($team->teamInvitations->isNotEmpty() && Gate::check('addTeamMember', $team))
<x-section-border />
<!-- Team Member Invitations -->
<div class="mt-10 sm:mt-0">
<x-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 dark:text-gray-400">{{ $invitation->email }}</div>
<div class="flex items-center">
@if (Gate::check('removeTeamMember', $team))
<!-- Cancel Team Invitation -->
<button class="cursor-pointer ms-6 text-sm text-red-500 focus:outline-none"
wire:click="cancelTeamInvitation({{ $invitation->id }})">
{{ __('Cancel') }}
</button>
@endif
</div>
</div>
@endforeach
</div>
</x-slot>
</x-action-section>
</div>
@endif
@if ($team->users->isNotEmpty())
<x-section-border />
<!-- Manage Team Members -->
<div class="mt-10 sm:mt-0">
<x-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="size-8 rounded-full object-cover" src="{{ $user->profile_photo_url }}" alt="{{ $user->name }}">
<div class="ms-4 dark:text-white">{{ $user->name }}</div>
</div>
<div class="flex items-center">
<!-- Manage Team Member Role -->
@if (Gate::check('updateTeamMember', $team) && Laravel\Jetstream\Jetstream::hasRoles())
<button class="ms-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="ms-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 ms-6 text-sm text-red-500" wire:click="$toggle('confirmingLeavingTeam')">
{{ __('Leave') }}
</button>
<!-- Remove Team Member -->
@elseif (Gate::check('removeTeamMember', $team))
<button class="cursor-pointer ms-6 text-sm text-red-500" wire:click="confirmTeamMemberRemoval('{{ $user->id }}')">
{{ __('Remove') }}
</button>
@endif
</div>
</div>
@endforeach
</div>
</x-slot>
</x-action-section>
</div>
@endif
<!-- Role Management Modal -->
<x-dialog-modal wire:model.live="currentlyManagingRole">
<x-slot name="title">
{{ __('Manage Role') }}
</x-slot>
<x-slot name="content">
<div class="relative z-0 mt-1 border border-gray-200 dark:border-gray-700 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-indigo-500 dark:focus:border-indigo-600 focus:ring-2 focus:ring-indigo-500 dark:focus:ring-indigo-600 {{ $index > 0 ? 'border-t border-gray-200 dark:border-gray-700 focus:border-none 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 dark:text-gray-400 {{ $currentRole == $role->key ? 'font-semibold' : '' }}">
{{ $role->name }}
</div>
@if ($currentRole == $role->key)
<svg class="ms-2 size-5 text-green-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" d="M9 12.75L11.25 15 15 9.75M21 12a9 9 0 11-18 0 9 9 0 0118 0z" />
</svg>
@endif
</div>
<!-- Role Description -->
<div class="mt-2 text-xs text-gray-600 text-start dark:text-gray-400">
{{ $role->description }}
</div>
</div>
</button>
@endforeach
</div>
</x-slot>
<x-slot name="footer">
<x-secondary-button wire:click="stopManagingRole" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-button class="ms-3" wire:click="updateRole" wire:loading.attr="disabled">
{{ __('Save') }}
</x-button>
</x-slot>
</x-dialog-modal>
<!-- Leave Team Confirmation Modal -->
<x-confirmation-modal wire:model.live="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-secondary-button wire:click="$toggle('confirmingLeavingTeam')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-danger-button class="ms-3" wire:click="leaveTeam" wire:loading.attr="disabled">
{{ __('Leave') }}
</x-danger-button>
</x-slot>
</x-confirmation-modal>
<!-- Remove Team Member Confirmation Modal -->
<x-confirmation-modal wire:model.live="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-secondary-button wire:click="$toggle('confirmingTeamMemberRemoval')" wire:loading.attr="disabled">
{{ __('Cancel') }}
</x-secondary-button>
<x-danger-button class="ms-3" wire:click="removeTeamMember" wire:loading.attr="disabled">
{{ __('Remove') }}
</x-danger-button>
</x-slot>
</x-confirmation-modal>
</div>
@@ -0,0 +1,50 @@
<x-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-label value="{{ __('Team Owner') }}" />
<div class="flex items-center mt-2">
<img class="size-12 rounded-full object-cover" src="{{ $team->owner->profile_photo_url }}" alt="{{ $team->owner->name }}">
<div class="ms-4 leading-tight">
<div class="text-gray-900 dark:text-white">{{ $team->owner->name }}</div>
<div class="text-gray-700 dark:text-gray-300 text-sm">{{ $team->owner->email }}</div>
</div>
</div>
</div>
<!-- Team Name -->
<div class="col-span-6 sm:col-span-4">
<x-label for="name" value="{{ __('Team Name') }}" />
<x-input id="name"
type="text"
class="mt-1 block w-full"
wire:model="state.name"
:disabled="! Gate::check('update', $team)" />
<x-input-error for="name" class="mt-2" />
</div>
</x-slot>
@if (Gate::check('update', $team))
<x-slot name="actions">
<x-action-message class="me-3" on="saved">
{{ __('Saved.') }}
</x-action-message>
<x-button>
{{ __('Save') }}
</x-button>
</x-slot>
@endif
</x-form-section>
@@ -0,0 +1,13 @@
<x-guest-layout>
<div class="pt-4 bg-gray-100 dark:bg-gray-900">
<div class="min-h-screen flex flex-col items-center pt-6 sm:pt-0">
<div>
<x-authentication-card-logo />
</div>
<div class="w-full sm:max-w-2xl mt-6 p-6 bg-white dark:bg-gray-800 shadow-md overflow-hidden sm:rounded-lg prose dark:prose-invert">
{!! $terms !!}
</div>
</div>
</div>
</x-guest-layout>
@@ -0,0 +1,23 @@
import defaultTheme from 'tailwindcss/defaultTheme';
import forms from '@tailwindcss/forms';
import typography from '@tailwindcss/typography';
/** @type {import('tailwindcss').Config} */
export default {
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: ['Figtree', ...defaultTheme.fontFamily.sans],
},
},
},
plugins: [forms, typography],
};
+11
View File
@@ -0,0 +1,11 @@
import { defineConfig } from 'vite';
import laravel from 'laravel-vite-plugin';
export default defineConfig({
plugins: [
laravel({
input: ['resources/css/app.css', 'resources/js/app.js'],
refresh: true,
}),
],
});