힙하게 코딩하는 방법(2)

haneum·2024년 3월 4일
0

힙하게 코딩하는 방법(2022)의 업그레이드 버전입니다.

부가적인 기능은 라이브러리를 사용하여 개발한다.

라이브러리를 자제하여 사용한다

자신의 역량으로도 충분히 개발할 수 있는 기능인데 굳이 라이브러리를 가져다가 사용하는 경우가 있다. 바로 라이브러리를 가져다가 사용하면 시간적인 효율성은 증가할 수도 있지만, 나중에 그 라이브러리를 사용하는 코드에 큰 에러라도 난다면, 아니면 프로젝트의 필수적이고 핵심적인 기능을 하는 로직과 라이브러리를 사용한 로직에 충돌이 일어나게 된다면, 정말 힘들어질 수 있다. 간단한 기능을 하는 라이브러리라면 라이브러리를 사용하지 않고 기능을 구현하는 것이 장기적인 효율적 측면으로 좋다고 생각한다.

어떤 기능을 구현하기 위해 라이브러리를 자제하여 사용하고 하나부터 열까지를 모두 다 개발하기 시작한다면 시간적인 비용이 너무 많이 발생한다. 하나부터 열까지를 모두 다 구현하면 좋겠지만(사실 개발자의 역량에 따라 좋지 않을 수도 있다.) 프로덕트를 개발해야 하는 측면에서는 이는 너무 비효율적이다. 다만, 개인 사이드 프로젝트를 개발할 때에는 개발 실력에 조금의 도움이 될 수도 있지만, 사이드 프로젝트도 어떻게 보면은 최종적인 목표가 프로덕트화하여 배포하여 수익을 창출하는 것이기에 사이드 프로젝트를 개발할 때도 모든 것을 다 개발하는 것은 비효율적이다. 즉 핵심 기능(서비스의 기둥)이 아니라면, 부가적인 기능이라면 라이브러리를 상용하는 것이 효율적이다는 것이다.

다른 개발자의 코드를 많이 읽는다

다른 사람의 코드를 많이 읽는다

나는 이 부분이 굉장히 중요하다고 생각된다. 나는 요즘 @velopert 님의 사이드 프로젝트인 velofolio의 코드를 읽고 있다. 이처럼 다른 사람의 코드들을 많이 읽게 된다면 나의 코드 스타일도 좋아질뿐더러 프로그래밍 실력도 같이 증가하게 된다.

여전히 전적으로 동의하는 부분이다. 개발자가 개발 실력을 향상시킬 수 있는 방법은 여러 가지다. 그 중 하나는 뛰어난 개발자의 코드를 읽고, 분석한 후에 좋은 점을 나의 코드에 적용하는 것이다. 많은 코드를 읽고, 분석하고, 적용시키는 것을 반복한다면 기존에 썼던 코드보다는 조금은 더 효율적인 코드를 작성할 수 있을 것이다.

코드에 누구나 알아볼 수 있는 주석을 많이 작성해둔다.

코드에 주석을 많이 작성해둔다

나는 정말 깔끔하게 코딩하는 것을 좋아해서 주석을 많이 작성하지 않았다. 그런데 이번에 프로젝트를 조금 수정하려고 하니 뭔지 하나도 몰라서 정말 다시 코드를 작성하고 있는 상황이다. 이처럼 필요한 주석을 많이 작성해둔다면 프로그래밍을 할 때도, 협업을 할 때도 정말 도움이 된다.

내가 쓴 코드에는 나만이 알아볼 수 있는 코드들이 생각 외로 정말 많이 포함되어 있다. 이런 나만이 알아볼 수 있는 코드들이 점차 많아진다면 협업에 큰 문제가 생기며, 가장 큰 문제점은 나중에 내가 작성한 코드를 수정할 때에 절대로 빠르게 수정할 수가 없다는 것이다. 또한, 내가 썼더라도 코드를 전혀 알아볼 수가 없으면(거짓말 같지만 이런 경우가 정말 많다.) 최악의 경우는 그 코드는 갈아엎어야 한다. 내가 쓴 코드를 알아볼 수 없는 가장 주된 이유는 나만이 알아볼 수 있다는 것은 그때만 내가 알아볼 수 있다는 점이다. 아무리 내가 썼더라도 그때만 내가 이런 코드를 왜 작성했는지를 알 수 있기에 나중에는 아무리 코드를 해석하려 해도 할 수가 없는 것이다.

