mirror of
https://github.com/snapotter-hq/SnapOtter.git
synced 2026-08-03 07:46:42 +02:00
fix(landing): link English-only tool-detail and self-hosted pages to un-prefixed URLs (#553)
Tool-detail pages (/tools/<section>/<tool>/) and the /self-hosted pages are built only in English, with no per-locale route, so a locale-prefixed link 404s in the static build. Add an enOnlyHref() helper and use it for those links in Footer, Navbar, HeroSearch, and ToolGrid so localized pages point at the English pages that actually exist. Adds an e2e guard asserting localized pages emit un-prefixed URLs for those routes.
This commit is contained in:
@@ -3,7 +3,7 @@
|
||||
// biome-ignore-all lint/correctness/noUnusedVariables: Astro template consumes frontmatter values.
|
||||
import LanguageSwitcher from "@/components/LanguageSwitcher.astro";
|
||||
import { t } from "@/i18n";
|
||||
import { localizeHref } from "@/lib/i18n-page";
|
||||
import { enOnlyHref, localizeHref } from "@/lib/i18n-page";
|
||||
|
||||
interface Props {
|
||||
locale?: string;
|
||||
@@ -29,7 +29,7 @@ const columns = [
|
||||
title: t(locale, "footer.col.solutions"),
|
||||
links: [
|
||||
{ label: t(locale, "footer.link.enterprise"), href: localizeHref(locale, "/#enterprise") },
|
||||
{ label: t(locale, "footer.link.selfHosted"), href: localizeHref(locale, "/self-hosted") },
|
||||
{ label: t(locale, "footer.link.selfHosted"), href: enOnlyHref("/self-hosted") },
|
||||
{ label: t(locale, "footer.link.openSource"), href: localizeHref(locale, "/#open-source") },
|
||||
{ label: t(locale, "footer.link.alternatives"), href: localizeHref(locale, "/alternatives") },
|
||||
{ label: t(locale, "footer.link.pricing"), href: localizeHref(locale, "/#pricing") },
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
import { TOOLS, toolSection } from "@snapotter/shared";
|
||||
import * as lucideIcons from "lucide";
|
||||
import { t } from "@/i18n";
|
||||
import { localizeHref } from "@/lib/i18n-page";
|
||||
import { enOnlyHref, localizeHref } from "@/lib/i18n-page";
|
||||
import { loadToolStrings } from "@/lib/tool-strings";
|
||||
|
||||
interface Props {
|
||||
@@ -72,7 +72,7 @@ function renderIcon(iconName: string): string {
|
||||
hidden
|
||||
>
|
||||
<a
|
||||
href={localizeHref(locale, `/tools/${toolSection(tool)}/${tool.id}/`)}
|
||||
href={enOnlyHref(`/tools/${toolSection(tool)}/${tool.id}/`)}
|
||||
class="flex items-center gap-3 px-4 py-2.5 no-underline transition-colors hover:bg-primary-subtle"
|
||||
>
|
||||
<svg
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
---
|
||||
// biome-ignore-all lint/correctness/noUnusedVariables: Astro template consumes frontmatter values.
|
||||
import { t } from "@/i18n";
|
||||
import { localizeHref } from "@/lib/i18n-page";
|
||||
import { enOnlyHref, localizeHref } from "@/lib/i18n-page";
|
||||
import { formatCompact, getStarCount } from "@/lib/stats";
|
||||
|
||||
interface Props {
|
||||
@@ -16,12 +16,12 @@ type NavItem = { label: string; href: string; external?: boolean; desc?: string
|
||||
const productLinks: NavItem[] = [
|
||||
{
|
||||
label: t(locale, "nav.product.developers.label"),
|
||||
href: localizeHref(locale, "/self-hosted/file-conversion-api"),
|
||||
href: enOnlyHref("/self-hosted/file-conversion-api"),
|
||||
desc: t(locale, "nav.product.developers.desc"),
|
||||
},
|
||||
{
|
||||
label: t(locale, "nav.product.selfHosted.label"),
|
||||
href: localizeHref(locale, "/self-hosted"),
|
||||
href: enOnlyHref("/self-hosted"),
|
||||
desc: t(locale, "nav.product.selfHosted.desc"),
|
||||
},
|
||||
{
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
import { CATEGORIES, TOOLS, toolSection } from "@snapotter/shared";
|
||||
import * as lucideIcons from "lucide";
|
||||
import { t } from "@/i18n";
|
||||
import { localizeHref } from "@/lib/i18n-page";
|
||||
import { enOnlyHref, localizeHref } from "@/lib/i18n-page";
|
||||
import { loadToolStrings } from "@/lib/tool-strings";
|
||||
import type { ModalityFilter, ToolSearchItem } from "../lib/tool-search";
|
||||
import SectionHeading from "./SectionHeading.astro";
|
||||
@@ -169,7 +169,7 @@ function toToolSearchItem(tool: (typeof TOOLS)[number]): ToolSearchItem {
|
||||
description: toolStrings[tool.id]?.description ?? tool.description,
|
||||
modality: tool.modality as ToolModality,
|
||||
category: tool.category,
|
||||
url: localizeHref(locale, `/tools/${toolSection(tool)}/${tool.id}/`),
|
||||
url: enOnlyHref(`/tools/${toolSection(tool)}/${tool.id}/`),
|
||||
icon: tool.icon,
|
||||
iconSvg: renderIcon(tool.icon),
|
||||
color: category?.color ?? "#E07832",
|
||||
|
||||
Reference in New Issue
Block a user