Limits of Laravel Jetstream's Profile Form Regarding Timezone Selection
0 reputation · 23 Feb 2025, 22:41 UTC
0 reputation · 23 Feb 2025, 22:41 UTC
Allow each user to select a preferred timezone so that timestamps shown in the Jetstream interface reflect their local time rather than a single application‑wide setting.
Jetstream’s default profile update form does not include a timezone field, leaving developers to decide whether to add a manual dropdown, rely on browser‑detected timezone via JavaScript, or combine both approaches, and how to validate the stored value to prevent Carbon instantiation errors.
Should Jetstream provide a built‑in timezone selector in the profile update form? Should the selector use browser detection, a manual list, or both? What validation rules should be applied to the stored timezone string?
32275 reputation · 24 Feb 2025, 06:09 UTC
Jetstream’s profile form does not ship with a timezone field. To give each user a local‑time experience you should add a custom timezone column, populate a dropdown from DateTimeZone::listIdentifiers(), and validate with Laravel’s timezone rule. Browser detection can pre‑fill the option but must never replace server‑side validation.
php artisan make:migration add_timezone_to_users_table --table=users
// In the migration:
Schema::table('users', function (Blueprint $table) {
$table->string('timezone')->nullable();
});
php artisan migrate
class User extends Authenticatable
{
protected $fillable = ['name', 'email', 'password', 'timezone'];
}
<div>
<label for="timezone" class="block text-sm font-medium text-gray-700">Timezone</label>
<select id="timezone" name="timezone" class="mt-1 block w-full" required>
@foreach (DateTimeZone::listIdentifiers() as $tz)
<option value="{{ $tz }}" {{ old('timezone', $user->timezone) === $tz ? 'selected' : '' }}>{{ $tz }}</option>
@endforeach
</select>
</div>
Optional JS to pre‑select the browser’s zone:
document.addEventListener('DOMContentLoaded', () => {
const tz = Intl.DateTimeFormat().resolvedOptions().timeZone;
const sel = document.getElementById('timezone');
if (sel && tz) sel.value = tz;
});
public function update(UpdateProfileInformation $request)
{
$request->user()->update($request->validated());
return back()->with('status', 'Profile updated.');
}
Validation rules are defined in UpdateProfileInformation.php:
public function rules()
{
return [
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'string', 'email', 'max:255', Rule::unique('users')->ignore($this->user->id)],
'timezone' => ['nullable', 'timezone'],
];
}
{{ \
Carbon::now($user->timezone ?? config('app.timezone'))
->toDateTimeString() }}
The timezone rule checks the string against PHP’s DateTimeZone list, preventing Carbon exceptions and ensuring only valid zones are stored.
If your application already stores a timezone in a different column name or uses a global fallback that must be overridden, let me know so the migration and code can be adjusted accordingly.
Use comments to ask for clarification. Post a solution as an answer.
No question comments on this page.