Skip to content

Commit 0d3ab6d

Browse files
committed
feat: 자주 사용되는 utils 및 components 추가
1 parent fdb7f1d commit 0d3ab6d

File tree

3 files changed

+71
-0
lines changed

3 files changed

+71
-0
lines changed
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import React from 'react';
2+
import * as runtime from "react/jsx-runtime";
3+
4+
import { evaluate } from "@mdx-js/mdx";
5+
import { MDXProvider } from "@mdx-js/react";
6+
import { CircularProgress, Typography } from '@mui/material';
7+
import { wrap } from '@suspensive/react';
8+
import { useSuspenseQuery } from "@tanstack/react-query";
9+
10+
const useMDX = (text: string) => useSuspenseQuery({
11+
queryKey: ['mdx', text],
12+
queryFn: async () => {
13+
const { default: RenderResult } = await evaluate(text, { ...runtime, baseUrl: import.meta.url });
14+
return <MDXProvider><RenderResult /></MDXProvider>
15+
}
16+
})
17+
18+
export const MDXRenderer: React.FC<{ text: string }> = wrap
19+
.ErrorBoundary({
20+
fallback: ({ error }) => {
21+
console.error('MDX 변환 오류:', error);
22+
return <Typography variant="body2" color="error">MDX 변환 오류: {error.message}</Typography>
23+
}
24+
})
25+
.Suspense({ fallback: <CircularProgress /> })
26+
.on(({ text }) => useMDX(text).data);
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
import React from 'react';
2+
3+
export const PriceDisplay: React.FC<{ price: number, label?: string }> = ({ price, label }) => {
4+
return <>{(label ? `${label} : ` : '') + price.toLocaleString()}</>
5+
};
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
import * as R from 'remeda'
2+
3+
export type PossibleFormInputType = HTMLFormElement | undefined | null
4+
export type FormResultObject = { [k: string]: FormDataEntryValue | boolean | null }
5+
6+
export const isFormValid = (form: HTMLFormElement | null | undefined): form is HTMLFormElement => {
7+
if (!(R.isObjectType(form) && form instanceof HTMLFormElement)) return false
8+
9+
if (!form.checkValidity()) {
10+
form.reportValidity()
11+
return false
12+
}
13+
14+
return true
15+
}
16+
17+
export function getFormValue<T>(_: { form: HTMLFormElement; fieldToExcludeWhenFalse?: string[]; fieldToNullWhenFalse?: string[] }): T {
18+
const formData: {
19+
[k: string]: FormDataEntryValue | boolean | null
20+
} = Object.fromEntries(new FormData(_.form))
21+
Object.keys(formData)
22+
.filter((key) => (_.fieldToExcludeWhenFalse ?? []).includes(key) || (_.fieldToNullWhenFalse ?? []).includes(key))
23+
.filter((key) => R.isEmpty(formData[key] as string))
24+
.forEach((key) => {
25+
if ((_.fieldToExcludeWhenFalse ?? []).includes(key)) {
26+
delete formData[key]
27+
} else if ((_.fieldToNullWhenFalse ?? []).includes(key)) {
28+
formData[key] = null
29+
}
30+
})
31+
Array.from(_.form.children).forEach((child) => {
32+
const targetElement: Element | null = child
33+
if (targetElement && !(targetElement instanceof HTMLInputElement)) {
34+
const targetElements = targetElement.querySelectorAll('input')
35+
for (const target of targetElements)
36+
if (target instanceof HTMLInputElement && target.type === 'checkbox') formData[target.name] = target.checked ? true : false
37+
}
38+
})
39+
return formData as T
40+
}

0 commit comments

Comments
 (0)