Fix hosting 500s: rc_service_orders migration and account layout.
Deploy Ladill Hosting / deploy (push) Successful in 22s
Deploy Ladill Hosting / deploy (push) Successful in 22s
Account pages were extending the email layout with undefined routes, and hosting type pages queried a missing rc_service_orders table. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -1,10 +1,8 @@
|
||||
@extends('layouts.email')
|
||||
@section('title', 'Billing — Ladill Email')
|
||||
@section('content')
|
||||
<x-app-layout title="Billing — Ladill Hosting">
|
||||
@php $fmt = fn ($m) => 'GHS '.number_format($m / 100, 2); @endphp
|
||||
<div class="mx-auto max-w-3xl">
|
||||
<h1 class="text-xl font-semibold tracking-tight text-slate-900">Billing</h1>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Your Ladill wallet funds mailboxes across every Ladill app.</p>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Your Ladill wallet funds hosting and other Ladill apps.</p>
|
||||
|
||||
<div class="mt-6 grid gap-4 sm:grid-cols-3">
|
||||
<div class="rounded-2xl bg-gradient-to-br from-indigo-700 via-indigo-600 to-blue-500 p-5 text-white shadow-sm sm:col-span-1">
|
||||
@@ -13,7 +11,7 @@
|
||||
<a href="{{ $topupUrl }}" class="mt-3 inline-block rounded-lg bg-white/15 px-3.5 py-1.5 text-xs font-semibold text-white backdrop-blur transition hover:bg-white/25">Add funds</a>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<p class="text-xs font-medium uppercase tracking-wide text-slate-400">Spent on email</p>
|
||||
<p class="text-xs font-medium uppercase tracking-wide text-slate-400">Spent on hosting</p>
|
||||
<p class="mt-1.5 text-2xl font-semibold text-slate-900">{{ $fmt($spentMinor) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
@@ -24,11 +22,11 @@
|
||||
|
||||
<div class="mt-6 rounded-2xl border border-slate-200 bg-white">
|
||||
<div class="flex items-center justify-between border-b border-slate-100 px-5 py-3.5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Mailbox subscriptions</h2>
|
||||
<span class="text-xs text-slate-400">priced by storage plan</span>
|
||||
<h2 class="text-sm font-semibold text-slate-900">Hosting subscriptions</h2>
|
||||
<span class="text-xs text-slate-400">billed from wallet</span>
|
||||
</div>
|
||||
@if(empty($paidMailboxes))
|
||||
<p class="px-5 py-8 text-center text-sm text-slate-400">No paid mailboxes yet — your free allowance covers you.</p>
|
||||
<p class="px-5 py-8 text-center text-sm text-slate-400">No active hosting subscriptions yet.</p>
|
||||
@else
|
||||
<ul class="divide-y divide-slate-50">
|
||||
@foreach($paidMailboxes as $m)
|
||||
@@ -47,6 +45,6 @@
|
||||
</div>
|
||||
@endif
|
||||
</div>
|
||||
<p class="mt-4 text-xs text-slate-400">Mailboxes beyond your free allowance renew monthly from your wallet. Keep it funded to avoid interruption.</p>
|
||||
<p class="mt-4 text-xs text-slate-400">Keep your wallet funded to avoid hosting interruption.</p>
|
||||
</div>
|
||||
@endsection
|
||||
</x-app-layout>
|
||||
|
||||
@@ -1,9 +1,7 @@
|
||||
@extends('layouts.email')
|
||||
@section('title', 'Developers — Ladill Email')
|
||||
@section('content')
|
||||
<x-app-layout title="Developers — Ladill Hosting">
|
||||
<div class="mx-auto max-w-3xl">
|
||||
<h1 class="text-xl font-semibold tracking-tight text-slate-900">Developers</h1>
|
||||
<p class="mt-0.5 text-sm text-slate-500">API tokens to manage your mailboxes programmatically.</p>
|
||||
<p class="mt-0.5 text-sm text-slate-500">API tokens to manage your hosting programmatically.</p>
|
||||
|
||||
@if($newToken)
|
||||
<div class="mt-6 rounded-2xl border border-emerald-200 bg-emerald-50 p-5">
|
||||
@@ -19,7 +17,6 @@
|
||||
</div>
|
||||
@endif
|
||||
|
||||
{{-- Create --}}
|
||||
<div class="mt-6 rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Create a token</h2>
|
||||
<form method="POST" action="{{ route('account.developers.store') }}" class="mt-4 flex flex-col gap-3 sm:flex-row sm:items-end">
|
||||
@@ -34,7 +31,6 @@
|
||||
</form>
|
||||
</div>
|
||||
|
||||
{{-- Tokens --}}
|
||||
<div class="mt-6 rounded-2xl border border-slate-200 bg-white">
|
||||
<div class="border-b border-slate-100 px-5 py-3.5"><h2 class="text-sm font-semibold text-slate-900">Your tokens</h2></div>
|
||||
@forelse($tokens as $token)
|
||||
@@ -56,15 +52,14 @@
|
||||
@endforelse
|
||||
</div>
|
||||
|
||||
{{-- Docs --}}
|
||||
<div class="mt-6 rounded-2xl border border-slate-200 bg-slate-900 p-5 text-slate-200">
|
||||
<h2 class="text-sm font-semibold text-white">Quick start</h2>
|
||||
<p class="mt-1 text-xs text-slate-400">Authenticate with a Bearer token. Base URL:</p>
|
||||
<code class="mt-2 block rounded-lg bg-black/40 px-3 py-2 font-mono text-[11px] text-emerald-300">{{ $apiBase }}</code>
|
||||
<pre class="mt-3 overflow-x-auto rounded-lg bg-black/40 px-3 py-3 font-mono text-[11px] leading-relaxed text-slate-300"><code>curl {{ $apiBase }}/mailboxes \
|
||||
<pre class="mt-3 overflow-x-auto rounded-lg bg-black/40 px-3 py-3 font-mono text-[11px] leading-relaxed text-slate-300"><code>curl {{ $apiBase }}/me \
|
||||
-H "Authorization: Bearer <your-token>" \
|
||||
-H "Accept: application/json"</code></pre>
|
||||
<p class="mt-3 text-[11px] text-slate-400">Endpoints: <span class="font-mono text-slate-300">GET /me</span>, <span class="font-mono text-slate-300">GET /mailboxes</span>. More coming soon.</p>
|
||||
<p class="mt-3 text-[11px] text-slate-400">Endpoints: <span class="font-mono text-slate-300">GET /me</span>. More coming soon.</p>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
</x-app-layout>
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
@extends('layouts.email')
|
||||
@section('title', 'Settings — Ladill Email')
|
||||
@section('content')
|
||||
<x-app-layout title="Settings — Ladill Hosting">
|
||||
@php $emailApp = 'https://email.'.config('app.platform_domain'); @endphp
|
||||
<div class="mx-auto max-w-2xl">
|
||||
<h1 class="text-xl font-semibold tracking-tight text-slate-900">Settings</h1>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Defaults, preferences, and account mailbox linking.</p>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Hosting preferences and account mailbox linking.</p>
|
||||
|
||||
@if($showMailboxLinkUi ?? (($linkStatus['linked_mailbox'] ?? null) || ($linkStatus['show_reminder'] ?? false)))
|
||||
<div class="mt-6 rounded-2xl border border-indigo-200 bg-white p-5 shadow-sm">
|
||||
@@ -31,13 +30,13 @@
|
||||
</form>
|
||||
@elseif(($linkStatus['stage'] ?? '') === 'needs_domain')
|
||||
<p class="mt-3 text-sm text-amber-800">Add and verify an email domain first.</p>
|
||||
<a href="{{ route('hosting.domains.index') }}" class="mt-3 inline-flex items-center gap-1 text-sm font-semibold text-indigo-700 hover:text-indigo-800">
|
||||
Go to domains
|
||||
<a href="{{ $emailApp }}/domains" class="mt-3 inline-flex items-center gap-1 text-sm font-semibold text-indigo-700 hover:text-indigo-800">
|
||||
Go to Ladill Email
|
||||
<svg class="h-3.5 w-3.5" fill="none" stroke="currentColor" stroke-width="2" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" d="M13.5 4.5 21 12m0 0-7.5 7.5M21 12H3"/></svg>
|
||||
</a>
|
||||
@elseif(($linkStatus['stage'] ?? '') === 'needs_mailbox')
|
||||
<p class="mt-3 text-sm text-amber-800">Create a mailbox on your verified domain first.</p>
|
||||
<a href="{{ route('hosting.mailboxes.create') }}" class="mt-3 inline-flex items-center gap-1 text-sm font-semibold text-indigo-700 hover:text-indigo-800">
|
||||
<a href="{{ $emailApp }}/mailboxes/create" class="mt-3 inline-flex items-center gap-1 text-sm font-semibold text-indigo-700 hover:text-indigo-800">
|
||||
Create mailbox
|
||||
<svg class="h-3.5 w-3.5" fill="none" stroke="currentColor" stroke-width="2" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" d="M13.5 4.5 21 12m0 0-7.5 7.5M21 12H3"/></svg>
|
||||
</a>
|
||||
@@ -66,22 +65,11 @@
|
||||
@csrf @method('PUT')
|
||||
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Mailbox defaults</h2>
|
||||
<div class="mt-4 grid gap-3 sm:grid-cols-2">
|
||||
<div>
|
||||
<label class="block text-[11px] font-medium text-slate-500">Default mailbox quota</label>
|
||||
<select name="default_quota_mb" class="mt-1 w-full rounded-lg border border-slate-200 bg-slate-50 px-3 py-2 text-sm focus:border-indigo-300 focus:bg-white focus:outline-none">
|
||||
@php $cur = (int) ($settings->default_quota_mb ?? config('hosting.default_quota_mb', 10240)); @endphp
|
||||
@foreach([1024 => '1 GB', 5120 => '5 GB', 10240 => '10 GB', 25600 => '25 GB', 51200 => '50 GB'] as $mb => $label)
|
||||
<option value="{{ $mb }}" @selected($cur === $mb)>{{ $label }}</option>
|
||||
@endforeach
|
||||
</select>
|
||||
</div>
|
||||
<div>
|
||||
<label class="block text-[11px] font-medium text-slate-500">Notifications email</label>
|
||||
<input type="email" name="notify_email" value="{{ old('notify_email', $settings->notify_email ?? $account->email) }}"
|
||||
class="mt-1 w-full rounded-lg border border-slate-200 bg-slate-50 px-3 py-2 text-sm focus:border-indigo-300 focus:bg-white focus:outline-none focus:ring-2 focus:ring-indigo-100">
|
||||
</div>
|
||||
<h2 class="text-sm font-semibold text-slate-900">Notifications</h2>
|
||||
<div class="mt-4">
|
||||
<label class="block text-[11px] font-medium text-slate-500">Notifications email</label>
|
||||
<input type="email" name="notify_email" value="{{ old('notify_email', $settings->notify_email ?? $account->email) }}"
|
||||
class="mt-1 w-full rounded-lg border border-slate-200 bg-slate-50 px-3 py-2 text-sm focus:border-indigo-300 focus:bg-white focus:outline-none focus:ring-2 focus:ring-indigo-100">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -89,7 +77,7 @@
|
||||
<label class="flex items-center justify-between">
|
||||
<span>
|
||||
<span class="block text-sm font-medium text-slate-800">Product updates</span>
|
||||
<span class="block text-xs text-slate-400">Occasional emails about new Ladill Email features.</span>
|
||||
<span class="block text-xs text-slate-400">Occasional emails about new Ladill Hosting features.</span>
|
||||
</span>
|
||||
<input type="checkbox" name="product_updates" value="1" @checked($settings->product_updates ?? true) class="h-5 w-5 rounded border-slate-300 text-indigo-600 focus:ring-indigo-500">
|
||||
</label>
|
||||
@@ -98,4 +86,4 @@
|
||||
<button class="rounded-lg bg-indigo-600 px-4 py-2.5 text-sm font-semibold text-white transition hover:bg-indigo-700">Save settings</button>
|
||||
</form>
|
||||
</div>
|
||||
@endsection
|
||||
</x-app-layout>
|
||||
|
||||
@@ -1,9 +1,7 @@
|
||||
@extends('layouts.email')
|
||||
@section('title', 'Team — Ladill Email')
|
||||
@section('content')
|
||||
<x-app-layout title="Team — Ladill Hosting">
|
||||
<div class="mx-auto max-w-3xl">
|
||||
<h1 class="text-xl font-semibold tracking-tight text-slate-900">Team</h1>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Invite people to help manage this account’s mailboxes & domains.</p>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Invite people to help manage this account’s hosting.</p>
|
||||
|
||||
@if($canManage)
|
||||
<div class="mt-6 rounded-2xl border border-slate-200 bg-white p-5">
|
||||
@@ -25,7 +23,7 @@
|
||||
</div>
|
||||
<button class="rounded-lg bg-indigo-600 px-4 py-2 text-sm font-semibold text-white hover:bg-indigo-700">Send invite</button>
|
||||
</form>
|
||||
<p class="mt-2 text-[11px] text-slate-400">Admins can manage mailboxes and the team. Members can manage mailboxes. Invitees join by signing in with that hosting.</p>
|
||||
<p class="mt-2 text-[11px] text-slate-400">Admins can manage hosting and the team. Members can manage hosting. Invitees join by signing in with that email.</p>
|
||||
</div>
|
||||
@endif
|
||||
|
||||
@@ -79,4 +77,4 @@
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
</x-app-layout>
|
||||
|
||||
@@ -1,10 +1,8 @@
|
||||
@extends('layouts.email')
|
||||
@section('title', 'Wallet — Ladill Email')
|
||||
@section('content')
|
||||
<x-app-layout title="Wallet — Ladill Hosting">
|
||||
@php $fmt = fn ($m) => 'GHS '.number_format($m / 100, 2); @endphp
|
||||
<div class="mx-auto max-w-3xl">
|
||||
<h1 class="text-xl font-semibold tracking-tight text-slate-900">Wallet</h1>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Your Ladill wallet funds mailboxes across every Ladill app.</p>
|
||||
<p class="mt-0.5 text-sm text-slate-500">Your Ladill wallet funds hosting and other Ladill apps.</p>
|
||||
|
||||
<div class="mt-6 rounded-2xl bg-gradient-to-br from-indigo-700 via-indigo-600 to-blue-500 p-6 text-white shadow-sm">
|
||||
<p class="text-xs font-medium uppercase tracking-wide text-indigo-100">Balance</p>
|
||||
@@ -14,7 +12,7 @@
|
||||
|
||||
<div class="mt-4 grid gap-4 sm:grid-cols-2">
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<p class="text-xs font-medium uppercase tracking-wide text-slate-400">Spent on email</p>
|
||||
<p class="text-xs font-medium uppercase tracking-wide text-slate-400">Spent on hosting</p>
|
||||
<p class="mt-1.5 text-2xl font-semibold text-slate-900">{{ $fmt($spentMinor) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
@@ -22,6 +20,6 @@
|
||||
<p class="mt-1.5 text-2xl font-semibold text-slate-900">{{ $fmt($creditedMinor) }}</p>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-4 text-xs text-slate-400">Mailboxes beyond your free allowance are billed monthly from this wallet.</p>
|
||||
<p class="mt-4 text-xs text-slate-400">Hosting renewals and upgrades are billed from this wallet.</p>
|
||||
</div>
|
||||
@endsection
|
||||
</x-app-layout>
|
||||
|
||||
Reference in New Issue
Block a user