그렇다면, 이런 문제점을 해결하려면 무엇을 통해 해결할 수 있을까? 바로 주석을 많이 작성하면 된다. 여기서 주석을 많이 작성하는 것이 의미하는 바는 아무리 내가 아는 것(내가 생각하기에 누구나 안다고 생각하는 것)이라도 그것에 대한 정보(주석)를 작성한다는 것이다. 이렇게 내가 생각하기에 누구나 안다고 생각하는 것에 대한 정보를 작성한다면 그 코드는 조금은 누구나 알아볼 수 있는 코드가 될 수 있다. 또한, 내가 조금은 잘 알아볼 수 있는 코드가 될 수 있다.

const isAgeOk = age => (age === 19 ? true : false);

예를 들어, isAgeOk 이라는 함수가 있다고 하자. 이 함수는 웹사이트 가입 시에 만 19세 이상인지를 확인하는 함수이다. 그런데 이 함수에는 인자로 age를 받는데, 이 코드를 처음 보는 사람의 입장에서는 이것이 만 나이 인지 아니면 세는나이 인지에 대한 정보가 없다. 그리고 함수 인자 age 가 어떤 형식의 데이터를 받는 지에 대한 정보가 없다. 다만, age === 19 로 어떤 형식의 데이터를 받는 지 추측은 가능하지만, 되도록이면 TypeScript나 JSDoc을 사용하여 정확히 명시하는 것이 낫다. 그리고 이 함수는 true와 false를 리턴하는데 이것이 무엇을 의미하는 지에 대한 정보도 없으며, 함수명인 isAgeOk라는 함수가 무슨 일을 하는 지에 대한 정보 또한 없다.

즉, 지금 이 코드를 쓰고 있는 나는 이 함수가 무엇을 위한 함수인지를 정확히 알지만 미래의 나는, 그리고 다른 개발자들은 이 함수가 무엇을 위한 함수인지 전혀 알지 못한다.

// 나이가 만 19세 이상인지 확인하는 함수
const isAgeOk = age: number => { // age는 만 나이
return age === 19 ? true : false; // true는 만 19세 이상을 의미
}

이 코드에서 true는 만 19세 이상을 의미 는 굳이 작성하지 않아도 추측하여 알아볼 순 있지만, 그래도 편의상 빠르게 코드를 읽기 위해 작성했다.

내가 주석을 작성하는 방식이 잘 못됐을 수도 있지만, 나는 대부분의 코드를 이런 방식으로 작성한다. 위의 코드와는 차이점을 단숨에 알 수 있을 것이다. 필요한 주석이 많은 코드는 코드를 읽는 사람에게 조금이라도 도움이 되게 된다.

주의할 점은 코드를 처음부터 깔끔하게 작성하라는 것이 아니다. 처음부터 클린코드를 하면서 코드를 작성하라는 것이 아니다. 그저 지금 내가 작성하고 있는 코드에 대한 주석을 많이 작성하라는 것이다. 이런 방식으로 코드를 작성하다 보면 나중에 클린코드를 할 때도, 수정을 할 때도 정말 편하게 수정을 할 수가 있다. 또한 협업을 할 때에도, 다른 개발자가 코드를 읽을 때에도 조금이나마 도움이 될 수 있다.

코딩 이외의 것은 신경 쓰지 않는다

코딩 이외의 것은 신경 쓰지 않는다

이 것은 Ryan DahlI hate almost all software의 글을 읽고 실행하게 된 것 중 하나인데, 그냥 개발자는 코딩만 잘하면 되고 그 이외의 것을 신경 쓰지 말라고 하는 글이었다.

나도 원래는 VSCode를 꾸미고, .vimrc 파일을 꾸미는 걸 좋아했는데, 이 글을 읽고 이제는 코딩에 외의 부가적인 것은 하지 않으려고 노력하는 중이다.

여전히 전적으로 동의하는 부분이다. "노트북 바꿀까", "Terminal 좀 이쁘게 꾸며볼까" 등등 코딩 이외의 것을 신경 쓰다 보면, 점차 우리가 해야 하는 본질인 코딩을 소홀히 하게 된다. 그저 주어진 환경에 맞게 데스크톱은 구성하면 되며, 개발 툴은 무료 개발 툴을 사용하면 되며, 기술을 배우고자 할 때는 공식 문서를 보거나, 정말 이해가 되지 않으면 강의를 사서 들으면 된다. 우리는 개발 그 자체에만 신경을 쓰면 된다. 그 외의 것은 절대로 신경을 꺼야 한다.

