refactor + fixes

This commit is contained in:
Andras Bacsai 2023-08-30 16:01:38 +02:00
parent 6f00740f67
commit 5b6667c461
21 changed files with 48 additions and 36 deletions

View File

@ -30,7 +30,7 @@ class Controller extends BaseController
if (!is_cloud()) { if (!is_cloud()) {
abort(404); abort(404);
} }
return view('subscription.show', [ return view('subscription.index', [
'settings' => InstanceSettings::get(), 'settings' => InstanceSettings::get(),
]); ]);
} }
@ -80,7 +80,7 @@ class Controller extends BaseController
if (auth()->user()->isAdminFromSession()) { if (auth()->user()->isAdminFromSession()) {
$invitations = TeamInvitation::whereTeamId(currentTeam()->id)->get(); $invitations = TeamInvitation::whereTeamId(currentTeam()->id)->get();
} }
return view('team.show', [ return view('team.index', [
'invitations' => $invitations, 'invitations' => $invitations,
]); ]);
} }
@ -129,7 +129,7 @@ class Controller extends BaseController
if ($diff <= config('constants.invitation.link.expiration')) { if ($diff <= config('constants.invitation.link.expiration')) {
$user->teams()->attach($invitation->team->id, ['role' => $invitation->role]); $user->teams()->attach($invitation->team->id, ['role' => $invitation->role]);
$invitation->delete(); $invitation->delete();
return redirect()->route('team.show'); return redirect()->route('team.index');
} else { } else {
$invitation->delete(); $invitation->delete();
abort(401); abort(401);
@ -151,7 +151,7 @@ class Controller extends BaseController
abort(401); abort(401);
} }
$invitation->delete(); $invitation->delete();
return redirect()->route('team.show'); return redirect()->route('team.index');
} catch (Throwable $th) { } catch (Throwable $th) {
throw $th; throw $th;
} }

View File

@ -38,7 +38,7 @@ class Kernel extends HttpKernel
\App\Http\Middleware\VerifyCsrfToken::class, \App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class, \Illuminate\Routing\Middleware\SubstituteBindings::class,
\App\Http\Middleware\CheckForcePasswordReset::class, \App\Http\Middleware\CheckForcePasswordReset::class,
\App\Http\Middleware\SubscriptionValid::class, \App\Http\Middleware\IsSubscriptionValid::class,
\App\Http\Middleware\IsBoardingFlow::class, \App\Http\Middleware\IsBoardingFlow::class,
], ],

View File

@ -49,7 +49,7 @@ class PricingPlans extends Component
], ],
'mode' => 'subscription', 'mode' => 'subscription',
'success_url' => route('subscription.success'), 'success_url' => route('subscription.success'),
'cancel_url' => route('subscription.show',['cancelled' => true]), 'cancel_url' => route('subscription.index',['cancelled' => true]),
]; ];
$customer = currentTeam()->subscription?->stripe_customer_id ?? null; $customer = currentTeam()->subscription?->stripe_customer_id ?? null;
if ($customer) { if ($customer) {

View File

@ -30,7 +30,7 @@ class Create extends Component
]); ]);
auth()->user()->teams()->attach($team, ['role' => 'admin']); auth()->user()->teams()->attach($team, ['role' => 'admin']);
refreshSession(); refreshSession();
return redirect()->route('team.show'); return redirect()->route('team.index');
} catch (\Throwable $th) { } catch (\Throwable $th) {
return general_error_handler($th, $this); return general_error_handler($th, $this);
} }

View File

@ -25,6 +25,6 @@ class Delete extends Component
}); });
refreshSession(); refreshSession();
return redirect()->route('team.show'); return redirect()->route('team.index');
} }
} }

View File

@ -28,7 +28,6 @@ class Form extends Component
try { try {
$this->team->save(); $this->team->save();
refreshSession(); refreshSession();
$this->emit('reloadWindow');
} catch (\Throwable $th) { } catch (\Throwable $th) {
return general_error_handler($th, $this); return general_error_handler($th, $this);
} }

View File

