Skip to content

Commit

Permalink
Merge pull request #1094 from tfuent1/i18nMapMigration
Browse files Browse the repository at this point in the history
I18nMap migration
  • Loading branch information
andrewtavis authored Jan 18, 2025
2 parents 5775af3 + bfa5a0f commit ebd13a0
Show file tree
Hide file tree
Showing 125 changed files with 871 additions and 530 deletions.
19 changes: 12 additions & 7 deletions STYLEGUIDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -239,23 +239,28 @@ activist is a global platform and must function in countless different regions a
>
> - This is the source from which all the other languages are translated from
> - Edits to the other files should be made on activist's [public localization project on Weblate](https://hosted.weblate.org/projects/activist/activist)
> - Do not put the JSON dictionaries into different levels!
> - Do not convert the JSON dictionaries into nested sub-objects!
> - The purpose of the flat dictionaries is so that we can search for the key in the codebase and easily find its uses and where it's defined
> - Do not include periods in aria-labels (screen reader user will configure their own preferences for a hard stop)
Localization keys should be defined based on the file in which they're used within the platform and the content that they refer to (`CONTENT_REFERENCE` below). Please use the following rules as a guide if you find yourself needing to create new localization keys:

- Please use the `i18nMap` object for all texts within the frontend
- This object returns the sequence of object methods as a string and allows ESLint to be used to check key accuracy
- Ex: Using the `i18nMap` object:
-`i18nMap._global.about`
-`"_global.about"`
- Separate directories and references by `.` and PascalCase/camelCase file name components by `_` in keys
- Ex: `"components.search_bar.CONTENT_REFERENCE"` for the `SearchBar` component
- Ex: `i18nMap.components.search_bar.CONTENT_REFERENCE` for the `SearchBar` component
- Even though Nuxt allows for us to nest components in directories, avoid repetition in the directory path used to define the localization key
- Ex: If you're defining a key within `CardAbout`:
-`"components.card_about.CONTENT_REFERENCE"`
-`"components.card.card_about.CONTENT_REFERENCE"`
-`i18nMap.components.card_about.CONTENT_REFERENCE`
-`i18nMap.components.card.card_about.CONTENT_REFERENCE`
- Define keys based on the lowest level file in which they're used
- Use `_global` to indicate that a key is used in multiple places in a given directory
- Ex: You're creating a key that's used by multiple cards:
-`"components.card._global.CONTENT_REFERENCE"`
-`"components.card.INDIVIDUAL_COMPONENT.CONTENT_REFERENCE"`
-`i18nMap.components.card._global.CONTENT_REFERENCE`
-`i18nMap.components.card.INDIVIDUAL_COMPONENT.CONTENT_REFERENCE`
- Please end all aria-label keys with `_alt_text` so the localization team knows that they're for screen readers
- If you need a capitalized and lower case version of a word, signify the lower case version with `_lower` at the end of the key
- For pages with long texts please follow the below naming criteria:
Expand All @@ -274,7 +279,7 @@ Localization keys should be defined based on the file in which they're used with
- This makes sure that content writers and the i18n team are only working with language that's actively in use

