Увійти Реєстрація
Блог Серії
Кар'єра
Вакансії Компанії
Навчання
Документація Співбесіди Тестування Відео
Екосистема
Пакети Ресурси Проєкти Інструменти Події
Інше
Про нас

Slug із транслітерацією

Перетворити українську назву на URL-адресу

Дані надсилаються на сервер, але не зберігаються

Цей інструмент не можна виконати у браузері, тому введені дані надсилаються на наш сервер. Ми обробляємо їх у пам'яті та одразу повертаємо результат: нічого не записується в базу, у файли чи в логи, нічого не передається третім сторонам. Та все ж не вставляйте сюди справжні робочі паролі чи ключі - для чутливих даних краще скористатися локальними інструментами.

Поділитись

Дві транслітерації, і вони різні

Для української назви існує два розумні способи зробити URL, і вони дають різний результат.

Str::slug() - те, що зробить Laravel, якщо ви напишете Str::slug($post->title). Саме цей рядок опиниться в адресі статті чи вакансії.

КМУ 55 - офіційна транслітерація, затверджена постановою Кабміну 2010 року. Це те, як ваше ім'я пишуть у закордонному паспорті й як українські топоніми подають у документах.

Різниця не косметична:

Оригінал Str::slug КМУ 55
Їжак yizak yizhak
щука shhuka shchuka
Київ kijev kyiv
Юрій iurii yurii

Str::slug губить ж у «Їжак» і перетворює щ на shh замість shch. Для URL це переживається - адреса лишається унікальною й читабельною. Для документа, візитки чи назви компанії латиницею - ні.

Чому Str::slug працює саме так

Str::slug() не знає української. Він проганяє рядок через загальну таблицю транслітерації Unicode, побудовану переважно для західноєвропейських мов, і бере найближчі відповідники. Тому «Київ» стає kijev - через російсько-німецьку традицію, а не українську.

Це не помилка Laravel: універсальна таблиця не може знати, що саме ця кирилиця - українська, а не болгарська чи сербська.

Що з цим робити на практиці

Для URL лишайте Str::slug(). Він передбачуваний, уже використовується в наявних посиланнях, і міняти його заднім числом означає зламати всі старі адреси.

Якщо потрібна правильна транслітерація - для експорту, документів, латинської назви компанії - беріть КМУ 55 і зберігайте окремим полем.

// Slug генерується один раз при створенні і далі не змінюється:
// зміна заголовка не має ламати посилання, які вже десь опубліковані.
protected static function booted(): void
{
    static::creating(function (self $post): void {
        $post->slug ??= Str::slug($post->title);
    });
}

Унікальність

Str::slug() нічого не знає про те, що така адреса вже зайнята. Дві вакансії «Middle Laravel Developer» дадуть однаковий slug і другий запис впаде на унікальному індексі.

$slug = Str::slug($title);
$base = $slug;
$i = 2;

while (Vacancy::where('slug', $slug)->exists()) {
    $slug = $base . '-' . $i++;
}

Альтернатива - додати до slug короткий ідентифікатор: middle-laravel-developer-a7f3. Довше, але без запиту в циклі.

Довжина і SEO

Занадто довгий slug ріжеться у видачі й погано читається в месенджері. Розумна межа - близько 60-70 символів:

$slug = Str::slug(Str::limit($title, 60, ''));

Обрізати треба заголовок до транслітерації, а не slug після: інакше можна відрізати посеред shch і отримати обірваний хвіст.

Якщо потрібне не посилання, а перетворення між camelCase і snake_case - це зміна регістру.