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

@ablogcms/i18n

v3.2.35

Published

Translation resource registry for the a-blog cms frontend (lets plugins extend the admin UI translations)

Readme

@ablogcms/i18n

a-blog cms フロントエンドの翻訳まわり。翻訳を引く薄いファサードと、プラグイン(拡張アプリ)が 翻訳を追加するための受け皿(i18next に依存しない小さなレジストリ)を提供する。

| サブパス | 中身 | |---|---| | @ablogcms/i18n | グローバル委譲ファサード(t / i18n / getLanguage)。window.ACMS.i18n へ委譲する | | @ablogcms/i18n/core | 受け皿の純粋実装(createI18nResourceRegistry)。グローバル非依存 | | @ablogcms/i18n/acms | Acms.i18nResources の型 augmentation(opt-in) |

翻訳を引く

import { t } from '@ablogcms/i18n';

t('deprecated.option.since', { since: '3.2' });
t('my-plugin:greeting'); // プラグインが登録した翻訳(名前空間付き)

ACMS.i18n と同じ感覚(呼べて .lng も読める)で使いたい場合は i18n を使う。

import { i18n } from '@ablogcms/i18n';

i18n('my-plugin:greeting');
i18n.lng; // 現在のロケール

実体は常にコアが保持する単一の i18next インスタンスに到達するため、プラグインのバンドルに 同梱されても「登録したインスタンスと参照するインスタンスがズレる」事故が起きない (@ablogcms/events のファサードと同じ理由)。初期化前・a-blog cms 外で呼ぶと明確な例外を投げる。

なぜ受け皿が要るのか

ACMS.i18n(i18next の t)は ablogcms/js/src/index.js の非同期ローダーの中で初期化される。 一方プラグインの <script type="module">ACMS.plugins.register() を呼んだ時点で setup(ctx) を同期実行するため、登録時点で i18next がまだ存在しないことがある。

そこで登録をいったんこのレジストリへ溜め、i18next 初期化側が subscribe() して既存分と 以後の分をまとめて取り込む。@ablogcms/eventscreateEventBus() と同じく、生成は アプリ側(index.js)が行い、プラグイン側へは注入する。

使い方

プラグイン側

直接このパッケージを触る必要はない。ctx.i18n 経由で登録する(@ablogcms/plugins)。

ACMS.plugins.register('my-plugin', {
  setup(ctx) {
    ctx.i18n.addResources('ja', { greeting: 'こんにちは' });
    ctx.i18n.addResources('en', { greeting: 'Hello' });
  },
});

// 参照(名前空間はプラグイン名に固定される)
ACMS.i18n('my-plugin:greeting');

同じ言語へ何度でも追加でき、既存とマージされる。ACMS.plugins.unregister('my-plugin') で 名前空間ごと破棄される。

取り込み側(アプリのブートストラップ)

import { createI18nResourceRegistry } from '@ablogcms/i18n';

const registry = createI18nResourceRegistry();

// i18next の初期化完了後に購読する。購読した時点で、それまでに溜まった分がまとめて配られる。
registry.subscribe(
  (namespace, lng, resources) => i18next.addResourceBundle(lng, namespace, resources, true, true),
  (namespace) => i18next.languages.forEach((lng) => i18next.removeResourceBundle(lng, namespace))
);

購読者が例外を投げても他の購読者と登録処理は止まらない(1 つのプラグインの翻訳が壊れていても コアの初期化は続ける)。