하나하나 잘게 쪼개어 코딩한다

컴포넌트 중심으로 코딩한다

모든 것을 컴포넌트로 나누고, 체계적으로 개발하게 된다면 새로운 기능을 추가할 때나 버그를 고칠 때에 상당히 구조상으로 유용할 수 있다.

만약 당신이 함수를 작성하고 있다면 그 함수에는 하나의 일만 할당해야 한다. 절대로 두 가지의 일을 할당해선 안된다. 이는 컴포넌트도 동일하다. 하나의 컴포넌트에는 하나의 기능만 수행해야 한다. 절대 두 가지의 일을 수행해선 안된다. 두 가지의 일을 수행하고자 한다면 같은 종류의 하나의 루트 컴포넌트를 만들고 두 개의 자식 컴포넌트를 만들어 루트 컴포넌트에 자식 컴포넌트를 불러와 할당시켜야 한다.

처음에는 막코딩으로 기능을 구현한다

클린 코드를 나중에 한다

만약 당신이 클린 코드의 대해 비숙련자라면, 처음 어떤 기능을 개발할 때는 막코딩으로 개발해야 한다. 너무 막코딩 하면 안되겠지만은 일단은 흐름대로 코딩을 하는 것이 시간적으로나 기능적으로 효율적이다.

이유는 만약 당신이 클린 코드와 프로덕트 개발을 병행하여 한다고 생각해 보자. 현재는 프로덕트의 기능적인 구조도 잡히지 않은 상태이다. 먼저 당신은 그 프로덕트의 기능 구현을 위해 코드를 작성할 것이다. 하지만 그 구현을 하는 도중에 클린 코드가 필요한 부분이 있다면, 당신은 시간을 들여서 기능 구현을 위한 코드에 클린 코드를 할 것이다. 이 과정이 구현하는 중에 몇 번만 반복될 때, 당신이 일반적으로 클린 코드의 형태로 코딩을 잘 한다면 괜찮을 것이다. 하지만, 당신이 클린 코드를 잘 모르고, 어떻게 클린 코드의 형태로 코드를 작성하는지 모른다면, 당신은 기능 구현이 아닌 클린 코드를 위해 더 많은 시간을 쓰게 될 것이다.

이처럼 클린코드에 대해 비숙련자라면 나는 병행하여 클린 코드를 하는 것은 추천하지 않는다. 왜냐하면, 지금 코딩하는 원래의 목적인 기능 구현이 아닌, 기능 구현을 위한 코드를 수정하는 것을 더욱더 중요하게 생각하여 코딩하기 때문이다. 만약 이런 식으로 코딩을 계속한다면, 당신은 기능 구현의 대한 본질이 흐려 저서 원래 생각한 기능 구현도 잘 못하게 될뿐더러, 클린 코드 한 코드도 만족스럽지 않은 두 마리의 토끼를 잃게 될 것이다.

그래서 나는 클린코드에 대해 비숙련자라면, 조금의 기능을 구현할 때는 흐름대로 코딩하는 것이 맞는다고 본다. 그래야 결과물도 만족스럽고 효율적인 측면에서도 만족스럽기 때문이다.

위의 글 처럼 모든 것을 처음 개발할 때는 막코딩(클린코드는 신경쓰지 않고서 코드를 작성하는 것.)으로 개발해야 한다. 막코딩으로 개발한 후에 조금 로직이 잡히는 것 같으면 그때 전체적으로 코드를 수정해야 하지 처음부터 기능을 구현하는데 예쁘게 코드를 작성하려고 힘을 쏟는다면 이는 너무 비효율적이다. 처음에는 막코딩으로 한 가지 기능을 구현하고 구현한 기능과 다른 기능들이 조금씩 자리가 잡히는 것 같으면, 그때 클린코드하여 안정적인 기능을 구현하면 된다.

즉, 내가 강조하는 것은 기능을 구현하는 것에만 초점을 두고 일단은 개발하라는 것이다. 이는 코딩 이외의 것은 신경 쓰지 않는다 와 비슷하다. 일단 구현하고자 하는 기능 이외의 것은 신경 쓰지 않고 기능이 조금 자리가 잡히는 것 같으면 그때 클린코드를 함으로써 완전하게 기능을 구현하라는 것이다.

마크업은 점차 체계적으로 작성한다

마크업을 최대한 체계적으로 작성한다

이는 클린코드를 할 때의 과정이며, 프로젝트의 마크업을 체계적으로 변경해야 프로그램에 CSS를 수정하거나 다시 마크업을 수정할 때 굉장히 편하게 수정할 수 있다. 나 같은 경우에는 마크업을 그냥 프로그램의 로직만 잘 굴러가면 됐지 왜 굳이 마크업까지 체계적으로 해야 해? 그냥 로직만 잘 동작하면 되는 거 아냐? 라고 생각하며 코딩했는데. 굉장히 큰 오산이었다. 마크업은 로직을 구성하는 것만큼 중요하다.

이는 처음에는 막코딩으로 기능을 구현한다 와 비슷하다. 마크업을 처음부터 작성하려 노력한다면, 기능 구현 시에 방해가 될 수 있다. 일단 처음은 마크업을 대충 작성하되, 자리가 잡히면(조금 기능이 구현되는 듯 싶으면) 마크업을 점차 체계적으로 바꾸라는 것이다. 위의 글 처럼 마크업은 프론트엔드에서 정말 중요하다. 마크업이 체계적일 수록 로직을 구현하는 데 있어 조금은 효율적이고 빠르게 기능을 구현시킬 수 있다.

코드의 형식으로 값을 표현하지 않는다

최대한 코드의 형식으로 값을 표현하지 않는다

만약 당신이 어떤 input 엘리먼트에서 입력하고 있는 값을 출력하고 싶다면 대략 이런 식으로 코드를 구성할 것이다.

const inputElement = document.querySelector('input');
const printElement = document.querySelector('div');
inputElement.addEventListener('keydown', e =>
printElement.innerHTML = e.target.value;
);

그런데 이 코드는 나중에 수정이 필요할 때 힘들어 질 수 있다.
만약 가져오는 값이 e.target.value 가 아니라 div 엘레멘트의 key 값 라면 어떻게 할 것인가? e.target.attributes.key.value 처럼 작성해야 하는데, 이같이 처음 볼 때는 뭔지도 모르겠는 코드로 표현된 값을 작성하게 된다면, 나는 나중에 알아볼 수도 있겠지만 다른 사람이 이 값으로 다른 기능을 추가하기도 한다면, 만약 그 사람이 자바스크립트를 잘 다룰 수 없다면 이 코드를 해석하는데 많은 시간이 소요할 수도 있을 것이다.

그렇지만, 당신이 e.target.attributes.key.value 라는 코드적인 값을 const divKeyValue = e.target.attributes.key.value 로 어떤 변수에 선언만 해준다면, 그 사람은 변수명을 읽고 이 값으로 다른 기능을 빨리 추가할 수 있을 것이다.

이 처럼 코드적인 값으로 많은 기능을 추가하고 선언하다 보다면 나도 헷갈릴 수도 있고, 협업의 과정에서도 어려움이 생길 수도 있다. 그러니 웬만하면 코드적인 값은 변수에 담아서 사용하는 것이 좋다.

이는 코드에 누구나 알아볼 수 있는 주석을 많이 작성해둔다 와 비슷하다. 코드의 형식으로 값을 표현하다 보면 코드를 쓰고 있는 그때만 그 값이 무엇을 의미하는 지 알 수 있으며, 나중에는 전혀 알 수가 없다. 그렇기에 누구나 알아볼 수 있는 형태로 값을 표현해야 한다.(값이 아닌 코드도 그렇게 표현해야 한다.)

최대한 사용자의 관점에서 바라보고 개발한다

최대한 사용자의 관점에서 바라보고 개발한다

개발은 내가 구현하고 싶은 로직을 구현하고 싶어서 개발하는 것이 아니다. 또 내가 편하게 스타일 로직을 구현하고 싶어서 쉽게 마크업을 구성하는 것은 개발이 아니다. 그것은 그냥 내가 구현하고 싶은 기능과 레이아웃이며 사용자를 위한 로직과 레이아웃이 아니다. 모든 기능과 레이아웃 들은 사용자를 위해 개발되어야 한다. 만약, 사용자를 무시한 채로 개발된다면 그 프로덕트는 성공하지 못할 것이다. 만약 그 프로덕트가 성공하였다고 해도 그것과 기능적인 측면은 비슷하지만 사용자 친화적인 다른 프로덕트로 사용자들은 언젠가 넘어갈 것이다.

여전히 전적으로 동의하는 부분이다. 정말 사용자의 관점에서 개발되지 않는 서비스는 언젠간 망하게 되어있다. 모든 서비스는 사용자의 관점에서 개발되어야 성공할 수 있다.

profile
Front-end developer

0개의 댓글