묻고 답해요
169만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
해결됨[풀스택 완성] Supabase로 웹사이트 3개 클론하기 (Next.js 14)
무한 스크롤 시 화면 위치 문제
무한 스크롤 구현 중에, 스크롤을 내리면 자연스럽게 다음 페이지로 이어지는 게 아니라, 한번 아래로 내려갔다가 다시 스크롤했던 위치로 돌아옵니다. 이 문제는 어떻게 해결할 수 있을까요?
-
미해결Next + React Query로 SNS 서비스 만들기
searchParams 질문있습니다.
const onClickHot = () => { setCurrent('hot'); router.replace(`/search?q=${searchParams.get('q')}`) } 이 코드가 있으면 q=null일때 주소가 http://localhost:3000/search?q=null이렇게 이동되는데 제로초님은 아무런 검색어가 없는데 어떻게 null로 안나오죠?null체크를해서 주소를 2개 분기해도 될거같긴한데 제로초님은 q가 null일땐 주소창의 쿼리가 안생기더라고요 . 뭐가다른건지 모르겠네요ㅠ
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
RN Drawer 설치시 오류,,
❗질문 작성시 꼭 참고해주세요최대한 상세히 현재 문제(또는 에러)와 코드(또는 github)를 첨부해주셔야 그만큼 자세히 답변드릴 수 있습니다.맥/윈도우, 안드로이드/iOS, ReactNative, Node 버전 등의 개발환경도 함께 적어주시면 도움이 됩니다. 에러메세지는 일부분이 아닌 전체 상황을 올려주세요. (일부만 자르거나 일부만 복사해서 올려주시면 답변이 어렵습니다.) [2-5]RN Drawer 관련 강의를 들으며, 따라한 이후,,, 빌드도 오류가 나고,,, 하기의 에러 메세지가 나와서, 이후 진도를 따라갈 수가 없습니다...😂😂강사님 강의를 들으며,, 이전에 동일한 오류로 질문을 올려주신 분들의 레퍼런스도 다 해보고,, 구글링한 결과로도 해봤는데,,, 어느 부분이 문제인지,,, 3일째,,, 진도를 못나가고 있습니다...ㅠ어떤 부분을 수정해야 할 지,,, 도움을 주시면,,,, 감사하겠습니다...!github: https://github.com/SooyeonBack/ReactNative.git개발환경윈도우안드로이드ReactNative 버전: 0.72.6 에러메세지> Task :react-native-reanimated:compileDebugJavaWithJavac FAILED Deprecated Gradle features were used in this build, making it incompatible with Gradle 9.0. You can use '--warning-mode all' to show the individual deprecation warnings and determine if they come from your own scripts or plugins. See https://docs.gradle.org/8.0.1/userguide/command_line_interface.html#sec:command_line_warnings 80 actionable tasks: 69 executed, 11 up-to-date info 💡 Tip: Make sure that you have set up your development environment correctly, by running react-native doctor. To read more about doctor command visit: https://github.com/react-native-community/cli/blob/main/packages/cli-doctor/README.md#doctor Warning: SDK processing. This version only understands SDK XML versions up to 3 but an SDK XML file of version 4 was encountered. This can happen if you use versions of Android Studio and the command-line tools that were released at different times. ``` 37 errors FAILURE: Build failed with an exception. * What went wrong: Execution failed for task ':react-native-reanimated:compileDebugJavaWithJavac'. > Compilation failed; see the compiler error output for details. * Try: > Run with --stacktrace option to get the stack trace. > Run with --info or --debug option to get more log output. > Run with --scan to get full insights. * Get more help at https://help.gradle.org BUILD FAILED in 13s info Run CLI with --verbose flag for more details.
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
회원 탈퇴 후, 로그아웃 미실행
안녕하세요 강사님회원탈퇴는 정상적으로 처리되서 팝업까지는 올라오는데로그아웃이 실행되지 않습니다.. 😭 https://github.com/KMSKang/react
-
미해결Next + React Query로 SNS 서비스 만들기
error.js 와 loading.js 에 대한 질문이 있습니다.
Next에서 자체적으로 제공하는 에러 바운더리인 error.js 와 서스펜스인 loading.js는 '서버 컴포넌트'의 에러와 로딩만 처리하는 것인가요? 예를 들어 서버 컴포넌트인 page.tsx의 하위 클라이언트 컴포넌트에서 에러가 발생했을 때는 error.js에서 캐치가 안 되는 것인가요...?
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
프로필 사진을 변경 후 뒤로가기 시, 서버 이미지 이슈
안녕하세요 강사님앱을 종료했다가 접속하면 정상적으로 보입니다.그런데 이미지, 닉네임을 설정하고 뒤로가기하면 아래와 같이 오류가 발생합니다..😭그런데 또 왔다갔다 하다보면 다시 또 프로필이 보입니다..🥲https://github.com/KMSKang/react.git
-
해결됨Next + React Query로 SNS 서비스 만들기
route handlers 에 대한 질문이 있습니다
안녕하세요, app router에 대해 계속 공부하다가 route handlers 에 대한 궁금증이 해결되지 않아 질문하게 됐습니다. Next app router에서 정확히 route handlers를 사용해야 하는 이유가 무엇인가요?제가 생각했을 땐 서버 데이터 캐싱이나 API 엔드포인트를 숨길 수 있다는 장점이 있는데 이건 서버 컴포넌트에서 fetch하는 것으로도 대체가 되는데 route handlers를 사용해야 하는 특별한 이유가 따로 있는 것인가요? 모든 API를 route handlers로 하면 Next서버에 부하가 걸릴텐데 어떻게 해결할 수 있을까요? 이 부분은 공식문서에서 제가 못 찾은 것 같은데, 만약 외부 백엔드 API가 있고 여기에 데이터 요청을 할 때클라이언트 컴포넌트에서의 모든 API 요청을 1차로 route handler에 하고 여기서 외부 백엔드 API로 요청하게되면 route handlers에 요청이 몰리게 되는데 이때 Next 서버에 걸리는 부하를 어떻게 해소할 수 있을까요?
-
미해결Next + React Query로 SNS 서비스 만들기
hydration 에러
제로초님 하신대로 그대로 프로젝트를 생성하고 실행했더니 화면은 그대로 뜨는데 에러가 1개 있어서 봤더니 hydration 에러라고 뜨네요 ㅠㅠ 지금 z-com 프로젝트를 수업용 / 연습용으로 총 2개 진행중인데 수업용 프로젝트는 이런 에러가 없었는데 연습용에서 에러가 발생하네요. 아래는 에러 코드입니다 ! Console ErrorHydration failed because the server rendered HTML didn't match the client. As a result this tree will be regenerated on the client. This can happen if a SSR-ed Client Component used- A server/client branch if (typeof window !== 'undefined'). - Variable input such as Date.now() or Math.random() which changes each time it's called. - Date formatting in a user's locale which doesn't match the server. - External changing data without sending a snapshot of it along with the HTML. - Invalid HTML tag nesting. It can also happen if the client has a browser extension installed which messes with the HTML before React loaded
-
해결됨Next + React Query로 SNS 서비스 만들기
배포 환경에서 request.nextUrl.origin 질문
안녕하세요 nextjs를 활용해서 프로젝트를 진행하는 중에 해결되지 않는 문제가 발생하여 질문 드립니다.현재 도커를 활용해서 nextjs를 배포하고 있는데middleware에서 request.nextUrl.origin값이 https://localhost:3000이 들어가고 있습니다.x-forwarded-host를 찍었을때는 제가 사용하는 https://test.domain.com이 들어가는데 request.nextUrl.origin에 x-forwared-host와 같은 값이 들어가도록 설정하기 위한 방법이 있는지 알 수 있을까요??
-
미해결
리액트 리렌더링 안되게 하는법
문제가 발생한 코드 로직에 대해 설명드리자면 유저가 어떤 상태 선택창을 띄우고 상태를 변경하면 서버로 요청을 보내고 응답이 와서 변경된 데이터로 새로 렌더링 되는 로직입니다. 그런데 여기서 저는 상태 선택창을 닫히지 않게 하고 싶습니다. 그런데 useState를 사용하면 리렌더링 됐을 때 당연히 상태가 초기화 돼서 선택창이 사라질 것이기 때문에 useRef를 사용했습니다.아래가 그 코드인데 useRef로 했음에도 리렌더링 되고 초기 상태인 false로 바뀌어버립니다. 그래서 상태창을 유지하지 못하고 있습니다. 해결법 좀 아시는 고수님들 도움 좀 주셨으면 좋겠습니다 ㅠconst maintainStatus = useRef(false); const changeStatus = (status: LocationStatusType) => { mutate({ locationStatus: status }, { onSuccess: async (res) => { // 성공시 await queryClient.invalidateQueries({ queryKey: homelessListQueryKey }); // 쿼리 최신화 maintainStatus.current = true; console.log("maintainStatus.current:", maintainStatus.current) //true 출력 } }) } useEffect(() => { console.log("Updated maintainStatus.current:", maintainStatus.current); // false 출력 }, [maintainStatus.current]);
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
pgAdmin 관련 질문입니다
윈도우를 사용하고 있습니다 선생님강의를 듣던 와중에 똑같이 따라서 설정 했는데런타임 오류가 발생해서 여쭤봅니다
-
미해결맛집 지도앱 만들기 (React Native & NestJS)
[해결]MapView 렌더링 이슈 , 뒤로가기시 마커 제거 안되는 이슈
{ "name": "matzip", "version": "0.0.1", "private": true, "scripts": { "android": "react-native run-android ", "ios": "react-native -run-ios --simulator 'iPhone 16 Pro'", "lint": "eslint .", "start": "react-native start --reset-cache", "test": "jest" }, "dependencies": { "@react-native-community/geolocation": "^3.4.0", "@react-native-community/slider": "^4.5.5", "@react-native-masked-view/masked-view": "^0.3.1", "@react-navigation/drawer": "^6.7.2", "@react-navigation/native": "^6.1.18", "@react-navigation/stack": "^6.4.1", "@tanstack/react-query": "^5.59.16", "axios": "^1.7.7", "react": "18.3.1", "react-native": "0.76.0", "react-native-date-picker": "^5.0.7", "react-native-encrypted-storage": "^4.0.3", "react-native-gesture-handler": "^2.20.1", "react-native-maps": "^1.18.2", "react-native-permissions": "^5.0.2", "react-native-reanimated": "^3.16.1", "react-native-safe-area-context": "^4.11.1", "react-native-screens": "^3.34.0", "react-native-vector-icons": "^10.2.0" }, "devDependencies": { "@babel/core": "^7.25.2", "@babel/plugin-transform-private-methods": "^7.25.9", "@babel/preset-env": "^7.25.3", "@babel/runtime": "^7.25.0", "@react-native-community/cli": "15.0.0-alpha.2", "@react-native-community/cli-platform-android": "15.0.0-alpha.2", "@react-native-community/cli-platform-ios": "15.0.0-alpha.2", "@react-native/babel-preset": "0.76.0", "@react-native/eslint-config": "0.76.0", "@react-native/metro-config": "0.76.0", "@react-native/typescript-config": "0.76.0", "@types/react": "^18.2.6", "@types/react-native-vector-icons": "^6.4.18", "@types/react-test-renderer": "^18.0.0", "babel-jest": "^29.6.3", "babel-plugin-module-resolver": "^5.0.2", "eslint": "^8.19.0", "jest": "^29.6.3", "prettier": "2.8.8", "react-test-renderer": "18.3.1", "typescript": "5.0.4" }, "engines": { "node": ">=18" }, "packageManager": "yarn@3.6.4" }const {data: markers = [], isPending, error} = useGetMarkers(); function MapHomeScreen() { // const {data: markers = []} = useGetMarkers();기존코드 const {data: markers = [], isPending, error} = useGetMarkers(); //바뀐코드 //추가한코드 if (isPending) return <Text>Loading...</Text>; if (error) return <Text>{error.message}</Text>; //추가한코드 return ( <> <MapView ... //기존코드 {selectLocation && ( <Callout> <Marker coordinate={selectLocation} /> </Callout> ) } //기존코드 {selectLocation != null ? ( <Callout> <Marker coordinate={selectLocation} /> </Callout> ) : ( <Callout> <Marker coordinate={selectLocation} /> </Callout> )} //바뀐코드렌더링에 계속 문제가 생겨서 하루종일 봤네요이미 존재하던 마커가 롱 프레스 이후에 노출되는 이슈가 있었는데 isPending 이후에 렌더링 하도록 하니 잘 노출 됩니다.처음 롱 프레스 이벤트시 마커가 출력 되지 않고 애드포스트 버튼 클릭후 뒤로가기 시 선택한 마커가 사라지지 않고 누적되는 이슈가 있었습니다.selectLocation에 값이 잘 전달 되지만 렌더링이 되지않는 이슈였고 강제로 컨디션문으로null 일때와 아닐 때 둘다 렌더링 하게 했더니 해결 되었습니다
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
pgadmin 파일 window는 도대체 어떻게 설치하라는건가요....
맥 OS만 써있고 window는 그냥 알아서 설치하라는 느낌인데강의 환불 어떻게 하나요
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
[3-8] React-Query 도입 부분에서 질문 있습니다!
useSignup 함수에서 mutationFn에 회원가입 함수를 넣어줘서 Omit으로 'mutationFn'를 제외하셨는데useLogin 함수에서는 mutationFn랑 onSuccess, onSettled 함수를 추가로 설정해주셨는데 Omit으로 onSuccess랑 onSettled를 추가하지 않았는데 왜 에러가 발생하지 않는건지 궁금합니다! useLogin에서 onSuccess에서 성공해서 토큰들을 설정해줬는데 onSettled에서 토큰을 또 설정해주는건가요?
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
[3-3] useForm 무한 useEffect 실행
지금 [3-3] 폼 로직 리팩토링 & 유효성 검증 강의까지 들은 상태여서 뒷 강의에서 다루시는 부분이 있을 수도 있지만 useForm 내부에 setErrors를 하는 useEffect가 무한으로 실행되는 현상을 겪어서 공유드립니다. CustomButton.tsx에 console.log('SCREEN : ', Dimensions.get('screen').height) console.log('WINDOW : ', Dimensions.get('window').height)로깅하는 부분이 무한으로 실행되서 알게되었습니다. 해결 방법validateLogin을 useCallback으로 최적화또는useEffect 의존성 배열에 validate 제거const login = useForm({ initialValue, validate: useCallback(validateLogin, []), })
-
해결됨[풀스택 완성] Supabase로 웹사이트 3개 클론하기 (Next.js 14)
Next.js 15에서 Material Tailwind 설정
# Material Tailwind 와 연관된 라이브러리 설치 npm install @emotion/react @emotion/styled @material-tailwind/react @mui/icons-material --savenpm install @tailwindcss/typography autoprefixer --save-dev 지난주 공개된 next.js 15에서 Material Tailwind 설정하려니 안되서 도움 부탁드립니다.아직 초보라 이런 부분들이 개인적으로 좀 어렵네요~~^^;
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
[해결] MapView 사용시 bubblingEventTypes of null error 해결법
{ "name": "matzip", "version": "0.0.1", "private": true, "scripts": { "android": "react-native run-android ", "ios": "react-native -run-ios --simulator 'iPhone 16 Pro'", "lint": "eslint .", "start": "react-native start --reset-cache", "test": "jest" }, "dependencies": { "@react-native-masked-view/masked-view": "^0.3.1", "@react-navigation/drawer": "^6.7.2", "@react-navigation/native": "^6.1.18", "@react-navigation/stack": "^6.4.1", "@tanstack/react-query": "^5.59.16", "axios": "^1.7.7", "react": "18.3.1", "react-native": "0.76.0", "react-native-encrypted-storage": "^4.0.3", "react-native-gesture-handler": "^2.20.1", "react-native-maps": "^1.18.2", "react-native-reanimated": "^3.16.1", "react-native-safe-area-context": "^4.11.1", "react-native-screens": "^3.34.0" }, "devDependencies": { "@babel/core": "^7.25.2", "@babel/plugin-transform-private-methods": "^7.25.9", "@babel/preset-env": "^7.25.3", "@babel/runtime": "^7.25.0", "@react-native-community/cli": "15.0.0-alpha.2", "@react-native-community/cli-platform-android": "15.0.0-alpha.2", "@react-native-community/cli-platform-ios": "15.0.0-alpha.2", "@react-native/babel-preset": "0.76.0", "@react-native/eslint-config": "0.76.0", "@react-native/metro-config": "0.76.0", "@react-native/typescript-config": "0.76.0", "@types/react": "^18.2.6", "@types/react-test-renderer": "^18.0.0", "babel-jest": "^29.6.3", "babel-plugin-module-resolver": "^5.0.2", "eslint": "^8.19.0", "jest": "^29.6.3", "prettier": "2.8.8", "react-test-renderer": "18.3.1", "typescript": "5.0.4" }, "engines": { "node": ">=18" }, "packageManager": "yarn@3.6.4" } 최신버전으로 작업중입니다node 버전 22.6.0 으로 바꾸시면 해결됩니다.node -v 버전뜨시는거 보고 vscode 창 무조건 닫고 명령어 실핼시킬 터미널에서도 node -v 꼭 써서 버전확인하세여
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
Slider 패키지 설치 후 에러
강의 듣는 중 Slider 패키지를 설치하고아래와같은 에러가 발생합니다.
-
해결됨Next + React Query로 SNS 서비스 만들기
두개의 차이점
안녕하세요, 아래 ISR에 대해서 질문드렸었는데, nextjs 에서 2가지 구현 방법이있다고 해서두가지가 어떤 차이점이 있고 어떻게 활용하는게 좋을지 궁금해서 질문드립니다!1번 방법 = fetch API 의 revlidate를 활용하여 ISR 구현import ProductList from "@/component/ProductList"; import { getQueryClient } from "@/component/TanstackQueryOption"; import { getProducts } from "@/fetch/getProducts"; import { dehydrate, HydrationBoundary, QueryClient } from "@tanstack/react-query"; import Image from "next/image"; export default async function ProductPage () { const queryClient = getQueryClient(); await queryClient.prefetchQuery({ queryKey:['products'], queryFn: getProducts, }) return ( <> <section className='visual-sec'> <Image src="/visual.png" alt="visual" width={1920} height={300}/> </section> <section className="product-sec"> <h2>상품 리스트</h2> <HydrationBoundary state={dehydrate(queryClient)}> <ProductList /> </HydrationBoundary> </section> </> ) }import { isServer, QueryClient, defaultShouldDehydrateQuery, } from '@tanstack/react-query' function makeQueryClient() { return new QueryClient({ defaultOptions: { queries: { staleTime: 10 * 1000, }, dehydrate: { shouldDehydrateQuery: (query) => defaultShouldDehydrateQuery(query) || query.state.status === 'pending', }, }, }) } let browserQueryClient: QueryClient | undefined = undefined export function getQueryClient() { if (isServer) { return makeQueryClient() } else { if (!browserQueryClient) browserQueryClient = makeQueryClient() return browserQueryClient } }'use client' import { getQueryClient } from '@/component/TanstackQueryOption'; import { QueryClientProvider, } from '@tanstack/react-query' import { ReactQueryDevtools } from '@tanstack/react-query-devtools'; import { ReactNode } from 'react' export default function TanstackQueryProvider({ children }: { children: ReactNode }) { const queryClient = getQueryClient() return ( <QueryClientProvider client={queryClient}> {children} <ReactQueryDevtools initialIsOpen={true} /> </QueryClientProvider> ) } export const getProducts = async () => { const res = await fetch(`http://localhost:9090/api/products`, { method: "GET", headers: { "Content-Type": "application/json", }, next: { revalidate: 10, } }); const data = await res.json(); const currentTime = new Date().toLocaleTimeString('ko-KR', { hour: '2-digit', minute: '2-digit', second: '2-digit', fractionalSecondDigits: 3, hour12: false, }); if (typeof window === "undefined") { console.log('fetch products', 'server', currentTime); console.table(data); } else { console.log('fetch products', 'client', currentTime); console.table(data); } if(!res.ok) { throw new Error("Failed to fetch products"); } return data; }2번 방법 = export const revalidate 로 시간 설정 후 fetch로 받은 data 값을 바로 렌더링 시키기 import Product from "@/component/Product"; import styles from '@/component/ProductList.module.css'; import Image from "next/image"; export const revalidate = 10; export default async function Product2Page() { const data = await fetch('/api/products'); const products = await data.json(); console.log(revalidate, 'Product2Page'); return ( <> <section className='visual-sec'> <Image src="/visual.png" alt="visual" width={1920} height={300}/> </section> <section className="product-sec"> <h2>상품 리스트</h2> <div className={styles.productList}> {products.map((product: any) => ( <Product key={product.item_no} product={product} /> ))} </div> </section> </> ) } 2개다 ISR로 구현되며, 1번 방법은 Data Cache 캐싱 매커니즘을 활용하고,2번 방법은 Full Router Cache 캐싱 매커니즘을 활용한다의 차이점으로 생각이 드는데,이 외에 다른 차이점과 실제 개발을 하면서 선호되는 방식이 따로 있을까요? 해당 페이지만 보았을때는 2번 방법으로 해도 어차피 주기적으로 다시 생성해서 최신 데이터를 반영하면 복잡하게 react-query를 사용하고, Hydration을 하면서 데이터를 동기화할 필요가 있나 싶어서 어떻게 사용해야할지 감이 안잡히네여
-
해결됨맛집 지도앱 만들기 (React Native & NestJS)
강의 중 에러 문의
강의 중 빨간줄이 떠서 문의드립니다.빌드도 정상으로 되는데 저기 빨간줄은 왜 계속 떠있는거죠?