> [!NOTE]
> The activist community also maintains the [i18n-check project](https://github.com/activist-org/i18n-check-action?tab=readme-ov-file#contentions) that enforces all of the above in pull requests. Do your best and we'll help you out during the PR process! You can also join us in the [localization room on Matrix](https://matrix.to/#/!DzbdYyfhjinQBWXgQe:matrix.org?via=matrix.org) if you have questions :)
> The activist community also maintains the [i18n-check project](https://github.com/activist-org/i18n-check) that enforces all of the above in pull requests. Do your best and we'll help you out during the PR process! You can also join us in the [localization room on Matrix](https://matrix.to/#/!DzbdYyfhjinQBWXgQe:matrix.org?via=matrix.org) if you have questions :)
<a id="images-icons"></a>

Expand Down
24 changes: 13 additions & 11 deletions frontend/components/EmptyState.vue
Original file line number Diff line number Diff line change
Expand Up @@ -8,36 +8,36 @@
<div>
<!-- Header -->
<span v-if="pageType == 'organizations'" class="responsive-h2">{{
$t("components.empty_state.organizations_header")
$t(i18nMap.components.empty_state.organizations_header)
}}</span>
<span v-if="pageType == 'groups'" class="responsive-h2">{{
$t("components.empty_state.groups_header")
$t(i18nMap.components.empty_state.groups_header)
}}</span>
<span v-if="pageType == 'events'" class="responsive-h2">{{
$t("components.empty_state.events_header")
$t(i18nMap.components.empty_state.events_header)
}}</span>
<span v-if="pageType == 'resources'" class="responsive-h2">{{
$t("components.empty_state.resources_header")
$t(i18nMap.components.empty_state.resources_header)
}}</span>
<span v-if="pageType == 'faq'" class="responsive-h2">{{
$t("components.empty_state.faq_header")
$t(i18nMap.components.empty_state.faq_header)
}}</span>
<span v-if="pageType == 'team'" class="responsive-h2">{{
$t("components.empty_state.team_header")
$t(i18nMap.components.empty_state.team_header)
}}</span>
<span v-if="pageType == 'affiliates'" class="responsive-h2">{{
$t("components.empty_state.affiliates_header")
$t(i18nMap.components.empty_state.affiliates_header)
}}</span>
<span v-if="pageType == 'tasks'" class="responsive-h2">{{
$t("components.empty_state.tasks_header")
$t(i18nMap.components.empty_state.tasks_header)
}}</span>
<span v-if="pageType == 'discussions'" class="responsive-h2">{{
$t("components.empty_state.discussions_header")
$t(i18nMap.components.empty_state.discussions_header)
}}</span>
<!-- Message -->
<div v-if="!permission" class="flex flex-col space-y-6 py-6">
<span class="responsive-h4">{{
$t("components.empty_state.message_no_permission")
$t(i18nMap.components.empty_state.message_no_permission)
}}</span>
<PageCommunityFooter
header="components.empty_state.cta_header_no_permission"
Expand All @@ -52,7 +52,7 @@
</div>
<div v-else class="flex flex-col space-y-6 py-6">
<span class="responsive-h4">{{
$t("components.empty_state.message_with_permission")
$t(i18nMap.components.empty_state.message_with_permission)
}}</span>
<div
class="mx-auto grid max-w-[70%] grid-cols-1 gap-y-4 pb-6 sm:mx-0 sm:max-w-[90%] sm:grid-cols-2 sm:grid-rows-1 sm:gap-x-4 sm:gap-y-0 md:max-w-[70%] md:gap-x-6 lg:max-w-[60%] xl:max-w-[50%] xl:gap-x-8 2xl:max-w-[80%]"
Expand Down Expand Up @@ -112,6 +112,8 @@
</template>

<script setup lang="ts">
import { i18nMap } from "~/types/i18n-map";

defineProps<{
pageType:
| "organizations"
Expand Down
5 changes: 3 additions & 2 deletions frontend/components/FriendlyCaptcha.vue
Original file line number Diff line number Diff line change
Expand Up @@ -15,19 +15,20 @@
class="style-btn flex w-full cursor-not-allowed items-center space-x-4 rounded-md border-none p-1 px-3 text-lg shadow-none"
:disabled="true"
:aria-label="
$t('components.friendly_captcha.captcha_disabled_aria_label')
$t(i18nMap.components.friendly_captcha.captcha_disabled_aria_label)
"
>
<Icon :name="IconMap.SHIELD" size="28px" />
<p class="font-bold">
{{ $t("components.friendly_captcha.captcha_disabled") }}
{{ $t(i18nMap.components.friendly_captcha.captcha_disabled) }}
</p>
</button>
</div>
</template>

<script setup lang="ts">
import VueFriendlyCaptcha from "@somushq/vue3-friendly-captcha";
import { i18nMap } from "~/types/i18n-map";
import { IconMap } from "~/types/icon-map";

const devMode = useDevMode();
Expand Down
4 changes: 2 additions & 2 deletions frontend/components/Loading.vue
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,13 @@
v-if="$colorMode.value == 'light'"
class="h-40"
:src="ACTIVIST_ICON_LIGHT_URL"
:alt="$t('_global.activist_icon_img_alt_text')"
:alt="$t(i18nMap._global.activist_icon_img_alt_text)"
/>
<img
v-else-if="$colorMode.value == 'dark'"
class="h-40"
:src="ACTIVIST_ICON_DARK_URL"
:alt="$t('_global.activist_icon_img_alt_text')"
:alt="$t(i18nMap._global.activist_icon_img_alt_text)"
/>
</div>
</div> -->
Expand Down
6 changes: 3 additions & 3 deletions frontend/components/SearchBar.vue
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@
>
<TooltipBase
class="invisible -mt-8"
:text="$t('components._global.slash_tooltip_label')"
:text="$t(i18nMap.components._global.slash_tooltip_label)"
/>
<p class="-mt-[0.075rem]">/</p>
</div>
Expand All @@ -52,7 +52,7 @@
>
<TooltipBase
class="invisible -mt-8"
:text="$t('components._global.command_tooltip_label')"
:text="$t(i18nMap.components._global.command_tooltip_label)"
/>
<p>⌘k</p>
</div>
Expand All @@ -62,7 +62,7 @@
>
<TooltipBase
class="invisible -mt-8"
:text="$t('components._global.control_tooltip_label')"
:text="$t(i18nMap.components._global.control_tooltip_label)"
/>
<p>⌃k</p>
</div>
Expand Down
8 changes: 6 additions & 2 deletions frontend/components/btn/BtnRoadMap.vue
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,12 @@
id="btn-roadmap"
class="style-btn select-none items-center rounded-md px-3 py-[0.35rem] text-base font-semibold"
to="https://docs.activist.org/activist/product/about/roadmap"
:aria-label="$t('components.btn_road_map.aria_label')"
:aria-label="$t(i18nMap.components.btn_road_map.aria_label)"
>
{{ $t("components._global.roadmap") }}
{{ $t(i18nMap.components._global.roadmap) }}
</NuxtLink>
</template>

<script setup lang="ts">
import { i18nMap } from "~/types/i18n-map";
</script>
3 changes: 2 additions & 1 deletion frontend/components/btn/BtnShareIcon.vue
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
v-if="contentCopied"
class="text-accepted-green hover:text-accepted-green dark:text-accepted-green dark:hover:text-accepted-green"
:iconName="IconMap.SQUARE_CHECK"
:text="$t('components.btn_share_icon.url_copied')"
:text="$t(i18nMap.components.btn_share_icon.url_copied)"
:iconSize="iconSize"
/>
</div>
Expand All @@ -59,6 +59,7 @@ import { ref, type Component } from "vue";
import { IconMap } from "~/types/icon-map";
import { toast } from "vue-sonner";
import { useI18n } from "vue-i18n";
import { i18nMap } from "~/types/i18n-map";

const vueSocials: { [key: string]: Component } = {
SEmail,
Expand Down
20 changes: 14 additions & 6 deletions frontend/components/card/CardConnect.vue
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<div class="card-style px-5 py-5">
<div class="flex items-center gap-5">
<h3 class="responsive-h3 text-left font-display">
{{ $t("components._global.connect") }}
{{ $t(i18nMap.components._global.connect) }}
</h3>
<div
class="cursor-pointer break-all rounded-lg p-1 text-primary-text transition-all hover:text-distinct-text"
Expand Down Expand Up @@ -83,22 +83,29 @@
<PopupNewField
@on-cta-clicked="emit('on-new-account')"
@on-close-clicked="onClose(close)"
:title="$t('components.card_connect.app_account_popup_title')"
:title="
$t(i18nMap.components.card_connect.app_account_popup_title)
"
:fieldNamePrompt="
$t(
'components.card_connect.app_account_popup_field_name_prompt'
i18nMap.components.card_connect
.app_account_popup_field_name_prompt
)
"
:fieldLabelPrompt="
$t(
'components.card_connect.app_account_popup_field_label_prompt'
i18nMap.components.card_connect
.app_account_popup_field_label_prompt
)
"
:ctaBtnLabel="
$t('components.card_connect.app_account_popup_cta_btn_label')
$t(
i18nMap.components.card_connect
.app_account_popup_cta_btn_label
)
"
:ctaBtnAriaLabel="
$t('components.card_connect.new_account_aria_label')
$t(i18nMap.components.card_connect.new_account_aria_label)
"
/>
</PopoverPanel>
Expand All @@ -114,6 +121,7 @@ import { Popover, PopoverButton, PopoverPanel } from "@headlessui/vue";
import type { Group } from "~/types/communities/group";
import type { Organization } from "~/types/communities/organization";
import type { Event } from "~/types/events/event";
import { i18nMap } from "~/types/i18n-map";
import { IconMap } from "~/types/icon-map";

const props = defineProps<{
Expand Down
12 changes: 7 additions & 5 deletions frontend/components/card/CardDangerZone.vue
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
>
<div class="flex flex-col gap-5">
<h3 class="responsive-h3 text-left font-display font-bold">
{{ $t("components.card_danger_zone.header") }}
{{ $t(i18nMap.components.card_danger_zone.header) }}
</h3>
<p>{{ description }}</p>
<form method="post">
Expand All @@ -17,10 +17,10 @@
class="responsive-h4 font-bold text-primary-text"
for="username"
:placeholder="
$t('components.card_danger_zone.username_placeholder')
$t(i18nMap.components.card_danger_zone.username_placeholder)
"
>
{{ $t("components.card_danger_zone.username_label") }} *
{{ $t(i18nMap.components.card_danger_zone.username_label) }} *
</label>
<input
id="username"
Expand All @@ -31,9 +31,9 @@
<label
class="responsive-h4 font-bold text-primary-text"
for="password"
:placeholder="$t('_global.enter_password')"
:placeholder="$t(i18nMap._global.enter_password)"
>
{{ $t("components.card_danger_zone.password_label") }} *
{{ $t(i18nMap.components.card_danger_zone.password_label) }} *
</label>
<input
id="password"
Expand All @@ -57,6 +57,8 @@
</template>

<script setup lang="ts">
import { i18nMap } from "~/types/i18n-map";

defineProps<{
description: string;
ctaBtnText: string;
Expand Down
7 changes: 4 additions & 3 deletions frontend/components/card/CardDatePicker.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,19 @@
<template>
<form class="card-style flex w-full flex-col space-y-3 px-5 py-4">
<h1 class="text-2xl">
<strong>{{ $t("components.card_date_picker.date") }} *</strong>
<strong>{{ $t(i18nMap.components.card_date_picker.date) }} *</strong>
</h1>
<div class="flex grow">
<div class="flex w-[50%] flex-row space-x-2">
<FormCheckbox />
<label for="All Day">{{
$t("components.card_date_picker.all_day")
$t(i18nMap.components.card_date_picker.all_day)
}}</label>
</div>
<div class="flex w-[50%] flex-row space-x-2 pl-1">
<FormCheckbox />
<label for="Multiple Days">{{
$t("components.card_date_picker.multiple_days")
$t(i18nMap.components.card_date_picker.multiple_days)
}}</label>
</div>
</div>
Expand Down Expand Up @@ -50,6 +50,7 @@
<script setup lang="ts">
import { DatePicker } from "v-calendar";
import "v-calendar/style.css";
import { i18nMap } from "~/types/i18n-map";

const date1 = "2021-02-28T18:20:00.000Z";
const date2 = "2021-02-28T18:20:00.000Z";
Expand Down
5 changes: 3 additions & 2 deletions frontend/components/card/CardDetails.vue
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
<div class="flex-col space-y-3">
<div class="flex items-center gap-5">
<h3 class="responsive-h3 text-left font-display">
{{ $t("components.card_details.header") }}
{{ $t(i18nMap.components.card_details.header) }}
</h3>
<IconEdit
@click="openModalEditTextEvent()"
Expand Down Expand Up @@ -38,7 +38,7 @@
</div>
<!-- <MetaTagAttendance
:numAttending="event.attendees ? event.attendees.length : 0"
:label="$t('components.card_details.attending')"
:label="$t(i18nMap.components.card_details.attending)"
/> -->
<MetaTagLocation
v-if="event.offlineLocation"
Expand All @@ -53,6 +53,7 @@

<script setup lang="ts">
import { useModalHandlers } from "~/composables/useModalHandlers";
import { i18nMap } from "~/types/i18n-map";

const { openModal: openModalEditTextEvent } =
useModalHandlers("ModalEditTextEvent");
Expand Down
5 changes: 3 additions & 2 deletions frontend/components/card/CardDonate.vue
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<div class="card-style flex flex-col space-y-3 px-5 py-5">
<div class="flex items-center gap-5">
<h3 class="responsive-h3 text-left font-display">
{{ $t("components.card_donate.donate") }}
{{ $t(i18nMap.components.card_donate.donate) }}
</h3>
<div
class="cursor-pointer break-all rounded-lg p-1 text-primary-text transition-all hover:text-distinct-text"
Expand All @@ -24,7 +24,7 @@
</div>
<p v-if="donationPrompt">{{ donationPrompt }}</p>
<p v-else>
{{ $t("components.card_donate.template_text") }}
{{ $t(i18nMap.components.card_donate.template_text) }}
</p>
<BtnRouteExternal
class="flex"
Expand All @@ -40,6 +40,7 @@
</template>

<script setup lang="ts">
import { i18nMap } from "~/types/i18n-map";
import { IconMap } from "~/types/icon-map";

defineProps<{
Expand Down
Loading

0 comments on commit ebd13a0

Please sign in to comment.