Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Sweep: Application Translation Next Intl #12

Open
4 tasks done
0xGeegZ opened this issue Oct 22, 2023 · 1 comment · May be fixed by #13
Open
4 tasks done

Sweep: Application Translation Next Intl #12

0xGeegZ opened this issue Oct 22, 2023 · 1 comment · May be fixed by #13
Labels

Comments

@0xGeegZ
Copy link
Owner

0xGeegZ commented Oct 22, 2023

Issue: Application Translation - Next.js TypeScript Application Translation using next-intl

Objective

The goal of this issue is to translate specific components in our Next.js application using the next-intl package.

Files to translate:

  • src/components/landing/hero/hero.tsx
  • src/components/landing/partners/technologies.tsx
  • src/components/landing/testimonials/testimonial-highlight.tsx
  • src/components/landing/features/column/feature-sections.tsx

Expected Behavior

Once the translation is implemented successfully, the application should display the content of the mentioned components in the user's preferred language, as specified in the i18n configuration.

Actual Behavior

Currently, the components are only displaying content in the default language (English).

How to Solve

Step 1: Understand the Translation Files Structure

The English translations for the application are located in src/i18n/messages/en.json. You will insert the English translations for the components here. Each file should have its own namespace.

For example, for stats.tsx component, you must have a namespace such as "stats": {} in the en.json file.

Step 2: Determine if the Component is a Client Component or a Server Component

Client Component:

  • Has the use client instruction at the top of the file.
  • The component function definition is not an async function.
    • E.g., export function StarterPacksTestimonials() {}

Server Component:

  • Do NOT Have the use client instruction at the top of the file.
  • The component function definition is an async function.
    • E.g., export default async function StarterPacksPage() {}

Step 3: Implement the Translation

