@korioinc/next-core 2.0.16 → 2.0.18
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/dist/i18n/routing.d.ts +8 -4
- package/dist/i18n/routing.d.ts.map +1 -1
- package/dist/i18n/routing.js +80 -38
- package/package.json +4 -4
package/dist/i18n/routing.d.ts
CHANGED
|
@@ -18,8 +18,12 @@ export declare function getPathname({ locale, href }: {
|
|
|
18
18
|
}): string;
|
|
19
19
|
export declare function getLanguageAlternates(pathname?: string): Record<string, string>;
|
|
20
20
|
export declare function getCurrentPathname(): Promise<string>;
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
21
|
+
export declare function getCurrentSearchParams(): Promise<URLSearchParams>;
|
|
22
|
+
export declare function getDefaultPathname(): Promise<string>;
|
|
23
|
+
export declare function getCurrentLanguageAlternates(): Promise<Record<string, string>>;
|
|
24
|
+
type FullUrlParams = Record<string, string | string[] | undefined> | URLSearchParams | ReadonlyURLSearchParams | undefined;
|
|
25
|
+
export declare function getFullUrlByPathname(pathname: string, params?: FullUrlParams): string;
|
|
26
|
+
export declare function getFullUrl(params?: FullUrlParams): Promise<string>;
|
|
27
|
+
export declare function getFullUrlWithCurrentParams(): Promise<string>;
|
|
28
|
+
export {};
|
|
25
29
|
//# sourceMappingURL=routing.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"routing.d.ts","sourceRoot":"","sources":["../../src/i18n/routing.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,iBAAiB,CAAC;AAC/D,OAAO,EAAE,KAAK,WAAW,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;
|
|
1
|
+
{"version":3,"file":"routing.d.ts","sourceRoot":"","sources":["../../src/i18n/routing.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,iBAAiB,CAAC;AAC/D,OAAO,EAAE,KAAK,WAAW,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAsC7D;;GAEG;AACH,wBAAgB,UAAU,IAAI,MAAM,EAAE,CAErC;AAED;;GAEG;AACH,wBAAgB,gBAAgB,IAAI,MAAM,CAEzC;AAyDD,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,WAAW,yBAyEvD;AAED,wBAAgB,gBAAgB,CAAC,cAAc,EAAE,OAAO,GAAG,MAAM,CAShE;AAED,wBAAgB,eAAe,CAAC,cAAc,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAkB9F;AAED,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,MAAM,CAoBvG;AAED,wBAAgB,WAAW,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,UAY7E;AAsBD,wBAAgB,qBAAqB,CAAC,QAAQ,GAAE,MAAY,0BAwB3D;AAED,wBAAsB,kBAAkB,IAAI,OAAO,CAAC,MAAM,CAAC,CAK1D;AAED,wBAAsB,sBAAsB,IAAI,OAAO,CAAC,eAAe,CAAC,CAMvE;AAED,wBAAsB,kBAAkB,IAAI,OAAO,CAAC,MAAM,CAAC,CAU1D;AAED,wBAAsB,4BAA4B,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAIpF;AAED,KAAK,aAAa,GACd,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,GAAG,SAAS,CAAC,GAC7C,eAAe,GACf,uBAAuB,GACvB,SAAS,CAAC;AAiDd,wBAAgB,oBAAoB,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,aAAa,GAAG,MAAM,CAErF;AAED,wBAAsB,UAAU,CAAC,MAAM,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,MAAM,CAAC,CAIxE;AAED,wBAAsB,2BAA2B,IAAI,OAAO,CAAC,MAAM,CAAC,CAKnE"}
|
package/dist/i18n/routing.js
CHANGED
|
@@ -18,6 +18,13 @@ const DEFAULT_FALLBACK = () => {
|
|
|
18
18
|
};
|
|
19
19
|
const LOCALE_COOKIE_NAME = 'NEXT_LOCALE';
|
|
20
20
|
const LOCALE_PREFIX = 'as-needed';
|
|
21
|
+
const PATHNAME_HEADER_NAME = 'x-pathname';
|
|
22
|
+
const SEARCH_PARAMS_HEADER_NAME = 'x-search-params';
|
|
23
|
+
const setRoutingHeaders = (response, pathname, search) => {
|
|
24
|
+
response.headers.set(PATHNAME_HEADER_NAME, pathname);
|
|
25
|
+
response.headers.set(SEARCH_PARAMS_HEADER_NAME, search.replace(/^\?/, ''));
|
|
26
|
+
return response;
|
|
27
|
+
};
|
|
21
28
|
/**
|
|
22
29
|
* Get all available locales
|
|
23
30
|
*/
|
|
@@ -54,8 +61,7 @@ const redirectWithoutLocale = (request, pathname, locale, shouldSetCookie = fals
|
|
|
54
61
|
const url = new URL(newPathname, request.url);
|
|
55
62
|
url.search = request.nextUrl.search;
|
|
56
63
|
url.hash = request.nextUrl.hash;
|
|
57
|
-
const response = NextResponse.redirect(url, 302);
|
|
58
|
-
response.headers.set('x-pathname', newPathname);
|
|
64
|
+
const response = setRoutingHeaders(NextResponse.redirect(url, 302), newPathname, request.nextUrl.search);
|
|
59
65
|
if (shouldSetCookie) {
|
|
60
66
|
setCookie(response, locale);
|
|
61
67
|
}
|
|
@@ -68,8 +74,7 @@ const rewriteWithLocale = (request, pathname, locale) => {
|
|
|
68
74
|
const internalUrl = new URL(`/${locale}${pathname}`, request.url);
|
|
69
75
|
internalUrl.search = request.nextUrl.search;
|
|
70
76
|
internalUrl.hash = request.nextUrl.hash;
|
|
71
|
-
const response = NextResponse.rewrite(internalUrl);
|
|
72
|
-
response.headers.set('x-pathname', pathname);
|
|
77
|
+
const response = setRoutingHeaders(NextResponse.rewrite(internalUrl), pathname, request.nextUrl.search);
|
|
73
78
|
return response;
|
|
74
79
|
};
|
|
75
80
|
export function handleLocaleRouting(request) {
|
|
@@ -89,8 +94,7 @@ export function handleLocaleRouting(request) {
|
|
|
89
94
|
// 2. URL에 locale이 포함된 경우
|
|
90
95
|
if (pathnameHasLocale) {
|
|
91
96
|
// 이미 path에 locale이 있을 때
|
|
92
|
-
const response = NextResponse.next();
|
|
93
|
-
response.headers.set('x-pathname', pathname);
|
|
97
|
+
const response = setRoutingHeaders(NextResponse.next(), pathname, request.nextUrl.search);
|
|
94
98
|
// 쿠키 값이 path locale과 다를 경우
|
|
95
99
|
if (localeCookie?.value !== pathLocale) {
|
|
96
100
|
// 기본 locale인 경우 URL에서 제거
|
|
@@ -125,8 +129,7 @@ export function handleLocaleRouting(request) {
|
|
|
125
129
|
// 다른 locale은 URL에 표시
|
|
126
130
|
const newPathname = getChangeLocalePath(pathname, defaultFallback, locale);
|
|
127
131
|
request.nextUrl.pathname = newPathname;
|
|
128
|
-
const response = NextResponse.redirect(request.nextUrl);
|
|
129
|
-
response.headers.set('x-pathname', newPathname);
|
|
132
|
+
const response = setRoutingHeaders(NextResponse.redirect(request.nextUrl), newPathname, request.nextUrl.search);
|
|
130
133
|
// 쿠키가 없는 경우 설정
|
|
131
134
|
if (localeCookie?.value === undefined) {
|
|
132
135
|
setCookie(response, locale);
|
|
@@ -189,18 +192,24 @@ export function getPathname({ locale, href }) {
|
|
|
189
192
|
}
|
|
190
193
|
return href.startsWith('/') ? `/${locale}${href}` : `/${locale}/${href}`;
|
|
191
194
|
}
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
// Remove any existing locale from the pathname to get the base path
|
|
195
|
-
let basePath = pathname;
|
|
195
|
+
const getBasePathWithoutLocale = (pathname = '/') => {
|
|
196
|
+
let basePath = pathname || '/';
|
|
196
197
|
locales.forEach((locale) => {
|
|
197
198
|
const localePattern = new RegExp(`^/${locale}(/|$)`);
|
|
198
199
|
if (localePattern.test(basePath)) {
|
|
199
200
|
basePath = basePath.replace(localePattern, '/');
|
|
200
201
|
}
|
|
201
202
|
});
|
|
202
|
-
// Normalize path
|
|
203
|
+
// Normalize path and ensure root fallback
|
|
203
204
|
basePath = basePath.replace(/\/+/g, '/');
|
|
205
|
+
if (!basePath.startsWith('/')) {
|
|
206
|
+
basePath = `/${basePath}`;
|
|
207
|
+
}
|
|
208
|
+
return basePath || '/';
|
|
209
|
+
};
|
|
210
|
+
export function getLanguageAlternates(pathname = '/') {
|
|
211
|
+
const defaultFallback = DEFAULT_FALLBACK();
|
|
212
|
+
const basePath = getBasePathWithoutLocale(pathname);
|
|
204
213
|
const alternates = {};
|
|
205
214
|
// Set x-default based on LOCALE_PREFIX and defaultFallback
|
|
206
215
|
if (LOCALE_PREFIX === 'as-needed') {
|
|
@@ -224,40 +233,73 @@ export function getLanguageAlternates(pathname = '/') {
|
|
|
224
233
|
export async function getCurrentPathname() {
|
|
225
234
|
const { headers } = await import('next/headers');
|
|
226
235
|
const headersList = await headers();
|
|
227
|
-
return headersList.get(
|
|
236
|
+
return headersList.get(PATHNAME_HEADER_NAME) || '';
|
|
228
237
|
}
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
238
|
+
export async function getCurrentSearchParams() {
|
|
239
|
+
const { headers } = await import('next/headers');
|
|
240
|
+
const headersList = await headers();
|
|
241
|
+
const rawSearchParams = headersList.get(SEARCH_PARAMS_HEADER_NAME) || '';
|
|
242
|
+
return new URLSearchParams(rawSearchParams);
|
|
243
|
+
}
|
|
244
|
+
export async function getDefaultPathname() {
|
|
245
|
+
const pathname = await getCurrentPathname();
|
|
246
|
+
const basePath = getBasePathWithoutLocale(pathname);
|
|
247
|
+
const defaultFallback = DEFAULT_FALLBACK();
|
|
248
|
+
if (LOCALE_PREFIX === 'as-needed') {
|
|
249
|
+
return basePath;
|
|
236
250
|
}
|
|
251
|
+
return `/${defaultFallback}${basePath === '/' ? '' : basePath}`;
|
|
252
|
+
}
|
|
253
|
+
export async function getCurrentLanguageAlternates() {
|
|
254
|
+
const pathname = await getCurrentPathname();
|
|
255
|
+
return getLanguageAlternates(pathname);
|
|
256
|
+
}
|
|
257
|
+
const isSearchParamsLike = (params) => {
|
|
258
|
+
return typeof params.get === 'function' && typeof params.forEach === 'function';
|
|
259
|
+
};
|
|
260
|
+
const toSearchParams = (params) => {
|
|
237
261
|
const searchParams = new URLSearchParams();
|
|
238
|
-
|
|
239
|
-
|
|
262
|
+
if (!params) {
|
|
263
|
+
return searchParams;
|
|
264
|
+
}
|
|
265
|
+
if (isSearchParamsLike(params)) {
|
|
240
266
|
params.forEach((value, key) => {
|
|
241
|
-
// locale 파라미터는 제외
|
|
242
267
|
if (key !== 'locale') {
|
|
243
268
|
searchParams.append(key, value);
|
|
244
269
|
}
|
|
245
270
|
});
|
|
271
|
+
return searchParams;
|
|
246
272
|
}
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
273
|
+
Object.entries(params).forEach(([key, value]) => {
|
|
274
|
+
if (value === undefined)
|
|
275
|
+
return;
|
|
276
|
+
if (Array.isArray(value)) {
|
|
277
|
+
value.forEach((v) => searchParams.append(key, v));
|
|
278
|
+
}
|
|
279
|
+
else {
|
|
280
|
+
searchParams.append(key, value);
|
|
281
|
+
}
|
|
282
|
+
});
|
|
283
|
+
return searchParams;
|
|
284
|
+
};
|
|
285
|
+
/**
|
|
286
|
+
* pathname과 params를 조합하여 전체 URL을 생성하는 함수
|
|
287
|
+
*/
|
|
288
|
+
const buildFullUrl = (pathname, params) => {
|
|
289
|
+
const baseUrl = process.env.NEXT_PUBLIC_APP_URL || '';
|
|
290
|
+
const searchParams = toSearchParams(params);
|
|
261
291
|
const queryString = searchParams.toString();
|
|
262
292
|
return `${baseUrl}${pathname}${queryString ? `?${queryString}` : ''}`;
|
|
293
|
+
};
|
|
294
|
+
export function getFullUrlByPathname(pathname, params) {
|
|
295
|
+
return buildFullUrl(pathname, params);
|
|
296
|
+
}
|
|
297
|
+
export async function getFullUrl(params) {
|
|
298
|
+
const pathname = await getCurrentPathname();
|
|
299
|
+
return buildFullUrl(pathname, params);
|
|
300
|
+
}
|
|
301
|
+
export async function getFullUrlWithCurrentParams() {
|
|
302
|
+
const pathname = await getCurrentPathname();
|
|
303
|
+
const currentParams = await getCurrentSearchParams();
|
|
304
|
+
return buildFullUrl(pathname, currentParams);
|
|
263
305
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@korioinc/next-core",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.18",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"exports": {
|
|
6
6
|
"./ads": {
|
|
@@ -79,11 +79,11 @@
|
|
|
79
79
|
"tsc-alias": "^1.8.16",
|
|
80
80
|
"tw-animate-css": "^1.4.0",
|
|
81
81
|
"typescript": "^5.9.3",
|
|
82
|
-
"@korioinc/next-configs": "2.0.
|
|
82
|
+
"@korioinc/next-configs": "2.0.18"
|
|
83
83
|
},
|
|
84
84
|
"dependencies": {
|
|
85
85
|
"@floating-ui/react": "^0.27.17",
|
|
86
|
-
"@formatjs/intl-localematcher": "^0.
|
|
86
|
+
"@formatjs/intl-localematcher": "^0.8.1",
|
|
87
87
|
"clsx": "^2.1.1",
|
|
88
88
|
"cookies-next": "^6.1.1",
|
|
89
89
|
"cosmiconfig": "^9.0.0",
|
|
@@ -94,7 +94,7 @@
|
|
|
94
94
|
"schema-dts": "^1.1.5",
|
|
95
95
|
"tailwind-merge": "^3.4.0",
|
|
96
96
|
"valtio": "^2.3.0",
|
|
97
|
-
"@korioinc/next-conf": "2.0.
|
|
97
|
+
"@korioinc/next-conf": "2.0.18"
|
|
98
98
|
},
|
|
99
99
|
"publishConfig": {
|
|
100
100
|
"access": "public",
|