auto-claude: subtask-1-2 - Document directory structure and file organization
This commit is contained in:
+268
-8
@@ -82,14 +82,274 @@ return <button>{t('newAction')}</button>;
|
|||||||
This documentation is organized into the following sections:
|
This documentation is organized into the following sections:
|
||||||
|
|
||||||
### 📁 Directory Structure & Organization
|
### 📁 Directory Structure & Organization
|
||||||
> Learn about the file organization, active vs. legacy systems, and configuration files
|
|
||||||
>
|
The i18n system is organized into three main directories, each serving a specific purpose in the translation infrastructure.
|
||||||
> **Topics covered:**
|
|
||||||
> - `src/i18n/` - Configuration files
|
#### Overview of Directory Structure
|
||||||
> - `src/messages/` - Active JSON translation files
|
|
||||||
> - `src/i18n/locales-old/` - Legacy TypeScript translations (deprecated)
|
```
|
||||||
> - `config.ts` - Locale metadata and settings
|
src/
|
||||||
> - `request.ts` - next-intl integration
|
├── i18n/ # Configuration Layer
|
||||||
|
│ ├── config.ts # ✅ Locale definitions & metadata
|
||||||
|
│ ├── request.ts # ✅ next-intl integration
|
||||||
|
│ └── locales-old/ # ⚠️ DEPRECATED - Do NOT use
|
||||||
|
│ ├── de.ts
|
||||||
|
│ ├── en.ts
|
||||||
|
│ └── sr.ts
|
||||||
|
│
|
||||||
|
└── messages/ # ✅ Active Translation Files
|
||||||
|
├── de.json # German translations
|
||||||
|
├── en.json # English translations
|
||||||
|
└── sr.json # Serbian translations
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
#### `src/i18n/` - Configuration Directory
|
||||||
|
|
||||||
|
This directory contains the core configuration files that define how the i18n system operates.
|
||||||
|
|
||||||
|
**Purpose:** Centralized configuration for locale definitions, metadata, and next-intl integration.
|
||||||
|
|
||||||
|
##### `config.ts` - Locale Metadata & Settings
|
||||||
|
|
||||||
|
**Location:** `src/i18n/config.ts`
|
||||||
|
|
||||||
|
This is the **single source of truth** for all locale-related configuration.
|
||||||
|
|
||||||
|
**What it contains:**
|
||||||
|
|
||||||
|
1. **Locales Array** - Defines all supported languages
|
||||||
|
```typescript
|
||||||
|
export const locales = ['de', 'en', 'sr'] as const;
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Default Locale** - Fallback language
|
||||||
|
```typescript
|
||||||
|
export const defaultLocale = 'de' as const;
|
||||||
|
```
|
||||||
|
|
||||||
|
3. **Locale Type** - TypeScript type for type-safe locale handling
|
||||||
|
```typescript
|
||||||
|
export type Locale = (typeof locales)[number];
|
||||||
|
```
|
||||||
|
|
||||||
|
4. **Display Names** - Human-readable language names
|
||||||
|
```typescript
|
||||||
|
export const localeNames: Record<Locale, string> = {
|
||||||
|
de: 'Deutsch',
|
||||||
|
en: 'English',
|
||||||
|
sr: 'Srpski',
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
5. **Locale Flags** - Emoji flags for UI
|
||||||
|
```typescript
|
||||||
|
export const localeFlags: Record<Locale, string> = {
|
||||||
|
de: '🇩🇪',
|
||||||
|
en: '🇬🇧',
|
||||||
|
sr: '🇷🇸',
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
6. **Extended Metadata** - SEO and regional data
|
||||||
|
```typescript
|
||||||
|
export const localeMetadata: Record<Locale, {
|
||||||
|
language: string; // ISO 639-1 code (e.g., 'de')
|
||||||
|
region: string; // ISO 3166-1 code (e.g., 'DE')
|
||||||
|
hreflang: string; // For <link rel="alternate"> tags
|
||||||
|
ogLocale: string; // For Open Graph meta tags
|
||||||
|
script: string; // Writing system (e.g., 'Latn')
|
||||||
|
territory: string; // Full country name
|
||||||
|
currency: string; // ISO 4217 code (e.g., 'EUR')
|
||||||
|
}> = {
|
||||||
|
de: {
|
||||||
|
language: 'de',
|
||||||
|
region: 'DE',
|
||||||
|
hreflang: 'de-DE',
|
||||||
|
ogLocale: 'de_DE',
|
||||||
|
script: 'Latn',
|
||||||
|
territory: 'Germany',
|
||||||
|
currency: 'EUR',
|
||||||
|
},
|
||||||
|
// ... en, sr
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
7. **SEO Keywords** - Localized keywords for each language
|
||||||
|
```typescript
|
||||||
|
export const seoKeywords: Record<Locale, string[]> = {
|
||||||
|
de: ['Fullstack Developer', 'KI Entwickler', 'Köln', ...],
|
||||||
|
en: ['AI Developer', 'Remote Developer Europe', 'London', ...],
|
||||||
|
sr: ['AI Programer Srbija', 'Beograd', 'Novi Sad', ...],
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
**When to modify this file:**
|
||||||
|
- ✅ Adding a new language
|
||||||
|
- ✅ Updating SEO keywords
|
||||||
|
- ✅ Changing metadata for Open Graph or hreflang
|
||||||
|
- ❌ Adding translation strings (use `src/messages/` instead)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
##### `request.ts` - next-intl Integration
|
||||||
|
|
||||||
|
**Location:** `src/i18n/request.ts`
|
||||||
|
|
||||||
|
This file integrates the translation system with next-intl and handles runtime locale resolution.
|
||||||
|
|
||||||
|
**What it does:**
|
||||||
|
|
||||||
|
```typescript
|
||||||
|
import { getRequestConfig } from 'next-intl/server';
|
||||||
|
import { locales, type Locale } from './config';
|
||||||
|
|
||||||
|
export default getRequestConfig(async ({ requestLocale }) => {
|
||||||
|
let locale = await requestLocale;
|
||||||
|
|
||||||
|
// Validate locale and fallback to default if invalid
|
||||||
|
if (!locale || !locales.includes(locale as Locale)) {
|
||||||
|
locale = 'de';
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
locale,
|
||||||
|
messages: (await import(`../messages/${locale}.json`)).default,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
```
|
||||||
|
|
||||||
|
**Key responsibilities:**
|
||||||
|
|
||||||
|
1. **Locale Validation** - Ensures only valid locales are used
|
||||||
|
2. **Fallback Logic** - Defaults to German (`de`) if locale is invalid or missing
|
||||||
|
3. **Dynamic Import** - Loads the appropriate translation JSON file at runtime
|
||||||
|
4. **Type Safety** - Uses the `Locale` type from `config.ts` for validation
|
||||||
|
|
||||||
|
**Flow:**
|
||||||
|
1. Receives `requestLocale` from next-intl (extracted from URL)
|
||||||
|
2. Validates against the `locales` array
|
||||||
|
3. Falls back to `de` if validation fails
|
||||||
|
4. Dynamically imports the corresponding JSON file from `src/messages/`
|
||||||
|
5. Returns locale and messages to next-intl
|
||||||
|
|
||||||
|
**When to modify this file:**
|
||||||
|
- ✅ Changing fallback locale logic
|
||||||
|
- ✅ Adding custom locale resolution rules
|
||||||
|
- ✅ Implementing locale persistence (cookies, etc.)
|
||||||
|
- ❌ Most use cases don't require changes
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
#### `src/messages/` - Active Translation Files ✅
|
||||||
|
|
||||||
|
**Location:** `src/messages/`
|
||||||
|
|
||||||
|
This directory contains the **active, production-ready** translation files in JSON format.
|
||||||
|
|
||||||
|
**Files:**
|
||||||
|
- `de.json` - German translations (default)
|
||||||
|
- `en.json` - English translations
|
||||||
|
- `sr.json` - Serbian translations
|
||||||
|
|
||||||
|
**Why JSON?**
|
||||||
|
- ✅ Simple, human-readable format
|
||||||
|
- ✅ Easy to edit without TypeScript knowledge
|
||||||
|
- ✅ Smaller bundle size (dynamic imports)
|
||||||
|
- ✅ Better IDE support for JSON
|
||||||
|
- ✅ Easier integration with translation tools
|
||||||
|
|
||||||
|
**Structure:**
|
||||||
|
|
||||||
|
Each file contains nested JSON objects organized by namespace:
|
||||||
|
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"meta": {
|
||||||
|
"site": { "name": "...", "title": "..." },
|
||||||
|
"author": { "name": "...", "role": "..." },
|
||||||
|
"social": { "linkedin": "...", "github": "..." }
|
||||||
|
},
|
||||||
|
"common": {
|
||||||
|
"nav": { "home": "...", "about": "..." },
|
||||||
|
"actions": { "readMore": "...", "submit": "..." }
|
||||||
|
},
|
||||||
|
"pages": {
|
||||||
|
"home": { "hero": { "title": "..." } },
|
||||||
|
"about": { "title": "..." }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
**Best Practices:**
|
||||||
|
|
||||||
|
1. **Keep keys synchronized** - All three files should have identical structure
|
||||||
|
2. **Use nested namespaces** - Organize by feature or page (e.g., `common`, `pages.home`)
|
||||||
|
3. **Descriptive keys** - Use semantic names like `hero.title` instead of `text1`
|
||||||
|
4. **No hardcoded text** - All user-facing text should be in these files
|
||||||
|
|
||||||
|
**When to modify these files:**
|
||||||
|
- ✅ Adding new translation keys
|
||||||
|
- ✅ Updating existing translations
|
||||||
|
- ✅ Fixing typos or improving wording
|
||||||
|
- ✅ Adding new pages or features
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
#### `src/i18n/locales-old/` - Legacy System ⚠️ DEPRECATED
|
||||||
|
|
||||||
|
**Location:** `src/i18n/locales-old/`
|
||||||
|
|
||||||
|
This directory contains **deprecated** TypeScript-based translations from a previous implementation.
|
||||||
|
|
||||||
|
**Files:**
|
||||||
|
- `de.ts` - Old German translations
|
||||||
|
- `en.ts` - Old English translations
|
||||||
|
- `sr.ts` - Old Serbian translations
|
||||||
|
|
||||||
|
**⚠️ IMPORTANT:** **Do NOT use these files!**
|
||||||
|
|
||||||
|
**Why it exists:**
|
||||||
|
- These files were part of an older TypeScript-based translation system
|
||||||
|
- Kept temporarily during migration for reference
|
||||||
|
- **Not loaded by the application** - they are completely inactive
|
||||||
|
|
||||||
|
**Why the migration happened:**
|
||||||
|
- JSON is simpler and more maintainable than TypeScript objects
|
||||||
|
- Better performance with dynamic imports
|
||||||
|
- Easier for non-developers to edit translations
|
||||||
|
- Better tooling support for JSON translation files
|
||||||
|
|
||||||
|
**What to do:**
|
||||||
|
- ❌ Do NOT add new keys here
|
||||||
|
- ❌ Do NOT reference these files in code
|
||||||
|
- ✅ Use `src/messages/*.json` for all translations
|
||||||
|
- ✅ These files can be safely deleted once migration is verified complete
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
#### File Relationships
|
||||||
|
|
||||||
|
```mermaid
|
||||||
|
graph TD
|
||||||
|
A[config.ts] -->|Defines locales| B[request.ts]
|
||||||
|
B -->|Loads messages| C[messages/*.json]
|
||||||
|
B -->|Validates locale| A
|
||||||
|
D[Components] -->|useTranslations| C
|
||||||
|
E[locales-old/*] -.->|DEPRECATED| F[Not Used]
|
||||||
|
```
|
||||||
|
|
||||||
|
**Summary:**
|
||||||
|
|
||||||
|
| Directory/File | Status | Purpose | When to Edit |
|
||||||
|
|----------------|--------|---------|--------------|
|
||||||
|
| `src/i18n/config.ts` | ✅ Active | Locale definitions & metadata | Adding locales, SEO keywords |
|
||||||
|
| `src/i18n/request.ts` | ✅ Active | next-intl integration | Rarely (fallback logic) |
|
||||||
|
| `src/messages/*.json` | ✅ Active | Translation strings | Frequently (new translations) |
|
||||||
|
| `src/i18n/locales-old/` | ⚠️ Deprecated | Legacy TypeScript translations | Never (can be deleted) |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
### 🔑 Adding Translation Keys
|
### 🔑 Adding Translation Keys
|
||||||
> Step-by-step guide to adding and managing translations
|
> Step-by-step guide to adding and managing translations
|
||||||
|
|||||||
Reference in New Issue
Block a user