The implementation of the translation depends on whether the component is a client component or a server component. The changes you need to make in each component are:

  1. Import next-intl in the right way (depending if it's a client or server component).
  2. Replace hardcoded text strings with translation function calls from the next-intl package.
  3. Add the appropriate namespace to the translation function calls.
  4. Add the English translations to the src/i18n/messages/en.json file.

Let's take a look at some examples based on the files you provided.

Example 1: Server Component (StaterPacksPage)

In this case, we are using the getTranslations function from next-intl/server.

import { getTranslations } from "next-intl/server"

...

export default async function StaterPacksPage({
  params,
}: StaterPacksPageProps) {
  ...
  const t = await getTranslations("starterPack")
  ...

  // using the translation function
  <h1 className="font-heading text-3xl sm:text-5xl md:text-6xl lg:text-7xl">
    {folder.name} <br />
    {t("heroTitle")}
  </h1>
  ...
}

In the above code snippet, we've imported the getTranslations function from next-intl/server as this is a server component. We then use the getTranslations function to get translations for the starterPack namespace. The translation function t is then used to replace hardcoded strings. For example, {t("heroTitle")} will get the translated text for the heroTitle key in the starterPack namespace from en.json.

Example 2: Client Component (StarterPacksTestimonials)

In this case, we are using the useTranslations hook from next-intl.

import { useTranslations } from "next-intl"

export function StarterPacksTestimonials() {
  const t = useTranslations("testimonials")

  // using the translation function
  <h2 className="font-heading text-3xl leading-[1.1] sm:text-3xl md:text-6xl">
    {t("heroTitle")}
  </h2>
  ...
}

In the above code snippet, we've imported the useTranslations hook from next-intl as this is a client component. We then use the useTranslations hook to get translations for the testimonials namespace. The translation function t is then used to replace hardcoded strings. For example, {t("heroTitle")} will get the translated text for the heroTitle key in the testimonials namespace from en.json.
For a detailed guide on how to implement translations in client components and server components, refer to the following resources:

Step 4: Review Example Files

You have to refer to the following files that have already been translated to understand how to apply translations, so check them carefully:

You must use these examples to apply the translation in the same way and be sure to manage Server Component and Client Component in the correct manner.

And do not forget to add translation for each component in the src/i18n/messages/en.json file, this is critical so your pull request have to include en.json file with new translations.

Summary

By following these steps, you should be able to successfully translate the necessary components and enhance our application's internationalization. Remember to replace the hardcoded text strings with translation function calls from the next-intl package and to add the appropriate namespace to the translation function calls.

Please, set the same title for your pull request as the issue title. And please, add comments only if it helps to understand your code.

If you encounter any issues or have any questions, feel free to ask for help. Happy coding!

Checklist
  • src/components/landing/hero/hero.tsx ✅ Commit b0b7815
  • src/components/landing/partners/technologies.tsx ✅ Commit 76098a0
  • src/components/landing/testimonials/testimonial-highlight.tsx ✅ Commit de648bf
  • src/components/landing/features/column/feature-sections.tsx ✅ Commit 95af774

Flowchart

@0xGeegZ 0xGeegZ added the sweep label Oct 22, 2023
@sweep-open-router
Copy link

sweep-open-router bot commented Oct 24, 2023

Here's the PR! #13.

💎 Sweep Pro: I'm creating this ticket using GPT-4. You have unlimited GPT-4 tickets.

Actions (click)

  • ↻ Restart Sweep

Step 1: 🔎 Searching

I found the following snippets in your repository. I will now analyze these snippets and come up with a plan.

Some code snippets I looked at (click to expand). If some file is missing from here, you can mention the path in the ticket description.

{
"IndexPage": {
"title": "next-intl example",
"description": "This is a basic example that demonstrates the usage of <code>next-intl</code> with the Next.js App Router. Try changing the locale in the top right corner and see how the content changes."
},
"AboutPage": {
"title": "About",
"description": "<p>The routing is internationalized too.</p><p>If you're using the default language English, you'll see <code>/about</code> in the browser address bar on this page.</p><p>If you change the locale to German, the URL is prefixed with the locale (<code>/de/about</code>).</p>"
},
"Error": {
"title": "Something went wrong!",
"description": "<p>We've unfortunately encountered an error.</p><p>You can try to <retry>reload the page</retry> you were visiting.</p>"
},
"NotFoundPage": {
"title": "Page not found",
"description": "Please double-check the browser address bar or use the navigation to go to a known page."
},
"LocaleLayout": {
"title": "next-intl example"
},
"LocaleSwitcher": {
"label": "Change language",
"locale": "{locale, select, de {German} en {English} other {Unknown}}"
},
"Navigation": {
"home": "Home",
"about": "About"
},
"PageLayout": {
"links": {
"docs": {
"title": "Docs",
"description": "Learn more about next-intl in the official docs.",
"href": "https://next-intl-docs.vercel.app/"
},
"source": {
"title": "Source code",
"description": "Browse the source code of this example on GitHub.",
"href": "https://github.com/amannn/next-intl/tree/main/examples/example-next-13"
}
}
}

"use client"
import TypewriterComponent from "typewriter-effect"
import { useAuth } from "@clerk/nextjs"
import ShimmerButton from "@/components/magicui/shimmer-button"
import { ChevronRight } from "lucide-react"
import router from "next/router"
import {
RADIAN_BACKGROUND,
SHIMMER_BACKGROUND,
SHIMMER_HOVER,
} from "@/config/constants"
import { cn } from "@/lib/utils"
export const Hero = () => {
const { isSignedIn } = useAuth()
return (
<div className="text-primary font-bold py-36 text-center space-y-5">
<div className="text-4xl sm:text-5xl md:text-6xl lg:text-7xl space-y-5 font-extrabold">
<h1>AI-Driven Micro-SaaS for</h1>
<div className={cn("text-transparent bg-clip-text", RADIAN_BACKGROUND)}>
<TypewriterComponent
options={{
strings: [
"Social Media Marketing.",
"Content Writing.",
"Recruitment & HR.",
"Product Management.",
],
autoStart: true,
loop: true,
}}
/>
</div>
</div>
<div className="text-sm md:text-xl font-light text-muted-foreground">
Work 10x faster with your personal AI assistants.
</div>
<div className="grid md:grid-cols-1 place-items-center">
<ShimmerButton
className={cn(
"flex items-center justify-center shadow-2xl",
SHIMMER_HOVER
)}
background={SHIMMER_BACKGROUND}
onClick={() => {
router.push(isSignedIn ? "/dashboard" : "/sign-up")
}}
>
<span className="whitespace-pre bg-gradient-to-b from-black from-30% to-gray-300/80 bg-clip-text text-center text-sm lg:text-2xl font-semibold leading-none tracking-tight text-white dark:from-white dark:to-slate-900/10 dark:text-transparent z-10">
Get started for free
</span>
<ChevronRight className="h-6 w-6 duration-150 ease-in-out transform group-hover:translate-x-1 m-auto" />
</ShimmerButton>
</div>
<div className="text-muted-foreground text-xs md:text-sm font-normal">
No credit card required.
</div>
</div>
)

type Tool = {
name: string
icon: React.ReactNode
}
const tools: Tool[] = [
{
name: "Next.js 13",
icon: (
<svg viewBox="0 0 24 24" className="h-9 w-9 fill-current">
<path d="M11.572 0c-.176 0-.31.001-.358.007a19.76 19.76 0 0 1-.364.033C7.443.346 4.25 2.185 2.228 5.012a11.875 11.875 0 0 0-2.119 5.243c-.096.659-.108.854-.108 1.747s.012 1.089.108 1.748c.652 4.506 3.86 8.292 8.209 9.695.779.25 1.6.422 2.534.525.363.04 1.935.04 2.299 0 1.611-.178 2.977-.577 4.323-1.264.207-.106.247-.134.219-.158-.02-.013-.9-1.193-1.955-2.62l-1.919-2.592-2.404-3.558a338.739 338.739 0 0 0-2.422-3.556c-.009-.002-.018 1.579-.023 3.51-.007 3.38-.01 3.515-.052 3.595a.426.426 0 0 1-.206.214c-.075.037-.14.044-.495.044H7.81l-.108-.068a.438.438 0 0 1-.157-.171l-.05-.106.006-4.703.007-4.705.072-.092a.645.645 0 0 1 .174-.143c.096-.047.134-.051.54-.051.478 0 .558.018.682.154.035.038 1.337 1.999 2.895 4.361a10760.433 10760.433 0 0 0 4.735 7.17l1.9 2.879.096-.063a12.317 12.317 0 0 0 2.466-2.163 11.944 11.944 0 0 0 2.824-6.134c.096-.66.108-.854.108-1.748 0-.893-.012-1.088-.108-1.747-.652-4.506-3.859-8.292-8.208-9.695a12.597 12.597 0 0 0-2.499-.523A33.119 33.119 0 0 0 11.573 0zm4.069 7.217c.347 0 .408.005.486.047a.473.473 0 0 1 .237.277c.018.06.023 1.365.018 4.304l-.006 4.218-.744-1.14-.746-1.14v-3.066c0-1.982.01-3.097.023-3.15a.478.478 0 0 1 .233-.296c.096-.05.13-.054.5-.054z" />
</svg>
),
},
{
name: "React 18",
icon: (
<svg viewBox="0 0 24 24" className="h-9 w-9 fill-current">
<path d="M14.23 12.004a2.236 2.236 0 0 1-2.235 2.236 2.236 2.236 0 0 1-2.236-2.236 2.236 2.236 0 0 1 2.235-2.236 2.236 2.236 0 0 1 2.236 2.236zm2.648-10.69c-1.346 0-3.107.96-4.888 2.622-1.78-1.653-3.542-2.602-4.887-2.602-.41 0-.783.093-1.106.278-1.375.793-1.683 3.264-.973 6.365C1.98 8.917 0 10.42 0 12.004c0 1.59 1.99 3.097 5.043 4.03-.704 3.113-.39 5.588.988 6.38.32.187.69.275 1.102.275 1.345 0 3.107-.96 4.888-2.624 1.78 1.654 3.542 2.603 4.887 2.603.41 0 .783-.09 1.106-.275 1.374-.792 1.683-3.263.973-6.365C22.02 15.096 24 13.59 24 12.004c0-1.59-1.99-3.097-5.043-4.032.704-3.11.39-5.587-.988-6.38a2.167 2.167 0 0 0-1.092-.278zm-.005 1.09v.006c.225 0 .406.044.558.127.666.382.955 1.835.73 3.704-.054.46-.142.945-.25 1.44a23.476 23.476 0 0 0-3.107-.534A23.892 23.892 0 0 0 12.769 4.7c1.592-1.48 3.087-2.292 4.105-2.295zm-9.77.02c1.012 0 2.514.808 4.11 2.28-.686.72-1.37 1.537-2.02 2.442a22.73 22.73 0 0 0-3.113.538 15.02 15.02 0 0 1-.254-1.42c-.23-1.868.054-3.32.714-3.707.19-.09.4-.127.563-.132zm4.882 3.05c.455.468.91.992 1.36 1.564-.44-.02-.89-.034-1.345-.034-.46 0-.915.01-1.36.034.44-.572.895-1.096 1.345-1.565zM12 8.1c.74 0 1.477.034 2.202.093.406.582.802 1.203 1.183 1.86.372.64.71 1.29 1.018 1.946-.308.655-.646 1.31-1.013 1.95-.38.66-.773 1.288-1.18 1.87a25.64 25.64 0 0 1-4.412.005 26.64 26.64 0 0 1-1.183-1.86c-.372-.64-.71-1.29-1.018-1.946a25.17 25.17 0 0 1 1.013-1.954c.38-.66.773-1.286 1.18-1.868A25.245 25.245 0 0 1 12 8.098zm-3.635.254c-.24.377-.48.763-.704 1.16-.225.39-.435.782-.635 1.174-.265-.656-.49-1.31-.676-1.947.64-.15 1.315-.283 2.015-.386zm7.26 0c.695.103 1.365.23 2.006.387-.18.632-.405 1.282-.66 1.933a25.952 25.952 0 0 0-1.345-2.32zm3.063.675c.484.15.944.317 1.375.498 1.732.74 2.852 1.708 2.852 2.476-.005.768-1.125 1.74-2.857 2.475-.42.18-.88.342-1.355.493a23.966 23.966 0 0 0-1.1-2.98c.45-1.017.81-2.01 1.085-2.964zm-13.395.004c.278.96.645 1.957 1.1 2.98a23.142 23.142 0 0 0-1.086 2.964c-.484-.15-.944-.318-1.37-.5-1.732-.737-2.852-1.706-2.852-2.474 0-.768 1.12-1.742 2.852-2.476.42-.18.88-.342 1.356-.494zm11.678 4.28c.265.657.49 1.312.676 1.948-.64.157-1.316.29-2.016.39a25.819 25.819 0 0 0 1.341-2.338zm-9.945.02c.2.392.41.783.64 1.175.23.39.465.772.705 1.143a22.005 22.005 0 0 1-2.006-.386c.18-.63.406-1.282.66-1.933zM17.92 16.32c.112.493.2.968.254 1.423.23 1.868-.054 3.32-.714 3.708-.147.09-.338.128-.563.128-1.012 0-2.514-.807-4.11-2.28.686-.72 1.37-1.536 2.02-2.44 1.107-.118 2.154-.3 3.113-.54zm-11.83.01c.96.234 2.006.415 3.107.532.66.905 1.345 1.727 2.035 2.446-1.595 1.483-3.092 2.295-4.11 2.295a1.185 1.185 0 0 1-.553-.132c-.666-.38-.955-1.834-.73-3.703.054-.46.142-.944.25-1.438zm4.56.64c.44.02.89.034 1.345.034.46 0 .915-.01 1.36-.034-.44.572-.895 1.095-1.345 1.565-.455-.47-.91-.993-1.36-1.565z" />
</svg>
),
},
{
name: "Next Auth",
icon: (
<svg
viewBox="0 0 24 24"
fill="none"
stroke="currentColor"
strokeWidth="1"
className="h-9 w-9 fill-current"
>
<path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"></path>
</svg>
),
},
{
name: "Tailwind CSS",
icon: (
<svg viewBox="0 0 24 24" className="h-12 w-12 fill-current">
<path d="M12.001 4.8c-3.2 0-5.2 1.6-6 4.8 1.2-1.6 2.6-2.2 4.2-1.8.913.228 1.565.89 2.288 1.624C13.666 10.618 15.027 12 18.001 12c3.2 0 5.2-1.6 6-4.8-1.2 1.6-2.6 2.2-4.2 1.8-.913-.228-1.565-.89-2.288-1.624C16.337 6.182 14.976 4.8 12.001 4.8zm-6 7.2c-3.2 0-5.2 1.6-6 4.8 1.2-1.6 2.6-2.2 4.2-1.8.913.228 1.565.89 2.288 1.624 1.177 1.194 2.538 2.576 5.512 2.576 3.2 0 5.2-1.6 6-4.8-1.2 1.6-2.6 2.2-4.2 1.8-.913-.228-1.565-.89-2.288-1.624C10.337 13.382 8.976 12 6.001 12z" />
</svg>
),
},
{
name: "Radix UI",
icon: (
<svg
xmlns="http://www.w3.org/2000/svg"
viewBox="4 0 17 25"
className="h-9 w-9 fill-current"
>
<path d="M12 25a8 8 0 1 1 0-16v16zM12 0H4v8h8V0zM17 8a4 4 0 1 0 0-8 4 4 0 0 0 0 8z" />
</svg>
),
},
{
name: "Prisma",
icon: (
<svg
viewBox="0.34 -0.059977834648891726 33.11668247084116 39.96397783464889"
xmlns="http://www.w3.org/2000/svg"
className="h-9 w-9 fill-current"
>
<path
d="M32.908 30.475L19.151 1.26a2.208 2.208 0 0 0-1.88-1.257 2.183 2.183 0 0 0-2.01 1.042L.34 25.212a2.26 2.26 0 0 0 .025 2.426L7.66 38.935a2.346 2.346 0 0 0 2.635.969l21.17-6.262a2.32 2.32 0 0 0 1.457-1.258 2.27 2.27 0 0 0-.013-1.91zm-3.08 1.253L11.864 37.04c-.548.163-1.074-.312-.96-.865l6.418-30.731c.12-.575.914-.666 1.165-.134l11.881 25.23a.858.858 0 0 1-.541 1.188z"
clipRule="evenodd"
fillRule="evenodd"
/>
</svg>
),
},
]
export const Technologies = () => {
return (
<section className="container max-w-[1400px] pb-12 md:pb-16 lg:pb-24 mx-auto">
<div className="w-full flex flex-col items-center text-center gap-8">
<div className="text-center">
<p className="text-muted-foreground text-base sm:text-lg">
This project was built using the following technologies
</p>
</div>
<div className="w-full max-w-4xl mx-auto flex justify-center items-center flex-wrap gap-6 sm:gap-12 place-items-center">
{tools.map((tool, index) => (
<div key={index} className="flex items-center space-x-2">
{tool.icon}
<h3 className="text-2xl font-medium hidden sm:block">
{tool.name}
</h3>
</div>
))}
</div>
</div>
</section>
)

"use client"
import { Icons } from "@/components/icons"
import { buttonVariants } from "@/components/ui/button"
import { MAIN_COLOR } from "@/config/constants"
import { cn } from "@/lib/utils"
import { List } from "lucide-react"
import Link from "next-intl/link"
const features = [
{
id: "feature-ai",
header: "AI Feature 1",
name: "AI Feature Name 1",
description:
"Description for AI Feature 1. This feature provides advanced AI capabilities to your application, enhancing its functionality and user experience.",
icon: Icons.openai,
video:
"https://static.videezy.com/system/resources/previews/000/022/066/original/4k-dynamic-preloader-with-dots-animation.mp4",
cta: "Get Started",
href: "/sign-up",
reverse: false,
},
{
id: "feature-ai-2",
header: "AI Feature 2",
name: "AI Feature Name 2",
description:
"Description for AI Feature 2. This feature leverages AI to provide unique insights and analytics, helping you make data-driven decisions.",
icon: List,
video:
"https://static.videezy.com/system/resources/previews/000/022/066/original/4k-dynamic-preloader-with-dots-animation.mp4",
cta: "Get Started",
href: "/sign-up",
reverse: true,
},
{
id: "feature-ai-3",
header: "AI Feature 3",
name: "AI Feature Name 3",
description:
"Description for AI Feature 3. This feature uses AI to personalize user experiences, making your application more engaging and user-friendly.",
icon: Icons.user,
video:
"https://static.videezy.com/system/resources/previews/000/022/066/original/4k-dynamic-preloader-with-dots-animation.mp4",
cta: "Get Started",
href: "/sign-up",
reverse: false,
},
]
const FeatureSections = () => {
return (
<>
{features.map((feature) => (
<section id={feature.id} key={feature.id}>
<div className="mx-auto px-6 py-6 sm:py-20">
<div className="mx-auto grid max-w-2xl grid-cols-1 gap-x-16 gap-y-16 sm:gap-y-20 lg:mx-0 lg:max-w-none lg:grid-cols-5">
<div
className={cn("m-auto lg:col-span-2", {
"lg:order-last": feature.reverse,
})}
>
<h2
className={cn(
"text-base font-semibold leading-7",
MAIN_COLOR
)}
>
{feature.header}
</h2>
<p className="mt-2 text-3xl font-bold tracking-tight text-foreground sm:text-4xl">
{feature.name}
</p>
<p className="mt-6 text-lg leading-8 text-muted-foreground">
{feature.description}
</p>
<Link
className={cn(
buttonVariants({
variant: "default",
size: "lg",
}),
"mt-8"
)}
href={feature.href}
>
{feature.cta}
</Link>
</div>
<video
src={feature.video}
autoPlay
loop
muted
className="rounded-xl border m-auto lg:col-span-3 shadow-2xl"
/>
</div>
</div>
</section>
))}
</>
)
}

import { Icons } from "@/components/icons"
import { siteConfig } from "@/config/site"
import Link from "next-intl/link"
const TestimonialHighlight = () => {
return (
<>
<section id="testimonial-highlight">
<div className="max-w-screen-xl mx-auto px-4 md:px-8 py-20">
<Link
className="max-w-3xl mx-auto cursor-pointer text-center group"
href="https://twitter.com/0xGeegZ"
>
{/* <h3 className=" font-semibold pb-6">What people are saying</h3> */}
<figure>
<blockquote>
<p
className="text-accent-foreground text-xl text-center font-semibold sm:text-2xl italic group-hover:-translate-y-1 transition-all duration-300 ease-in-out
"
>
“🔥 {siteConfig.name} is awesome to build AI micro saas and
leverage Next13“
</p>
</blockquote>
<div className="mt-6">
<img
width={64}
height={64}
src="https://pbs.twimg.com/profile_images/1575152461156913152/bb0IchqM_400x400.jpg"
alt="GeegZ"
className="w-16 h-16 mx-auto rounded-full"
/>
<div className="mt-3">
<span className="block font-semibold">
GeegZ
<Icons.twitterVerified className="ml-1 mb-[0.2rem] inline h-4 w-4 text-blue-500" />
</span>
<span className="block text-accent-foreground text-sm mt-0.5">
Builder of {siteConfig.name}
</span>
<Icons.vercel className="w-24 mx-auto" />
</div>
</div>
</figure>
</Link>
</div>
</section>
</>
)
}

I also found the following external resources that might be helpful:

Summaries of links found in the content:

https://next-intl-docs.vercel.app/docs/getting-started/app-router-server-components:

The page provides a guide on how to implement application translation using the next-intl package in a Next.js TypeScript application. It starts by explaining the file structure for translations and then distinguishes between client components and server components.

For client components, the guide demonstrates how to import the useTranslations hook from next-intl and use it to replace hardcoded strings with translation function calls. It also explains the need to add the appropriate namespace to the translation function calls and provides an example of a client component implementation.

For server components, the guide explains how to import the getTranslations function from next-intl/server and use it to get translations for a specific namespace. It shows how to replace hardcoded strings with the translation function and provides an example of a server component implementation.

The guide also mentions the importance of adding the English translations to the src/i18n/messages/en.json file and provides examples of how to structure the translations for different components.

Overall, the guide provides step-by-step instructions and code snippets to help developers successfully implement application translation using next-intl in a Next.js TypeScript application.

https://next-intl-docs.vercel.app/docs/getting-started/app-router-client-components:

The page provides a guide on how to implement application translation using the next-intl package in a Next.js TypeScript application. It starts by explaining the file structure for translations and how to insert English translations for specific components in the en.json file. The page then explains the difference between client components and server components and provides examples of how to implement translations in each type of component.

For server components, the getTranslations function from next-intl/server is used to retrieve translations for a specific namespace, and the translation function t is used to replace hardcoded strings with translated text.

For client components, the useTranslations hook from next-intl is used to retrieve translations for a specific namespace, and the translation function t is used to replace hardcoded strings with translated text.

The page also mentions the importance of adding translations for each component in the en.json file and provides links to the Next.js documentation for more information on internationalization in client components and server components.

Overall, the page provides a step-by-step guide on how to implement application translation using next-intl in a Next.js TypeScript application, including code snippets and examples.


Step 2: ⌨️ Coding

  • src/components/landing/hero/hero.tsx ✅ Commit b0b7815
Modify src/components/landing/hero/hero.tsx with contents:
• Import the `useTranslations` hook from `next-intl` at the top of the file.
• Use the `useTranslations` hook to get translations for the `hero` namespace. Assign the returned translation function to a variable, e.g., `const t = useTranslations("hero")`.
• Replace all hardcoded text strings in the component with calls to the translation function `t`, passing the appropriate key as an argument. For example, replace `"AI-Driven Micro-SaaS for"` with `{t("aiDrivenMicroSaas")}`.
• Add the English translations for all the keys used in the `hero` namespace to the `src/i18n/messages/en.json` file.
  • src/components/landing/partners/technologies.tsx ✅ Commit 76098a0
Modify src/components/landing/partners/technologies.tsx with contents:
• Import the `useTranslations` hook from `next-intl` at the top of the file.
• Use the `useTranslations` hook to get translations for the `technologies` namespace. Assign the returned translation function to a variable, e.g., `const t = useTranslations("technologies")`.
• Replace all hardcoded text strings in the component with calls to the translation function `t`, passing the appropriate key as an argument. For example, replace `"This project was built using the following technologies"` with `{t("builtUsingTechnologies")}`.
• Add the English translations for all the keys used in the `technologies` namespace to the `src/i18n/messages/en.json` file.
  • src/components/landing/testimonials/testimonial-highlight.tsx ✅ Commit de648bf
Modify src/components/landing/testimonials/testimonial-highlight.tsx with contents:
• Import the `useTranslations` hook from `next-intl` at the top of the file.
• Use the `useTranslations` hook to get translations for the `testimonialHighlight` namespace. Assign the returned translation function to a variable, e.g., `const t = useTranslations("testimonialHighlight")`.
• Replace all hardcoded text strings in the component with calls to the translation function `t`, passing the appropriate key as an argument. For example, replace `"What people are saying"` with `{t("peopleSaying")}`.
• Add the English translations for all the keys used in the `testimonialHighlight` namespace to the `src/i18n/messages/en.json` file.
  • src/components/landing/features/column/feature-sections.tsx ✅ Commit 95af774
Modify src/components/landing/features/column/feature-sections.tsx with contents:
• Import the `useTranslations` hook from `next-intl` at the top of the file.
• Use the `useTranslations` hook to get translations for the `featureSections` namespace. Assign the returned translation function to a variable, e.g., `const t = useTranslations("featureSections")`.
• Replace all hardcoded text strings in the component with calls to the translation function `t`, passing the appropriate key as an argument. For example, replace `"AI Feature 1"` with `{t("aiFeature1")}`.
• Add the English translations for all the keys used in the `featureSections` namespace to the `src/i18n/messages/en.json` file.

Step 3: 🔁 Code Review

Here are my self-reviews of my changes at sweep/application-translation.

Here is the 1st review

Thank you for your work on this pull request. The changes in `src/components/landing/features/column/feature-sections.tsx` and `src/components/landing/partners/technologies.tsx` are correct and in line with the issue requirements. However, there are a few areas that need to be addressed:
  • In src/components/landing/hero/hero.tsx, the useTranslations hook from next-intl is imported correctly, but the hardcoded text strings in the component are not replaced with calls to the translation function t. Please replace all hardcoded text strings in this component with calls to t, passing the appropriate key as an argument.

  • Similarly, in src/components/landing/testimonials/testimonial-highlight.tsx, the useTranslations hook is imported correctly, but the hardcoded text strings in the component are not replaced with calls to the translation function t. Please replace all hardcoded text strings in this component with calls to t, passing the appropriate key as an argument.

  • Lastly, please add the English translations for all the keys used in the hero, technologies, testimonialHighlight, and featureSections namespaces to the src/i18n/messages/en.json file. The changes in this file are not provided in the diff.

Please make these changes and update the pull request. If you have any questions, feel free to ask.

I finished incorporating these changes.


🎉 Latest improvements to Sweep:

  • Sweep can now passively improve your repository! Check out Rules to learn more.

💡 To recreate the pull request edit the issue title or description. To tweak the pull request, leave a comment on the pull request.
Join Our Discord

@sweep-open-router sweep-open-router bot linked a pull request Oct 24, 2023 that will close this issue
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant