npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

srcdev-nuxt-i18n

v0.1.1

Published

[![Tests](https://github.com/srcdev/srcdev-nuxt-i18n/workflows/Tests/badge.svg)](https://github.com/srcdev/srcdev-nuxt-i18n/actions/workflows/test.yml) [![npm version](https://badge.fury.io/js/srcdev-nuxt-i18n.svg)](https://badge.fury.io/js/srcdev-nuxt-i1

Readme

srcdev-nuxt-i18n

Tests npm version License

A standalone Nuxt layer providing i18n infrastructure for SRCDEV apps. Consuming apps get locale switching, RTL support, and reusable error translations out of the box via Nuxt's extends mechanism.

What's included

  • @nuxtjs/i18n v10 configured with 3 locales: en-GB (LTR), zh-CN (LTR), ar-YE (RTL)
  • LocaleSwitcher component — renders a button per locale, calls setLocale() on click, available via Nuxt auto-import
  • useRawLocaleData<T>(path, defaultValue?) — hydration-safe locale data composable with AST normalisation. Required for arrays/objects — see "Known gotchas" below
  • useMarkdown() — markdown-it renderer; external links get target="_blank" rel="noopener noreferrer"
  • Base translationsglobal.siteName (blank, override in consuming app) and reusable errors.* keys (404, 500, serverError, general, actions, help, contact)
  • Build script — merges modular JSON source files into compiled .ts locale files

Usage

1. Install peer dependencies in your consuming app

npm install @nuxtjs/[email protected] markdown-it

2. Extend the layer

// nuxt.config.ts
export default defineNuxtConfig({
  extends: ["../srcdev-nuxt-i18n"], // local path, or npm package name once published
})

3. Override global.siteName

Create a locale source file in your consuming app:

// i18n-source/locales/global/en-GB.json
{ "global": { "siteName": "Your App Name" } }

4. Wire up reactive <html lang>/dir and titleTemplate

Not automatic — add this to your consuming app's app/app.vue (or wherever your root layout lives):

<script setup lang="ts">
const { locale, locales, t } = useI18n()

const currentLocale = computed(() => locales.value.find(l => l.code === locale.value))

useHead({
  htmlAttrs: {
    lang: computed(() => currentLocale.value?.language || currentLocale.value?.code || "en"),
    dir: computed(() => currentLocale.value?.dir || "ltr"),
  },
  titleTemplate: computed(() => `%s - ${t("global.siteName")}`),
})
</script>

Without this, <html lang> stays static regardless of the active locale.

Claude Code Skills

This package ships Claude Code skills — reference docs for i18n tasks and composables — in the .claude/ directory.

To copy them into your consuming app after install, add a setup:claude script:

"scripts": {
  "setup:claude": "cp -r node_modules/srcdev-nuxt-i18n/.claude/skills .claude/skills/srcdev-nuxt-i18n",
  "postinstall": "nuxt prepare && npm run setup:claude"
}

Then run once to bootstrap:

npm run setup:claude

Skills land in .claude/skills/srcdev-nuxt-i18n/ and never conflict with your own project's skills or skills from other layers.

Using multiple SRCDEV layers

If your app also consumes srcdev-nuxt-components, chain both copy commands so a single postinstall handles all layers:

"scripts": {
  "setup:claude": "cp -r node_modules/srcdev-nuxt-components/.claude/skills .claude/skills/srcdev-nuxt-components && cp -r node_modules/srcdev-nuxt-i18n/.claude/skills .claude/skills/srcdev-nuxt-i18n",
  "postinstall": "nuxt prepare && npm run setup:claude"
}

See .claude/skills/setup-postinstall.md for the full guide including CI setup.

Repo structure

srcdev-nuxt-i18n/
├── package.json
├── nuxt.config.ts                  ← i18n module config, 3 locales
├── tsconfig.json
├── scripts/
│   └── build-i18n.mjs              ← merge JSON → .ts, supports --watch
├── components/
│   └── locale-switcher/
│       └── LocaleSwitcher.vue      ← renders a button per locale, calls setLocale()
├── composables/
│   ├── useRawLocaleData.ts         ← useRawLocaleData<T>(path, defaultValue?)
│   └── useMarkdown.ts              ← useMarkdown() → { renderMarkdown(text) }
├── i18n-source/
│   └── locales/
│       └── global/
│           ├── en-GB.json          ← edit these to change source translations
│           ├── zh-CN.json
│           └── ar-YE.json
└── i18n/
    └── locales/
        ├── en-GB.ts                ← committed generated files (do not edit)
        ├── zh-CN.ts
        └── ar-YE.ts

Commands

npm run dev               # run nuxt dev + i18n watch concurrently
npm run build             # build:i18n then nuxt build
npm run build:i18n        # regenerate i18n/locales/*.ts from i18n-source JSON once
npm run build:i18n:watch  # same, with file watching (used automatically by dev)

Known gotchas

  • tm() renders raw AST JSON, not the string. For array/object locale values (e.g. a features list), tm(path) returns compiled Vue I18n message AST nodes, not plain values — using it directly in a v-for renders {"type":0,"start":0,...} as text. Always use useRawLocaleData<T>(path, default) instead for arrays/objects; $t() remains correct for plain strings.
  • Testing via a local file: dependency needs one extra step. npm does not install a linked local package's own dependencies automatically — run npm install inside srcdev-nuxt-i18n itself first, or a consumer's install will fail with Could not load @nuxtjs/i18n. Is it installed?. This same npm install also runs this repo's own prepare script (nuxt prepare), which is required separately: tsconfig.json extends ./.nuxt/tsconfig.json, and Vite/jiti resolve the nearest tsconfig.json when loading .ts locale files at runtime — without it, translations silently fail to load (WARN Failed to load messages for locale...). Neither of these applies to a real npm install.

Notes

  • langDir resolves relative to <rootDir>/i18n/ (not the layer root directly) — resolveI18nDir() resolves to <rootDir>/i18n first, then langDir is resolved relative to that. Since locale files live at i18n/locales/*.ts, the correct value is langDir: "locales". This applies identically to a consuming app's own i18n config (see locale-add-app-translations.md), not just this layer.
  • Generated .ts locale files are committed — consuming apps do not need to run the build script
  • RTL support (ar-YE) requires CSS in the consuming app (:dir(rtl) or [dir="rtl"] selectors) — not provided by this layer
  • Extracted from srcdev-design-system, which remains the canonical reference for original patterns and decisions