@ -6,7 +6,7 @@ use Closure;
use Illuminate\Http\Request; use Illuminate\Http\Request;
use Symfony\Component\HttpFoundation\Response; use Symfony\Component\HttpFoundation\Response;
class SubscriptionValid class IsSubscriptionValid
{ {
public function handle(Request $request, Closure $next): Response public function handle(Request $request, Closure $next): Response
{ {

View File

@ -32,6 +32,7 @@ class User extends Authenticatable implements SendsEmail
$team = [ $team = [
'name' => $user->name . "'s Team", 'name' => $user->name . "'s Team",
'personal_team' => true, 'personal_team' => true,
'boarding' => true
]; ];
if ($user->id === 0) { if ($user->id === 0) {
$team['id'] = 0; $team['id'] = 0;

View File

@ -53,7 +53,8 @@ function showBoarding(): bool
} }
function refreshSession(): void function refreshSession(): void
{ {
session(['currentTeam' => currentTeam()]); $team = Team::find(currentTeam()->id);
session(['currentTeam' => $team]);
} }
function general_error_handler(Throwable | null $err = null, $that = null, $isJson = false, $customErrorMessage = null): mixed function general_error_handler(Throwable | null $err = null, $that = null, $isJson = false, $customErrorMessage = null): mixed
{ {

View File

@ -70,7 +70,6 @@ function isSubscriptionActive()
} }
function isSubscriptionOnGracePeriod() function isSubscriptionOnGracePeriod()
{ {
$team = currentTeam(); $team = currentTeam();
if (!$team) { if (!$team) {
return false; return false;
@ -96,7 +95,7 @@ function subscriptionProvider()
function getStripeCustomerPortalSession(Team $team) function getStripeCustomerPortalSession(Team $team)
{ {
Stripe::setApiKey(config('subscription.stripe_api_key')); Stripe::setApiKey(config('subscription.stripe_api_key'));
$return_url = route('team.show'); $return_url = route('team.index');
$stripe_customer_id = $team->subscription->stripe_customer_id; $stripe_customer_id = $team->subscription->stripe_customer_id;
$session = \Stripe\BillingPortal\Session::create([ $session = \Stripe\BillingPortal\Session::create([
'customer' => $stripe_customer_id, 'customer' => $stripe_customer_id,

View File

@ -12,8 +12,8 @@ return [
'limits' => [ 'limits' => [
'server' => [ 'server' => [
'basic' => 1, 'basic' => 1,
'pro' => 3, 'pro' => 10,
'ultimate' => 9999999999999999999, 'ultimate' => 25,
], ],
], ],
]; ];

View File

@ -1,6 +1,6 @@
<div class="flex flex-col items-center justify-center h-screen"> <div class="flex flex-col items-center justify-center h-screen">
<span class="text-xl font-bold text-white">You have reached the limit of {{ $name }} you can create.</span> <span class="text-xl font-bold text-white">You have reached the limit of {{ $name }} you can create.</span>
<span>Please <a class="text-white underline "href="{{ route('team.show') }}">upgrade your <span>Please <a class="text-white underline "href="{{ route('team.index') }}">upgrade your
subscription<a /> to create more subscription<a /> to create more
{{ $name }}.</span> {{ $name }}.</span>
</div> </div>

View File

@ -1,6 +1,15 @@
@auth @auth
<nav class="fixed h-full overflow-hidden overflow-y-auto scrollbar"> <nav class="fixed h-full overflow-hidden overflow-y-auto scrollbar">
<ul class="flex flex-col h-full gap-4 menu flex-nowrap"> <ul class="flex flex-col h-full gap-4 menu flex-nowrap">
<li title="Dashboard">
<a class="hover:bg-transparent" @if (!request()->is('/')) href="/" @endif>
<svg xmlns="http://www.w3.org/2000/svg" class="{{ request()->is('/') ? 'text-warning icon' : 'icon' }}"
fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2"
d="M3 12l2-2m0 0l7-7 7 7M5 10v10a1 1 0 001 1h3m10-11l2 2m-2-2v10a1 1 0 01-1 1h-3m-6 0a1 1 0 001-1v-4a1 1 0 011-1h2a1 1 0 011 1v4a1 1 0 001 1m-6 0h6" />
</svg>
</a>
</li>
<li class="pb-6" title="Logout"> <li class="pb-6" title="Logout">
<form action="/logout" method="POST" class=" hover:bg-transparent"> <form action="/logout" method="POST" class=" hover:bg-transparent">
@csrf @csrf

View File

@ -51,7 +51,7 @@
</a> </a>
</li> </li>
<li title="Teams"> <li title="Teams">
<a class="hover:bg-transparent" href="{{ route('team.show') }}"> <a class="hover:bg-transparent" href="{{ route('team.index') }}">
<svg xmlns="http://www.w3.org/2000/svg" class="icon" viewBox="0 0 24 24" stroke-width="1.5" <svg xmlns="http://www.w3.org/2000/svg" class="icon" viewBox="0 0 24 24" stroke-width="1.5"
stroke="currentColor" fill="none" stroke-linecap="round" stroke-linejoin="round"> stroke="currentColor" fill="none" stroke-linecap="round" stroke-linejoin="round">
<path stroke="none" d="M0 0h24v24H0z" fill="none" /> <path stroke="none" d="M0 0h24v24H0z" fill="none" />

View File

@ -3,21 +3,21 @@
]) ])
<div x-data="{ selected: 'yearly' }" class="w-full pb-20"> <div x-data="{ selected: 'yearly' }" class="w-full pb-20">
<div class="px-6 mx-auto lg:px-8"> <div class="px-6 mx-auto lg:px-8">
<div class="flex justify-center mt-5"> <div class="flex justify-center">
<fieldset <fieldset
class="grid grid-cols-2 p-1 text-xs font-semibold leading-5 text-center rounded-full gap-x-1 "> class="grid grid-cols-2 p-1 text-xs font-semibold leading-5 text-center text-white rounded gap-x-1 bg-white/5">
<legend class="sr-only">Payment frequency</legend> <legend class="sr-only">Payment frequency</legend>
<label class="cursor-pointer rounded px-2.5 py-1" <label class="cursor-pointer rounded px-2.5 py-1"
:class="selected === 'monthly' ? 'bg-coollabs-100 text-white' : ''"> :class="selected === 'monthly' ? 'bg-coollabs-100 text-white' : ''">
<input type="radio" x-on:click="selected = 'monthly'" name="frequency" value="monthly" <input type="radio" x-on:click="selected = 'monthly'" name="frequency" value="monthly"
class="sr-only"> class="sr-only">
<span>Monthly</span> <span>Monthly</span>
</label> </label>
<label class="cursor-pointer rounded px-2.5 py-1" <label class="cursor-pointer rounded px-2.5 py-1"
:class="selected === 'yearly' ? 'bg-coollabs-100 text-white' : ''"> :class="selected === 'yearly' ? 'bg-coollabs-100 text-white' : ''">
<input type="radio" x-on:click="selected = 'yearly'" name="frequency" value="annually" <input type="radio" x-on:click="selected = 'yearly'" name="frequency" value="annually"
class="sr-only"> class="sr-only">
<span>Annually <span class="text-xs text-warning">(save ~1 month)<span></span> <span>Annually</span>
</label> </label>
</fieldset> </fieldset>
</div> </div>
@ -167,9 +167,9 @@
<span>billed annually</span> <span>billed annually</span>
</span> </span>
@if ($showSubscribeButtons) @if ($showSubscribeButtons)
@isset($pro) @isset($pro)
{{ $pro }} {{ $pro }}
@endisset @endisset
@endif @endif
<p class="h-20 mt-10 text-sm leading-6 text-white">Scale your business or self-hosting environment. <p class="h-20 mt-10 text-sm leading-6 text-white">Scale your business or self-hosting environment.
</p> </p>
@ -181,7 +181,7 @@
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z" d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
clip-rule="evenodd" /> clip-rule="evenodd" />
</svg> </svg>
5 servers <x-helper helper="Bring Your Own Server. All you need is n SSH connection." /> 10 servers <x-helper helper="Bring Your Own Server. All you need is n SSH connection." />
</li> </li>
<li class="flex gap-x-3"> <li class="flex gap-x-3">
<svg class="flex-none w-5 h-6 text-warning" viewBox="0 0 20 20" fill="currentColor" <svg class="flex-none w-5 h-6 text-warning" viewBox="0 0 20 20" fill="currentColor"
@ -229,7 +229,7 @@
{{ $ultimate }} {{ $ultimate }}
@endisset @endisset
@endif @endif
<p class="h-20 mt-10 text-sm leading-6 text-white">Deploy complex infrastuctures and <p class="h-20 mt-10 text-sm leading-6 text-white">Deploy complex infrastructures and
manage them easily in one place.</p> manage them easily in one place.</p>
<ul role="list" class="mt-6 space-y-3 text-sm leading-6 "> <ul role="list" class="mt-6 space-y-3 text-sm leading-6 ">
<li class="flex gap-x-3"> <li class="flex gap-x-3">
@ -239,7 +239,7 @@
d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z" d="M10 18a8 8 0 100-16 8 8 0 000 16zm3.857-9.809a.75.75 0 00-1.214-.882l-3.483 4.79-1.88-1.88a.75.75 0 10-1.06 1.061l2.5 2.5a.75.75 0 001.137-.089l4-5.5z"
clip-rule="evenodd" /> clip-rule="evenodd" />
</svg> </svg>
15 servers <x-helper helper="Bring Your Own Server. All you need is n SSH connection." /> 25 servers <x-helper helper="Bring Your Own Server. All you need is n SSH connection." />
</li> </li>
<li class="flex font-bold text-white gap-x-3"> <li class="flex font-bold text-white gap-x-3">
<svg class="flex-none w-5 h-6 text-warning" viewBox="0 0 20 20" fill="currentColor" <svg class="flex-none w-5 h-6 text-warning" viewBox="0 0 20 20" fill="currentColor"

View File

@ -21,7 +21,7 @@
</ol> </ol>
</nav> </nav>
<nav class="navbar-main"> <nav class="navbar-main">
<a class="{{ request()->routeIs('team.show') ? 'text-white' : '' }}" href="{{ route('team.show') }}"> <a class="{{ request()->routeIs('team.index') ? 'text-white' : '' }}" href="{{ route('team.index') }}">
<button>General</button> <button>General</button>
</a> </a>
<a class="{{ request()->routeIs('team.members') ? 'text-white' : '' }}" href="{{ route('team.members') }}"> <a class="{{ request()->routeIs('team.members') ? 'text-white' : '' }}" href="{{ route('team.members') }}">

View File

@ -8,7 +8,7 @@
@endif @endif
@if (currentTeam()->subscription->stripe_cancel_at_period_end) @if (currentTeam()->subscription->stripe_cancel_at_period_end)
<a class="hover:no-underline" href="{{ route('subscription.show') }}"><x-forms.button>Subscribe <a class="hover:no-underline" href="{{ route('subscription.index') }}"><x-forms.button>Subscribe
again</x-forms.button></a> again</x-forms.button></a>
@endif @endif
<x-forms.button wire:click='stripeCustomerPortal'>Manage My Subscription</x-forms.button> <x-forms.button wire:click='stripeCustomerPortal'>Manage My Subscription</x-forms.button>

View File

@ -3,7 +3,7 @@
<div class="subtitle ">Your user profile settings.</div> <div class="subtitle ">Your user profile settings.</div>
<livewire:profile.form :request="$request" /> <livewire:profile.form :request="$request" />
<h2 class="py-4">Subscription</h2> <h2 class="py-4">Subscription</h2>
<a href="{{ route('team.show') }}">Check in Team Settings</a> <a href="{{ route('team.index') }}">Check in Team Settings</a>
<h2 class="py-4">Two-factor Authentication</h2> <h2 class="py-4">Two-factor Authentication</h2>
@if (session('status') == 'two-factor-authentication-enabled') @if (session('status') == 'two-factor-authentication-enabled')
<div class="mb-4 font-medium"> <div class="mb-4 font-medium">

View File

@ -3,7 +3,7 @@
<div class="flex justify-center mx-10"> <div class="flex justify-center mx-10">
<div x-data> <div x-data>
<div class="flex gap-2"> <div class="flex gap-2">
<h2>Subscription</h2> <h1>Subscription</h1>
<livewire:switch-team /> <livewire:switch-team />
</div> </div>
<div class="flex items-center pb-8"> <div class="flex items-center pb-8">
@ -11,7 +11,10 @@
class="text-warning">{{ session('currentTeam.name') }}</span></span> class="text-warning">{{ session('currentTeam.name') }}</span></span>
</div> </div>
@if(request()->query->get('cancelled')) @if(request()->query->get('cancelled'))
<div class="text-xl text-center text-red-500">Something went wrong. Please try again.</div> <div class="rounded alert alert-error">
<svg xmlns="http://www.w3.org/2000/svg" class="w-6 h-6 stroke-current shrink-0" fill="none" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M10 14l2-2m0 0l2-2m-2 2l-2-2m2 2l2 2m7-2a9 9 0 11-18 0 9 9 0 0118 0z" /></svg>
<span>Something went wrong with your subscription. Please try again or contact support.</span>
</div>
@endif @endif
@if (config('subscription.provider') !== null) @if (config('subscription.provider') !== null)
<livewire:subscription.pricing-plans /> <livewire:subscription.pricing-plans />

View File

@ -11,7 +11,7 @@
<livewire:subscription.actions /> <livewire:subscription.actions />
@else @else
<x-forms.button class="mt-4"><a class="text-white hover:no-underline" <x-forms.button class="mt-4"><a class="text-white hover:no-underline"
href="{{ route('subscription.show') }}">Subscribe Now</a> href="{{ route('subscription.index') }}">Subscribe Now</a>
</x-forms.button> </x-forms.button>
@endif @endif

View File

@ -98,13 +98,13 @@ Route::middleware(['auth'])->group(function () {
Route::middleware(['throttle:force-password-reset'])->group(function () { Route::middleware(['throttle:force-password-reset'])->group(function () {
Route::get('/force-password-reset', [Controller::class, 'force_passoword_reset'])->name('auth.force-password-reset'); Route::get('/force-password-reset', [Controller::class, 'force_passoword_reset'])->name('auth.force-password-reset');
}); });
Route::get('/subscription', [Controller::class, 'subscription'])->name('subscription.show'); Route::get('/subscription', [Controller::class, 'subscription'])->name('subscription.index');
Route::get('/subscription/success', fn () => view('subscription.success'))->name('subscription.success'); Route::get('/subscription/success', fn () => view('subscription.success'))->name('subscription.success');
Route::get('/subscription/cancel', fn () => view('profile'))->name('subscription.cancel'); Route::get('/subscription/cancel', fn () => view('profile'))->name('subscription.cancel');
Route::get('/settings', [Controller::class, 'settings'])->name('settings.configuration'); Route::get('/settings', [Controller::class, 'settings'])->name('settings.configuration');
Route::get('/settings/license', [Controller::class, 'license'])->name('settings.license'); Route::get('/settings/license', [Controller::class, 'license'])->name('settings.license');
Route::get('/profile', fn () => view('profile', ['request' => request()]))->name('profile'); Route::get('/profile', fn () => view('profile', ['request' => request()]))->name('profile');
Route::get('/team', [Controller::class, 'team'])->name('team.show'); Route::get('/team', [Controller::class, 'team'])->name('team.index');
Route::get('/team/new', fn () => view('team.create'))->name('team.create'); Route::get('/team/new', fn () => view('team.create'))->name('team.create');
Route::get('/team/notifications', fn () => view('team.notifications'))->name('team.notifications'); Route::get('/team/notifications', fn () => view('team.notifications'))->name('team.notifications');
Route::get('/team/storages', [Controller::class, 'storages'])->name('team.storages.all'); Route::get('/team/storages', [Controller::class, 'storages'])->name('team.storages.all');