@fluenti/next 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +325 -0
- package/client.d.ts +9 -0
- package/dist/client-provider.d.ts +17 -0
- package/dist/client-provider.d.ts.map +1 -0
- package/dist/generate-server-module.d.ts +11 -0
- package/dist/generate-server-module.d.ts.map +1 -0
- package/dist/index.cjs +128 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.ts +18 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +183 -0
- package/dist/index.js.map +1 -0
- package/dist/loader.cjs +2 -0
- package/dist/loader.cjs.map +1 -0
- package/dist/loader.js +29 -0
- package/dist/loader.js.map +1 -0
- package/dist/provider.cjs +8 -0
- package/dist/provider.cjs.map +1 -0
- package/dist/provider.d.ts +3 -0
- package/dist/provider.d.ts.map +1 -0
- package/dist/provider.js +197 -0
- package/dist/provider.js.map +1 -0
- package/dist/read-config.d.ts +6 -0
- package/dist/read-config.d.ts.map +1 -0
- package/dist/scope-transform.d.ts +3 -0
- package/dist/scope-transform.d.ts.map +1 -0
- package/dist/server.cjs +2 -0
- package/dist/server.cjs.map +1 -0
- package/dist/server.d.ts +7 -0
- package/dist/server.d.ts.map +1 -0
- package/dist/server.js +14 -0
- package/dist/server.js.map +1 -0
- package/dist/trans-transform.d.ts +3 -0
- package/dist/trans-transform.d.ts.map +1 -0
- package/dist/types.d.ts +59 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/with-fluenti.d.ts +26 -0
- package/dist/with-fluenti.d.ts.map +1 -0
- package/dist/with-locale.d.ts +28 -0
- package/dist/with-locale.d.ts.map +1 -0
- package/package.json +101 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scope-transform.d.ts","sourceRoot":"","sources":["../src/scope-transform.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAA;AACvD,YAAY,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAA"}
|
package/dist/server.cjs
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});async function e(e,t,n){if(!n)throw Error(`[fluenti] withLocale requires a server module reference. Pass the generated server module as the third argument: withLocale("ja", fn, serverI18n)`);let r=(await n.getI18n()).locale;try{return n.setLocale(e),await n.getI18n(),await t()}finally{n.setLocale(r),await n.getI18n()}}exports.withLocale=e;
|
|
2
|
+
//# sourceMappingURL=server.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.cjs","names":[],"sources":["../src/with-locale.ts"],"sourcesContent":["/**\n * Per-component locale isolation for RSC.\n *\n * Temporarily switches the request-scoped locale, executes a function,\n * then restores the previous locale.\n *\n * @example\n * ```tsx\n * import { withLocale } from '@fluenti/next/server'\n *\n * export default async function Page() {\n * return (\n * <div>\n * <h1>{t`Main content`}</h1>\n * {await withLocale('ja', async () => (\n * <JapaneseWidget />\n * ))}\n * <Footer />\n * </div>\n * )\n * }\n * ```\n */\nexport async function withLocale<T>(\n locale: string,\n fn: () => T | Promise<T>,\n serverModule?: { setLocale: (l: string) => void; getI18n: () => Promise<unknown> },\n): Promise<T> {\n if (!serverModule) {\n throw new Error(\n '[fluenti] withLocale requires a server module reference. ' +\n 'Pass the generated server module as the third argument: ' +\n 'withLocale(\"ja\", fn, serverI18n)',\n )\n }\n\n // Read current locale from the module's request store\n // We need to save/restore state. Since we can't access the store directly,\n // we use setLocale to switch and rely on the caller to restore.\n const prevInstance = await serverModule.getI18n()\n const prevLocale = (prevInstance as { locale: string }).locale\n\n try {\n serverModule.setLocale(locale)\n // Force instance recreation by calling getI18n again\n await serverModule.getI18n()\n return await fn()\n } finally {\n serverModule.setLocale(prevLocale)\n await serverModule.getI18n()\n }\n}\n"],"mappings":"mEAuBA,eAAsB,EACpB,EACA,EACA,EACY,CACZ,GAAI,CAAC,EACH,MAAU,MACR,oJAGD,CAOH,IAAM,GADe,MAAM,EAAa,SAAS,EACO,OAExD,GAAI,CAIF,OAHA,EAAa,UAAU,EAAO,CAE9B,MAAM,EAAa,SAAS,CACrB,MAAM,GAAI,QACT,CACR,EAAa,UAAU,EAAW,CAClC,MAAM,EAAa,SAAS"}
|
package/dist/server.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAA"}
|
package/dist/server.js
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
//#region src/with-locale.ts
|
|
2
|
+
async function e(e, t, n) {
|
|
3
|
+
if (!n) throw Error("[fluenti] withLocale requires a server module reference. Pass the generated server module as the third argument: withLocale(\"ja\", fn, serverI18n)");
|
|
4
|
+
let r = (await n.getI18n()).locale;
|
|
5
|
+
try {
|
|
6
|
+
return n.setLocale(e), await n.getI18n(), await t();
|
|
7
|
+
} finally {
|
|
8
|
+
n.setLocale(r), await n.getI18n();
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
//#endregion
|
|
12
|
+
export { e as withLocale };
|
|
13
|
+
|
|
14
|
+
//# sourceMappingURL=server.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.js","names":[],"sources":["../src/with-locale.ts"],"sourcesContent":["/**\n * Per-component locale isolation for RSC.\n *\n * Temporarily switches the request-scoped locale, executes a function,\n * then restores the previous locale.\n *\n * @example\n * ```tsx\n * import { withLocale } from '@fluenti/next/server'\n *\n * export default async function Page() {\n * return (\n * <div>\n * <h1>{t`Main content`}</h1>\n * {await withLocale('ja', async () => (\n * <JapaneseWidget />\n * ))}\n * <Footer />\n * </div>\n * )\n * }\n * ```\n */\nexport async function withLocale<T>(\n locale: string,\n fn: () => T | Promise<T>,\n serverModule?: { setLocale: (l: string) => void; getI18n: () => Promise<unknown> },\n): Promise<T> {\n if (!serverModule) {\n throw new Error(\n '[fluenti] withLocale requires a server module reference. ' +\n 'Pass the generated server module as the third argument: ' +\n 'withLocale(\"ja\", fn, serverI18n)',\n )\n }\n\n // Read current locale from the module's request store\n // We need to save/restore state. Since we can't access the store directly,\n // we use setLocale to switch and rely on the caller to restore.\n const prevInstance = await serverModule.getI18n()\n const prevLocale = (prevInstance as { locale: string }).locale\n\n try {\n serverModule.setLocale(locale)\n // Force instance recreation by calling getI18n again\n await serverModule.getI18n()\n return await fn()\n } finally {\n serverModule.setLocale(prevLocale)\n await serverModule.getI18n()\n }\n}\n"],"mappings":";AAuBA,eAAsB,EACpB,GACA,GACA,GACY;AACZ,KAAI,CAAC,EACH,OAAU,MACR,sJAGD;CAOH,IAAM,KADe,MAAM,EAAa,SAAS,EACO;AAExD,KAAI;AAIF,SAHA,EAAa,UAAU,EAAO,EAE9B,MAAM,EAAa,SAAS,EACrB,MAAM,GAAI;WACT;AAER,EADA,EAAa,UAAU,EAAW,EAClC,MAAM,EAAa,SAAS"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"trans-transform.d.ts","sourceRoot":"","sources":["../src/trans-transform.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,wBAAwB,EAAE,MAAM,wBAAwB,CAAA;AACjE,YAAY,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAA"}
|
package/dist/types.d.ts
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { DateFormatOptions, NumberFormatOptions, Locale } from '@fluenti/core';
|
|
2
|
+
/**
|
|
3
|
+
* Configuration for `withFluenti()`.
|
|
4
|
+
*
|
|
5
|
+
* Reads defaults from `fluenti.config.ts` in the project root.
|
|
6
|
+
* All options here override the config file values.
|
|
7
|
+
*/
|
|
8
|
+
export interface WithFluentConfig {
|
|
9
|
+
/** Override `fluenti.config.ts` locales */
|
|
10
|
+
locales?: string[];
|
|
11
|
+
/** Override `fluenti.config.ts` sourceLocale (used as defaultLocale) */
|
|
12
|
+
defaultLocale?: string;
|
|
13
|
+
/** Override `fluenti.config.ts` compileOutDir */
|
|
14
|
+
compiledDir?: string;
|
|
15
|
+
/** Custom serverModule path (skip auto-generation) */
|
|
16
|
+
serverModule?: string;
|
|
17
|
+
/** Where to generate the serverModule (default: node_modules/.fluenti) */
|
|
18
|
+
serverModuleOutDir?: string;
|
|
19
|
+
/**
|
|
20
|
+
* Path to a module that default-exports an async function returning the locale string.
|
|
21
|
+
* Used in contexts where FluentProvider doesn't run (e.g. Server Actions).
|
|
22
|
+
*
|
|
23
|
+
* The module must `export default` a function `() => string | Promise<string>`.
|
|
24
|
+
*
|
|
25
|
+
* If omitted, defaults to reading the `locale` cookie.
|
|
26
|
+
*
|
|
27
|
+
* @example './lib/resolve-locale'
|
|
28
|
+
*/
|
|
29
|
+
resolveLocale?: string;
|
|
30
|
+
/** Custom date format styles */
|
|
31
|
+
dateFormats?: DateFormatOptions;
|
|
32
|
+
/** Custom number format styles */
|
|
33
|
+
numberFormats?: NumberFormatOptions;
|
|
34
|
+
/** Fallback chain per locale */
|
|
35
|
+
fallbackChain?: Record<string, Locale[]>;
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Resolved config after merging fluenti.config.ts + withFluenti() overrides.
|
|
39
|
+
*/
|
|
40
|
+
export interface ResolvedFluentConfig {
|
|
41
|
+
locales: string[];
|
|
42
|
+
defaultLocale: string;
|
|
43
|
+
compiledDir: string;
|
|
44
|
+
serverModule: string | null;
|
|
45
|
+
serverModuleOutDir: string;
|
|
46
|
+
resolveLocale?: string;
|
|
47
|
+
dateFormats?: DateFormatOptions;
|
|
48
|
+
numberFormats?: NumberFormatOptions;
|
|
49
|
+
fallbackChain?: Record<string, Locale[]>;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Props for the FluentProvider server component.
|
|
53
|
+
*/
|
|
54
|
+
export interface FluentProviderProps {
|
|
55
|
+
/** Active locale. If omitted, uses defaultLocale from config. */
|
|
56
|
+
locale?: string;
|
|
57
|
+
children: React.ReactNode;
|
|
58
|
+
}
|
|
59
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,iBAAiB,EAAE,mBAAmB,EAAE,MAAM,EAAE,MAAM,eAAe,CAAA;AAEnF;;;;;GAKG;AACH,MAAM,WAAW,gBAAgB;IAC/B,2CAA2C;IAC3C,OAAO,CAAC,EAAE,MAAM,EAAE,CAAA;IAClB,wEAAwE;IACxE,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,iDAAiD;IACjD,WAAW,CAAC,EAAE,MAAM,CAAA;IAEpB,sDAAsD;IACtD,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,0EAA0E;IAC1E,kBAAkB,CAAC,EAAE,MAAM,CAAA;IAE3B;;;;;;;;;OASG;IACH,aAAa,CAAC,EAAE,MAAM,CAAA;IAEtB,gCAAgC;IAChC,WAAW,CAAC,EAAE,iBAAiB,CAAA;IAC/B,kCAAkC;IAClC,aAAa,CAAC,EAAE,mBAAmB,CAAA;IACnC,gCAAgC;IAChC,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAA;CACzC;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,OAAO,EAAE,MAAM,EAAE,CAAA;IACjB,aAAa,EAAE,MAAM,CAAA;IACrB,WAAW,EAAE,MAAM,CAAA;IACnB,YAAY,EAAE,MAAM,GAAG,IAAI,CAAA;IAC3B,kBAAkB,EAAE,MAAM,CAAA;IAC1B,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,WAAW,CAAC,EAAE,iBAAiB,CAAA;IAC/B,aAAa,CAAC,EAAE,mBAAmB,CAAA;IACnC,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAA;CACzC;AAED;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,iEAAiE;IACjE,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;CAC1B"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { WithFluentConfig } from './types';
|
|
2
|
+
type NextConfig = Record<string, unknown>;
|
|
3
|
+
/**
|
|
4
|
+
* Wrap your Next.js config with Fluenti support.
|
|
5
|
+
*
|
|
6
|
+
* Adds a webpack loader that transforms `t\`\`` and `t()` calls,
|
|
7
|
+
* and generates a server module for RSC i18n.
|
|
8
|
+
*
|
|
9
|
+
* @example
|
|
10
|
+
* ```ts
|
|
11
|
+
* // next.config.ts — function style (recommended)
|
|
12
|
+
* import { withFluenti } from '@fluenti/next'
|
|
13
|
+
* export default withFluenti()({ reactStrictMode: true })
|
|
14
|
+
* ```
|
|
15
|
+
*
|
|
16
|
+
* @example
|
|
17
|
+
* ```ts
|
|
18
|
+
* // next.config.ts — direct style
|
|
19
|
+
* import { withFluenti } from '@fluenti/next'
|
|
20
|
+
* export default withFluenti({ reactStrictMode: true })
|
|
21
|
+
* ```
|
|
22
|
+
*/
|
|
23
|
+
export declare function withFluenti(fluentConfig?: WithFluentConfig): (nextConfig?: NextConfig) => NextConfig;
|
|
24
|
+
export declare function withFluenti(nextConfig: NextConfig): NextConfig;
|
|
25
|
+
export {};
|
|
26
|
+
//# sourceMappingURL=with-fluenti.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"with-fluenti.d.ts","sourceRoot":"","sources":["../src/with-fluenti.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAA;AAI/C,KAAK,UAAU,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;AAEzC;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAgB,WAAW,CAAC,YAAY,CAAC,EAAE,gBAAgB,GAAG,CAAC,UAAU,CAAC,EAAE,UAAU,KAAK,UAAU,CAAA;AACrG,wBAAgB,WAAW,CAAC,UAAU,EAAE,UAAU,GAAG,UAAU,CAAA"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Per-component locale isolation for RSC.
|
|
3
|
+
*
|
|
4
|
+
* Temporarily switches the request-scoped locale, executes a function,
|
|
5
|
+
* then restores the previous locale.
|
|
6
|
+
*
|
|
7
|
+
* @example
|
|
8
|
+
* ```tsx
|
|
9
|
+
* import { withLocale } from '@fluenti/next/server'
|
|
10
|
+
*
|
|
11
|
+
* export default async function Page() {
|
|
12
|
+
* return (
|
|
13
|
+
* <div>
|
|
14
|
+
* <h1>{t`Main content`}</h1>
|
|
15
|
+
* {await withLocale('ja', async () => (
|
|
16
|
+
* <JapaneseWidget />
|
|
17
|
+
* ))}
|
|
18
|
+
* <Footer />
|
|
19
|
+
* </div>
|
|
20
|
+
* )
|
|
21
|
+
* }
|
|
22
|
+
* ```
|
|
23
|
+
*/
|
|
24
|
+
export declare function withLocale<T>(locale: string, fn: () => T | Promise<T>, serverModule?: {
|
|
25
|
+
setLocale: (l: string) => void;
|
|
26
|
+
getI18n: () => Promise<unknown>;
|
|
27
|
+
}): Promise<T>;
|
|
28
|
+
//# sourceMappingURL=with-locale.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"with-locale.d.ts","sourceRoot":"","sources":["../src/with-locale.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAsB,UAAU,CAAC,CAAC,EAChC,MAAM,EAAE,MAAM,EACd,EAAE,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,EACxB,YAAY,CAAC,EAAE;IAAE,SAAS,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;IAAC,OAAO,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAA;CAAE,GACjF,OAAO,CAAC,CAAC,CAAC,CAwBZ"}
|
package/package.json
ADDED
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@fluenti/next",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"description": "Next.js plugin for Fluenti — withFluenti, FluentProvider, t`` transforms for App Router and Pages Router",
|
|
6
|
+
"homepage": "https://fluenti.dev",
|
|
7
|
+
"repository": {
|
|
8
|
+
"type": "git",
|
|
9
|
+
"url": "git+https://github.com/usefluenti/fluenti.git",
|
|
10
|
+
"directory": "packages/next-plugin"
|
|
11
|
+
},
|
|
12
|
+
"bugs": {
|
|
13
|
+
"url": "https://github.com/usefluenti/fluenti/issues"
|
|
14
|
+
},
|
|
15
|
+
"license": "MIT",
|
|
16
|
+
"publishConfig": {
|
|
17
|
+
"access": "public"
|
|
18
|
+
},
|
|
19
|
+
"keywords": [
|
|
20
|
+
"i18n",
|
|
21
|
+
"internationalization",
|
|
22
|
+
"compile-time",
|
|
23
|
+
"icu",
|
|
24
|
+
"messageformat",
|
|
25
|
+
"next",
|
|
26
|
+
"nextjs",
|
|
27
|
+
"rsc",
|
|
28
|
+
"server-components"
|
|
29
|
+
],
|
|
30
|
+
"main": "./dist/index.cjs",
|
|
31
|
+
"module": "./dist/index.js",
|
|
32
|
+
"types": "./dist/index.d.ts",
|
|
33
|
+
"exports": {
|
|
34
|
+
".": {
|
|
35
|
+
"import": {
|
|
36
|
+
"types": "./dist/index.d.ts",
|
|
37
|
+
"default": "./dist/index.js"
|
|
38
|
+
},
|
|
39
|
+
"require": {
|
|
40
|
+
"types": "./dist/index.d.ts",
|
|
41
|
+
"default": "./dist/index.cjs"
|
|
42
|
+
}
|
|
43
|
+
},
|
|
44
|
+
"./server": {
|
|
45
|
+
"import": {
|
|
46
|
+
"types": "./dist/server.d.ts",
|
|
47
|
+
"default": "./dist/server.js"
|
|
48
|
+
},
|
|
49
|
+
"require": {
|
|
50
|
+
"types": "./dist/server.d.ts",
|
|
51
|
+
"default": "./dist/server.cjs"
|
|
52
|
+
}
|
|
53
|
+
},
|
|
54
|
+
"./provider": {
|
|
55
|
+
"import": {
|
|
56
|
+
"types": "./dist/provider.d.ts",
|
|
57
|
+
"default": "./dist/provider.js"
|
|
58
|
+
},
|
|
59
|
+
"require": {
|
|
60
|
+
"types": "./dist/provider.d.ts",
|
|
61
|
+
"default": "./dist/provider.cjs"
|
|
62
|
+
}
|
|
63
|
+
},
|
|
64
|
+
"./client": {
|
|
65
|
+
"types": "./client.d.ts"
|
|
66
|
+
}
|
|
67
|
+
},
|
|
68
|
+
"files": [
|
|
69
|
+
"dist",
|
|
70
|
+
"client.d.ts"
|
|
71
|
+
],
|
|
72
|
+
"peerDependencies": {
|
|
73
|
+
"next": ">=14.0.0",
|
|
74
|
+
"react": ">=18.0.0"
|
|
75
|
+
},
|
|
76
|
+
"dependencies": {
|
|
77
|
+
"jiti": "^2",
|
|
78
|
+
"@fluenti/react": "0.1.0",
|
|
79
|
+
"@fluenti/core": "0.1.0"
|
|
80
|
+
},
|
|
81
|
+
"devDependencies": {
|
|
82
|
+
"@types/node": "^22",
|
|
83
|
+
"@types/react": "^19.0.0",
|
|
84
|
+
"@types/react-dom": "^19.0.0",
|
|
85
|
+
"@vitest/coverage-v8": "^4",
|
|
86
|
+
"next": "^15",
|
|
87
|
+
"react": "^19.0.0",
|
|
88
|
+
"react-dom": "^19.0.0",
|
|
89
|
+
"typescript": "^5.9",
|
|
90
|
+
"vite": "^8",
|
|
91
|
+
"vite-plugin-dts": "^4",
|
|
92
|
+
"vitest": "^4",
|
|
93
|
+
"webpack": "^5"
|
|
94
|
+
},
|
|
95
|
+
"scripts": {
|
|
96
|
+
"build": "vite build",
|
|
97
|
+
"dev": "vite build --watch",
|
|
98
|
+
"test": "vitest run",
|
|
99
|
+
"typecheck": "tsc --noEmit"
|
|
100
|
+
}
|
|
101
|
+
}
|