1.오늘은 리액트 블로그에 있는 18 버전 업그레이드에 대한 글을 번역하는 작업을 했다.
영어 공부도 하고, 리액트 18에 대해서도 공부할 겸 번역을 쭉 해볼 생각이다.
2.게시글 작성 페이지에서 모달을 만들었다.
모달에서 제목, 해시태그, 컨텐츠, 썸네일, 설명글을 모두 서버로 전달하도록 리팩토링했다.
3.몽고디비 연결하는 부분 수정 :
이전에 getStaticProps에서 몽고 디비로 바로 연결하는 부분이 이상하다고 생각되어서 코드를 수정했었다. 수정한 코드는 api routes에서 바로 몽고디비로 쿼리보내고 받아온 정보를 getStaticProps 안에서 요청하는 것이었다. 그런데 조금 찾아보니 getStaticProps 안에서 바로 api routes로 요청하지 말라는 글을 공식문서에서 확인했다. 그냥 getStaticProps 안에서 곧바로 db로 쿼리를 보내는 코드를 작성하라는 것이다. 코드를 수정했었는데, 이전 코드로 다시 수정해야 할 것 같다. 그래도, getStaticProps와 api routes 사이의 관계를 명확하게 이해할 수 있는 시간이었다.
추가로 모든 getStaticProps에서 mongoConnect하도록 했었는데, 공식문서에서 제공하는 example을 확인해보니 몽고디비 연결하는 부분을 캐싱할 수 있도록 해주고 있었다. 그래서 해당 코드를 추가하기로 했다. 그러면 변경 완료된 그림은
1)몽고디비 연결하는 코드 캐싱해서 앱이 실행되는 동안 다음번에도
2)모든 getStaticProps에서 직접 데이터를 쿼리하기
가 되겠다.
4.몽고디비 캐싱하는데 에러 발생 :
nextjs example에서 제공하는 코드를 보니, 몽고디비 연결하는 부분을 캐싱하게하는 코드가 있었다. 해당 코드를 적용해보니 타입 에러가 난다. 하.. 서버쪽 타입에러를 해결하는건 익숙하지 않다.
좀 검색을 해보니 다음과 같은 자료가 있었다.
https://bobbyhadz.com/blog/typescript-element-implicitly-has-any-type-typeof-globalthis
그러니까 global에 존재하지 않는데 접근하려고해서 발생했던 타입에러이다. 현재 글로벌에는 mongoose가 존재하지 않고 있기 때문에 해당 에러가 발생하는 것이다. 이 자료에 의하면 global에 해당 객체에 대한 타입을 선언해주라는 것 같은데, 사실 이 mongoose를 타입 선언하는 방법을 모르겠다. 다른 자료들도 찾아봤는데, 아직은 해결하지 못하겠다. 내가 이 문제를 해결하려면 무엇을 더 공부해야 하는 것일까? 우선은 js로 파일을 바꿔둬야할 것 같다.
5.개발자가 추구해야 할 본질은 무엇일까? :
오늘 갑자기 문득 들었던 질문이 있다. 개발자가 추구해야 할 본질은 무엇일까? 그래서 내가 속해있는 커뮤니티에 질문을 남겼다.
안녕하세요 여러분 개발자가 추구해야 할 본질은 무엇일까요?
예를 들면 이런 질문입니다.
"실력이 좋으면 연봉은 따라온다."
라는 문장이있습니다. 그렇다면 여기서
00을 추구하면 실력은 따라온다
는 무엇일까? 하는 것입니다. 00은 무엇일까요?
파레토의 법칙에 의하면 본질적인 20%의 영역을 추구하기만 하면 나머지 80%는 자연스럽게 따라온다고 합니다. 실력이 20%이고 연봉은 80%의 영역에 포함되어 있다고 생각합니다. 그러면 여기서 한번 더 던질 수 있는 질문이 있습니다. 실력의 영역에서 20%에 해당하는 본질은 무엇일까 하는 것입니다. 그래서 그 본질을 추구했더니 실력이 따라왔다 라고 말할 수 있는것이 무엇이라고 생각하시나요?
이 질문에 제가 생각해 본 몇가지 대답은 다음과 같습니다 :
1.재미있게 한다. 그러면 실력은 따라온다.
쉽게 나올 수 있는 대답인 것 같습니다. 하지만, 조금 상투적인 대답이라는 생각이 듭니다. 조금은 더 구체적인 대답을 찾아볼 수 없을까 싶습니다. 무엇이 개발을 즐겁게 만들어주는 것일까요?
2.해결하고 싶은 문제에 집중한다. 그러면 실력은 따라온다.
스스로 얻은 대답이지만 꽤 공감되는 문장입니다. 진정 해결하고 싶은 문제를 만났고, 그 문제를 해결하려고 집중하고, 공부하고 삽질했더니 실력이 따라오게 된 것입니다. 그렇게 실력이 쌓이니 연봉도 따라온 것이죠.
혹시 여러분이 생각하기는 개발자가 추구해야 할 본질이 무엇이 있다고 생각하시나요? 여러분의 다른 생각 혹은 제가 말한 대답에 대한 첨언도 좋습니다!
그리고 다른 분들의 대답이다.
W : 저는 두번째 자질이 좋은 개발자이기위한 반드시 필요한 조건이지만, 충분조건은 아니라고 생각해요!
활을 예로 들어보면 위에서 말씀드린 역량은 활을 잘 만들고 잘 쏘기 위한 능력이라고 생각해요.
하지만, 활만 잘쏜다고 충분하진 않죠.목표를 설정하고 목표물을 추적하는 능력도 중요하다고 생각합니다.
개발계로 다시 돌아와서 예시를 들어보면 제가 Angular가 너무 재밌어서 깊게 팟는데, 세상에서 너무 비주류이면, 기껏 공부한 지식을 써먹을 기회가 많을 수가 없을거라고 생각합니다.
즉, 해결하고 싶은 문제도 조금은 세상에 발을 맞춰 적당히 골라야한다고 생각해요!
L : 안녕하세요! 짧게 제 생각 남겨봅니당ㅋㅋ 비단 개발자에게만 해당되는 것은 아니겠지만, 저라는 사람의 가치관으로는 `
현재를 사는 것`이 그 본질이라고 생각해요! 사실 그 본질은 예찬님께서 들어주신 예시들처럼 사람들마다 혹은 상황마다 다르기 때문에(누군가는 재미를, 누군가는 문제 해결을 추구하듯이) 개개인이 말하는 본질을 넓게 영위할 수 있는 그 무언가가 그나마 대표적인 본질이 아닐까 생각했어요! 때문에 지금 우리가 행동하고 바꿀 수 있는 현재야말로 그 본질이 아닐까 생각합니다! 그 현재에 재미가 대입될 수도 있고 해결하고 싶은 문제가 대입될수도 있고, 남들보다 나아가겠다는 경쟁심이 될 수도 있을 것 같아요. 마치 수학에서의 변수처럼 무엇이 들어와도 커버가 되는 느낌이지만, 저는 결국에는 현재를 사는 사람을 이길 수 없다고 생각해요!
W : 첫번째 자질은 뭐가 재밌는건지에 따라 이리저리 말이 다를 수 있어서 너무 추상적인 대답이라고 생각합니다.문제 해결에 집중한다! 라고 한다면 2번 자질과 같은 것이고, 다른 이야기도 많을테니까요
W : 현재를 산다,,, 극 동의합니다…!
나 : 오 저 또한 현재에 몰입하는 것을 중요하게 여기고 있습니다. 그런데 진정한 의미에서 현재에 몰입하기 위해서는 전제 조건이 필요하다고 생각합니다. 그 전제 조건이란 그 행위자체가 목적이 되는 행위에 집중하고 있어야 한다는 것입니다.(수학을 공부하는 목적이 좋은 성적을 얻어서 엄마에게 초콜릿을 얻고자 하는 친구와 수학 자체가 즐거워서 수학을 공부하는 친구. 둘 중 누가 현재에 집중하고 있는 것일까요?)
그 행위자체가 목적이 되는 행위가 무엇인지 설명하기 위해서, 무엇이 아닌지를 설명할 수 있을 것 같습니다. 돈을 버는 것은 행위자체로 목적이 될 수 없습니다. 돈은 항상 다른 무엇을 위한 목적이 됩니다. 돈은 항상 그 자체로 ‘수단‘이 될 수 밖에 없는 대상입니다.
반면 행복을 추구하는 것은 또 다른 상위 목적이 존재하지 않습니다. 다시 말해 행복을 추구하는 것은 다른 무언가를 위한 ‘수단’으로 존재하지 않는 것입니다. 이런 행위가 곧 행위 자체가 목적이 되는 행위라고 생각합니다. 그리고 이런 행위들에 집중할 때 비로소 현재에 몰입하며 살아갈 수 있습니다.
그러면 저는 다시 질문하는 것입니다. 여러분의 무엇이 현재에 몰입하게 하느냐는 것입니다. 저는 W님께서 말씀해주신것처럼 취업 시장에 맞춰서 문제해결의 영역을 조절해야 한다는 부분에서 꽤 많이 공감하면서도, 마음 한 편으로는 공감하기가 어려운 것 같습니다. 결국 문제해결의 목적이 취업이 되어버리는 것이기 때문에, 문제해결 자체가 목적이 되지 않게 됩니다. 내가 문제를 해결하는 와중에도 이 문제를 해결하면 취직하는데 유리할까?라는 질문을 하는 사람은 문제를 해결하는 현재에 높은 순도로 몰입할 수 없게 됩니다. 수학공부를 하는 목적이 초콜릿을 얻고자 공부하는 친구와 다를 것이 없습니다.
저는 개발을 공부하는 이유가 단순히 취직과 높은 연봉, 빛나는 타이틀이 되지 않았으면 좋겠다고 생각합니다. 그것이 추구하는 목표에 높은 가치를 차지하고 있는 것이라면, 현재의 인생은 그 목표를 차지하기 전까지는 실패한 인생이 되어버립니다. 그렇다고 비본질적인 요소에만 온전히 몰입하다간 현실적으로 얻어야 할 가치와 책임(돈,직장) 을 가지지 못할 수도 있습니다.(이 부분이 경준님의 이야기에 한편으론 동감한다는 의미였습니다.)그런 이유로 과연 진정 개발자를 성장으로 이끌어주면서도 현재에 몰입하게 만들어줄 가치는 무엇일까? 추구해야 할 가치는 무엇일까? 라는 질문을 던지게 된 것 같습니다.
어쩌면 이 질문은 보편적인 대답을 얻고자하는 질문은 아닌 것 같고, 여러분 개개인은 개발자로써 어떤 본질적인 가치를 추구하고 있는지를 묻는 질문이 되는 것 같습니다. 그것으로부터 영감으로 얻고 싶은 마음도 있는 것 같구요.
M : 매번 좋은 논의 만들어주셔서 감사합니다 ㅎㅎ아래는 제가 생각하는 “ “을 추구하면 실력은 따라온다는 부분에대한 의견입니다
1순위로 흥미가 가장 중요한 부분이라고 생각합니다 2순위는 변화 3순위는 꾸준함 였던거같습니다
헬스를 7~8년동안하면서 5년동안은 정말 일주일에 5일이상 한번도 안쉬고 꾸준히했었습니다.그 배경은 흥미가 가장컸고 운동을 하면할수록 생기는 몸에 대한 변화가 있었기에 꾸준함을 만들어주었던거같습니다. 이것을 개발 관점으로 따졌을떄 개발로 부터 오는 흥미를 찾고 그 흥미로부터 내 자신의 실력에대한 변화도 생길것이고 실력에 대한 변화로 인해 꾸준함도 생길거라고 저는생각합니다.
그러면 개발로 부터 어떻게 흥미를 얻을까 ?곰곰히 생각해본결과 내가만들고 싶어하는 어플리케이션을 사이드프로젝트로 녹여 기술에 대한 재미를 붙인다는 방법을 생각해봤네요 ㅎㅎ사이드프로젝트를 하기위해서는 개발스킬이 필요할것이고 그것을 위해 스터디도 자연스럽게 하게되고 개인공부도 할꺼라는 생각도 듭니다 ㅎㅎ
저는 전공자임에도 불구하고 학교를 졸업하고 평생 공부해야하는 개발자를 내가 하는게 맞을까 라는 생각을 정말 많이했었습니다.
그 결과 자신이없어서 학교를 졸업하고 1년의 공백기를 가지게되었고 이러한 고민은 남과의 비교에서 가져왔던거같습니다.. 곰곰히 생각해본결과 개발자처럼 의미있고 재밌는일을 하고 본인실력에 맞춰서 자유롭게 이직할수있는 직업이 몇이나 될까?
또한 학교에서 동기들과 사이드프로젝트를 진행하면서 얻은 성취감이 너무 좋았던 기억이 났습니다.
그리고 헬스를 통해 배운 흥미, 변화 , 꾸준함을 바탕으로 개발자라는 직업에 녹이면 엄청난 발전이 있을꺼같아 올해4월부터 다시 개발자의 꿈을 가지고 열심히 달리려고합니다 ㅎㅎ
L : 오... 다른 분들의 이야기도 들어보니까 많은 생각이 드네요ㅋㅋㅋ 평상시에 저는 복잡한 것은 최대한 단순하게 생각하는 편이라, 그저 현재를 열심히 살자라는 마인드로 퉁치는 게 편하더라구요ㅋㅋㅋㅋㅋ 생각이 많아지면 오히려 동력을 잃는 것 같아서, 늘 결론이 저렇게 귀결되는 것 같아요!
저에게는 `행위 자체가 목적이 되는 행위`가 `그저 현재를 살아가는 것`이 가능하다고 생각해요! 현재를 살아서 무엇을 하려고? 하는 의문을 두지 않고 그저 묵묵히 현재를 열심히 살아가는, 현재를 열심히 살아가는 것이 그 목적이기도 한 사람들이 정말 무섭더라구요ㅋㅋ 이런 사람들을 보면 목표가 없어보이기도 하면서 동시에 이 사람의 목표의 끝이 가늠이 안되는 느낌..?
00을 추구하면 실력이 따라온다.
여기서 00은 정답이 없고 사람마다 다르다고 생각되지만, 저에게 딱 하나로만 채우라고 한다면 `현재`이고 `현재`이고 싶습니다
6.SyntaxError: Unexpected token u in JSON at position 0
몽고디비 연결하는 부분을 캐싱하고 나서 다시 getStaticProps 그리고 getStaticPaths를 사용하는 부분에 몽고 디비 연결하는 코드를 작성했다.
그랬더니 위 사진과 같이 에러가 발생했다. 데이터를 parse하는 과정에서 뭔가 문제가 생긴 것 같다. 그래서 데이터를 어떻게 가져오고 있는지를 확인해봤더니 데이터는 잘 가져오고 있었다.
아 그런데, 다시 확인해보니 이전에 axios를 통해서 데이터를 가져오고 stringify 해줄 때는 res에서 date를 꺼내서 값을 넣어주고 있었는데, 몽고디비에서 바로 가져온 데이터에서는 이렇게 넣으면 안되는 것이었다. 그래서 JSON.stringify(res.data)로 되어있던 코드를 JSON.stringify(res)로 바꿔줬더니 해당 에러가 사라졌다.
해결!
7.게시글 작성하는 부분에서의 몽고디비 Schema 변경하기 :
게시글 작성할 때, 이미지 url과 해시태그 부분이 추가되었다. 그래서 해당 부분 스키마를 추가하는 작업을 했다. 그리고 관련 api들, 타입들을 수정해줬다.
8.aws에서 받아오는 이미지 사용가능하도록 환경 설정해주기 :
nextjs에서는 static한 이미지가 아닌 외부 이미지를 사용하기 위해서는 환경 설정을 해줘야 한다. nextjs가 이렇게 하도록 강제 한 이유는 요상한 유저로부터 어플리케이션을 보호하기 위함이다. 딱 내가 지정한 도메인으로부터만 이미지를 받아오도록 허용해야한다. 이렇게 하는 것을 remotePattern이라고 한다. 공식문서에 소개되어있다.
https://nextjs.org/docs/api-reference/next/image#configuration-options
공식문서에서 소개해주는대로, 설정을 아래와 같이 변경해주었다.
const nextConfig = {
...
images: {
remotePatterns: [
{
protocol: 'https',
hostname: 'recoen.s3.ap-northeast-2.amazonaws.com',
port: '',
pathname: '/next-s3-uploads/**',
},
],
},
};
혹시혹시 한번에 될까??! 했지만, 역시 한번에 되지 않는다ㅋㅋㅋ
이런에는 이런 에러를 만났다.
아무튼 이미지를 가져오는 부분에서 문제가 있었다. 에러문구를 조금 더 상세하게 살펴보자.
"Image with src "https://recoen.s3.ap-northeast-2.amazonaws.com/next-s3-uploads/34606707-2b1e-4f0f-ac8b-d4d937a240d4/sumner-mahaffey-7Y0NshQLohk-unsplash.jpg"
has "placeholder='blur'" property but is missing the "blurDataURL" property.
Possible solutions:
- Add a "blurDataURL" property, the contents should be a small Data URL to represent the image
- Change the "src" property to a static import with one of the supported file types: jpeg,png,webp,avif
- Remove the "placeholder" property, effectively no blur effect
Read more: https://nextjs.org/docs/messages/placeholder-blur-data-url"
아, blurDataURL을 안넣어줬다고 뭐라고 하는 것 같다. 해당 내용을 공식문서에서 한번 살펴보자. https://nextjs.org/docs/api-reference/next/image#placeholder
For dynamic images, you must provide the blurDataURL property. Solutions such as Plaiceholder can help with base64 generation.
공식문서에서 말씀하시기를, dynamic image를 사용하려 한다면 blurDataURL을 must! 사용해줘야 한단다. 그리고 Plaiceholder를 사용한다고 하는데, 오.. 역시 만만치 않다.
blurDataURL에는 blur시에 보여줄 이미지 url이 필요하다. 이것을 Plaiceholder에서 제공해준다. 다른 의미없는 이미지를 넣을수도 있겠지만, 이 라이브러리를 이용하면 해당 이미지의 blur 처리된 이미지를 얻을 수 있다.
그래서 이것을 nextjs에서 어떻게 사용하는지를 살펴보니, getStaticProps 내부에서 blur 이미지와 실제 이미지를 같이 받아온다.
export const getStaticProps = async () => {
const { base64, img } = await getPlaiceholder(
"https://images.unsplash.com/photo-1621961458348-f013d219b50c?auto=format&fit=crop&w=2850&q=80",
{ size: 10 }
);
return {
props: {
imageProps: {
...img,
blurDataURL: base64,
},
title: config.examples.pages.base64.title,
heading: config.examples.variants.single.title,
},
};
};
현재 나는 article이라는 페이지에서 전체 데이터를 한번에 받아온다. 그 전체 데이터에는 image들을 포함하고 있는데, 위의 예시는 하나의 컴포넌트를 대상으로 저렇게 이미지를 가져오고 있다.
음 혹시 각각 개별 컴포넌트 안쪽에서 props로 받아온 이미지 값을 저 staticProps 안에서 사용할 수는 없는걸까? 그러면 위에서 소개한 예시대로 코드를 작성할 수 있을 것 같다는 생각이 든다.
아, 아니면 또 다른 방법이 있는데 애초에 처음에 데이터베이스에 해당 이미지를 저장하려고 할 때, 저 라이브러리를 이용해서 base64이미지를 받아놓고 같이 사용하는 것이다. 이렇게하면 훨씬 간단해질 것 같다는 생각이 든다.
자, 이것을 한번 테스트해보려면 라이브러리를 다운받고 시도를 해보자. 우선 plaiceholder 공식문서에서 제공하고 있는 대로 라이브러리를 다운 받는다. 그런데, 에러가 난다...
plaiceholder를 사용하려면 먼저 sharp라는 라이브러리를 다운받아야 한다. 그런데 이 sharp를 다운받으려고 할 때, 에러가 나는 것이다.
npm ERR! code 1
npm ERR! path /Users/noyechan/Desktop/RECOEN/node_modules/sharp
npm ERR! command failed
npm ERR! command sh -c /var/folders/_9/cc9fptys7kn7h31vsq71rztw0000gn/T/install664267459.sh
npm ERR! sharp: Downloading https://github.com/lovell/sharp-libvips/releases/download/v8.13.1/libvips-8.13.1-darwin-arm64v8.tar.br
npm ERR! sharp: Please see https://sharp.pixelplumbing.com/install for required dependencies
npm ERR! sharp: Installation error: aborted
뭔가 미리 요구되는 dependencies가 있는 것 같다.
아 근데 잠시, plaiceholder 공식문서에보면 몇몇 프레임워크는 sharp를 이미 가지고 있다고 한다. 그래서 검색을 해보니, 넥스트 js는 built-int 이미지 최적화를 위해서 sharp를 사용한다고 한다. 그래서 만약 sharp를 이용하는데에 문제가 있을 경우 참고하라고 문서를 만들어뒀다. 어쩌면 이미 sharp가 설치되어있는지도 모르겠다. 우선 sharp를 무시하고 plaiceholder만 설치하고 진행을 해보자. 만약 문제가 생기면 그때 다시 sharp 설치하는 문제를 해결해야겠다.
확인해보니 이미 sharp가 설치되어있는 것은 아니었다ㅋㅋㅋ 음.. 이것저것 문제를 해결하려니 머리가 아주 살짝 복잡해졌다.
지금 내가 해야할 일은
1)sharp 설치문제 해결하기
2)plaiceholder를 어디서에 사용할지 생각하기(3가지 옵션 : 이미지업로드할때, 개별컴포넌트에서, 전체데이터불러오는 컴포넌트에서)
이런 세가지를 해결하려면 족히 1시간에서 2시간 정도는 걸릴 것 같다는 판단이 들었다. 우선 해당 내용을 요구하는 이유는 내가 next/image에서 blur 옵션을 사용하고 있기 때문이다. 그러면 blur 옵션을 우선은 사용하지 말자.
blur 옵션을 사용하는 것은 사용자 경험을 위해서는 필요하다고 생각한다. 그러나 지금은 우선 이미지를 불러오는 것을 우선순위로 해야할 것 같다.
그래서 blur 옵션을 제거했다. 그랬더니 아니 또 다시 에러가 나타난다.
Error: Invalid src prop
(https://recoen.s3.ap-northeast-2.amazonaws.com/next-s3-uploads/34606707-2b1e-4f0f-ac8b-d4d937a240d4/sumner-mahaffey-7Y0NshQLohk-unsplash.jpg)
on `next/image`, hostname "recoen.s3.ap-northeast-2.amazonaws.com"
is not configured under images in your `next.config.js`
라는 것이다. 어허. 나는 분명 위에 공식문서가 하라는대로 설정해줬는데, 안된다. 해당 에러문구에서 이 문서를 봐라라는 안내가 있어서 들어가봤다. 해당 문서를 봤더니, domains를 사용하라는 것이다. domains는 여러 도메인을 사용하려고 할 때 사용하라고 그랬는데... 아무튼 일단 domains로 바꿔봤더니
이렇게 외부에서 url로 가져오는 이미지를 사용할 수 있게 되었다. 잘된 김에 몇가지 데이터를 더 넣어보자.
좋아 계획대로 되고 있다. 우선 사용자 경험을 위해서 blur 처리하는 부분은 추후에 다시 진행해보도록 하자. 여기 TIL에 이렇게 잘 기록해뒀으니, 다음번에 다시 와서 진행할때도 수월할 것이라고 생각된다.
그리고 remotePattern은 왜 안되었는지도 다시한번 찾아봐야 할 것 같다.
9.jest, react-testing-library에 대한 공부 :
오늘은 멘토링이 있는 날이다. 멘토님이 오늘은 테스트 코드를 작성하는 방법에 대한 강의를 해주신다고 하셨다. 그래서 미리 공식문서들을 읽어가려고 한다.
10.폴더구조에 대한 고민 :
기존에 폴더 구조를 atomic 패턴을 이용하고 있었다. 그런데, 생각보다 다른 사람들이 코드를 보려고 할 때는 이해하기 쉽지 않을 것 같다는 생각이 들었다. 나야 해당 코드가 어디에 있는지를 알기 때문에 좋을 수 있겠지만, 다른 사람들이 코드를 이해하려면 쉽지 않겠다는 생각이 들었다.
왜 쉽지 않을것 같다고 생각이 들었냐면, 단순히 컴포넌트를 계층별로 나누어두었기 때문이다. 다른 사람들이 특정 컴포넌트를 사용하려고 할 때, 해당 컴포넌트의 계층을 바로 떠올리는 것은 쉽지 않다. 해당 컴포넌트의 기능을 생각하면서 폴더를 찾아보게 될 것이다. 해당 컴포넌트의 기능은 00이니까, 00과 관련된 폴더는 보니까~~~ 라고 하면서 폴더를 찾아볼 것이다. 해당 컴포넌트의 계층은 mocules 이니까 mocules를 찾아봐야지 하지 않을 것 같다.
그리고 리액트 공식문서에서도 atomic 패턴은 그냥 참고만 하라고 한다.
Some people also prefer to go further, and separate components into different folders depending on their role in the application. For example, Atomic Design is a design methodology built on this principle. Remember that it’s often more productive to treat such methodologies as helpful examples rather than strict rules to follow.
[react docs]
우선 폴더구조를 잘 만들기 위해서 고려해야하는 것은 확장성, 유지보수 가능성이다.
확장성이 있다는 것은 새로운 기능이 추가되기 쉽다는 것이다.
https://sennieworld.tistory.com/67
이 글을 읽어보니 모듈화에 대한 이야기가 나오고 있다. 안그래도 최근 객체지향과 관련된 책을 읽으면서 공부를 하는 중인데, 조금 더 객체지향적인 폴더 구조를 만들어보는 것은 어떨까 싶은 생각이 든다.
객체지향적인 폴더구조란. 무엇이라고 할 수 있을까. 내가 생각하는 객체지향적이라는 것의 의미는 각각의 모듈이 자신이 책임져야하는 부분을 스스로 잘 감당하도록 하는 것이다. 이런 의미를 놓고 봤을 떄 폴더구조는 각각이 가진 역할을 잘 분리시키는 방향으로 폴더구조를 짜는 것이 좋을 것 같다.
현재 나의 컴포넌트의 구조는
components,
utils,
hooks,
mocks,
shared,
로 되어있다. 그리고 components 안쪽에서 아토믹 패턴으로 분류를 해두었다.
다른 부분들은 기능별로 잘 분리를 해두었지만, components 폴더 안쪽에서는 기능과 역할별로 컴포넌트를 분리해둔 것이 아닌, 계층별로 컴포넌트를 구분해두었다. components 폴더 안에서 역할별로 컴포넌트를 나눈다면 어떻게 나눌 수 있을까?
저런 고민을 하던 와중에 아무래도 많은 스타를 받은 프로젝트의 폴더구조를 보는 것이 좋겠다는 생각이 들었다.
https://github.com/oldboyxx/jira_clone/tree/master/client/src
https://github.com/gothinkster/react-redux-realworld-example-app
https://github.com/cypress-io/cypress-realworld-app/tree/develop/src/components
https://github.com/withspectrum/spectrum
https://github.com/craigary/nobelium
이런 각종 프로젝트들을 확인해보니 모두들 그냥 component에 넣어두고, 주제별로 컴포넌트를 나눠두고 있는 것 같았다.
리액트 공식문서에서는 폴더 구조를 놓고 5분 이상 고민하지 말라고 이야기한다ㅋㅋㅋ
https://reactjs.org/docs/faq-structure.html#dont-overthink-it
조금 더 참고해보면 좋을 것 같은 자료
https://www.robinwieruch.de/react-folder-structure/
https://blog.webdevsimplified.com/2022-07/react-folder-structure/
https://www.xenonstack.com/insights/reactjs-project-structure
https://www.taniarascia.com/react-architecture-directory-structure/
아마도 현재 폴더 구조에서 바뀔 부분은 다음과 같을 것 같다.
components : 기능별로 분리, 계층별 분리 x
lib : 외부라이브러리를 사용하는 경우 사용할 것
utils : 반복해서 사용하는 함수들
'TIL(Today i learned)' 카테고리의 다른 글
[TIL-2022.09.29] keydown 한글입력 에러해결 feat. compositionEnd (2) | 2022.09.30 |
---|---|
[TIL-2022.09.28]jest.SpyOn, createPortal 테스트코드 작성 (0) | 2022.09.28 |
[TIL-2022.09.26] nextjs image upload (0) | 2022.09.26 |
[TIL-에러노트] The policy failed legacy parsing (0) | 2022.09.26 |
[TIL- 2022.09.24] 웹폰트 최적화 (0) | 2022.09.24 |