클린 코드에 대해서 많이 들어봤을 것이다. 그러나 개발자로서 왜 클린코드를 작성해야 하는지에 대해서 알고 있나? 많이 듣던대로 가독성과 유지보수를 위해서 라고 대답할 것 같다. 나 또한 그렇기 때문이다!
하지만 좀 더 심층적으로 알고 싶고 왜 클린 코드로 작성하면 유지보수가 쉬운지 클린코드를 어떻게 작성해야하는지 포스팅하려고 한다.
# 1. Clean Code
개발자가 갖춰야하는 능력 중 하나는 좋은 코드(클린 코드)를 쓰는 것이다. 이는 매우 중요하며 나쁜 코드를 쓰지 않는 것은 더더욱 중요하다. 왜 좋은 코드를 써야할까?
코드는 소프트웨어의 근본이기 때문이다. 이 근본이 나쁜 코드로 이루어져 있다면 곧 망가지고 만다. 이는 더이상 기능을 확장하거나, 수정할 수 없다는 의미이다. 소프트웨어는 의미 자체로 유연해야하며 이는 유지보수와 수정이 쉬어야 한다는 말이다. 따라서 나쁜 코드로 이루어져 있는 소프트웨어는 유지보수가 어렵고 이는 망가진 소프트웨어이다.
SI나 기능 구현이 급한 개발자는 좋은 코드를 포기하기도 하는데 이 결과는 안좋은 결과를 낳는다. 실제로 프로그램의 복잡도가 올라갈수록 코드 한 줄을 입력하거나 수정하는데 드는 시간은 점점 늘어난다고 한다. "출시하고 나중에 다시 고쳐야지" 라고 생각해도 실제로는 코드를 다시 볼 여유가 생기는 일은 대부분 일어나지 않는다고 한다... 주로 금융 앱이 버전업이 아니라 차세대 앱(새로운 앱)이 새로 나오는 이유인 것 같다,,
물론, 여기서 말하는 나쁜 코드는 "나중에 봤을 때 나쁜 코드" 를 의미하는 것은 아니다. 당시에는 React가 없었을 수도 있 고, 그 당시에는 최선이었던 방법이 시간이 흐름에 따라 현재는 적합한 방법이 아닐 수 있다는 것이다. 그때 최선이였던 코드는 비교적 마이그레이션하거나, 개편하기가 쉽다. 하지만, 애초에 나쁜 코드는 이러한 작업들을 불가능에 가깝게 만든다.
따라서, 개발자는 반드시 좋고 깨끗한 코드를 작성하기 위해서 노력해야 한다. 좋은 코드를 작성할 수 있는 능력은 개발자의 실력을 평가할 수 있는 요소 중 하나이기도 하다. 여태껏 개발자들은 좋은 코드를 작성하기 위한 방법과 원칙들을 공유해왔다. 이를 좀 더 알아보도록 하자!
# 2. 관심사 분리
개발에는 관심사의 분리(Seperation of Concerns)이라는 용어가 있다.
이는 좋은 코드를 짜기 위한 가장 기본적인 원칙이며, 더 좋은 애플리케이션을 만들기 위한 여러 디자인 패턴, 기법, 아키텍쳐 등은 결국 모두 이 SoC를 가장 기본적인 원칙으로 삼고 있다.
관심사란 무엇일까?
"관심사" 란 하나의 모듈이 수행하고자 하는 목적이다. 여기서 모듈이란 함수, 클래스 등의 단위로 해석할 수 있다.
따라서, "관심사 분리"란 각 모듈들이 한번에 여러 관심사를 처리하려고 하지 않고, 하나의 관심사만 처리하도록 분리하는 것을 의미한다.
## 2-1. 관심사를 분리하는 이유
관심사를 분리하면 모듈은 하나의 목적만 가지게 되고 이는 코드가 수정될 이유는 단 한가지만 존재한다는 것이다.
소프트웨어는 변화가능해야하며, 좋은 소프트웨어 일수록 기존의 기능을 수정, 확장하는 것이 용이해야한다. 즉 유연해야 한다.
우리는 이를 흔히 "유지보수"라고 한다.
관심사를 분리하는 이유는 소프트웨어의 특정 부분이 변경되는 이유를 한가지로 한정하여 수정을 용이하기 위해서 이다.
만약 여러 모듈들이 여러 관심사를 동시에 다룬다면 특정분야를 수정할 때 관련된 모든 모듈을 수정해야 할 것이다.
관심사 분리는 프로그래밍에서 가장 기본이 되는 원칙이며, 비슷한 개념을 표현하는 "단일 책임 원칙", "KISS" 라는 단어들이 생겨났다.
단일 책임 원칙(Single Responsibility Principle): 관심사의 분리와 유사한 개념이지만, 관심사란 표현 대신 책임이란 용어를 사용합니다. 각 모듈들은 책임(수행해야 하는 동작)을 가지고 있으며 각기 하나의 책임만을 가져야 한다는 원칙입니다.
KISS(Keep It Simple, Stupid): 각 모듈들은 간단하고, 단순하게 만들라는 의미로서 여러 기능을 포함시키면서 복잡하게 만들면 유지보수가 힘들어지기에, 하나의 기능만 수행하도록 하라는 의미입니다. SoC, SRP등의 원칙과 유사한 의미를 가지고 있습니다.
# 3. React의 관심사와 Custom Hook
리액트가 가진 관심사는 어떤 것일까?
리액트는 UI 구축을 위하 라이브러리로, 핵심적인 관심사는 UI와 UI를 변경시킬 수 있는 로직일 것이다.
이 중 UI는 실제 코드상에서는 JSX라는 형태로 표현되며, 로직은 유저의 입력에 대한 인터렉션, API를 호출 등이 있을 것이다.
React v16.8에서 Hook이 발표되었다. 이 전에는 React에서 컴포넌트를 선언합는 방법은 클래스 컴포넌트를 사용했으며, 현재는 함수 컴포넌트로 옮겨왔다. 많은 코드들이 함수 컴포넌트로 옮겨온 이유는 문법이 더 단순하고, 교착상태로 인한 버그가 발생하지 않는다는 장점도 있으며, Custom Hook의 편리함과 유용성을 가지기 때문이라고 생각한다.
Custom Hook을 통해서 관심사를 분리할 수 있다.
## 3.2 React에서 관심사를 분리하는 법: Custom Hook
커스텀 훅이란 무엇일까?
커스텀 훅은 리액트가 기본적으로 제공해주는 훅들을(useState, useEffect 등) 이용해서 만든 함수이다.
다만, 컴포넌트 안에서 쓰는 함수라고 해서 모두 커스텀 훅은 아니다. 만약 함수의 인자로 setState를 받아서 내부에서 setState를 사용하고 있다면 그 함수는 custom Hook이란 걸까? 정답을 말하면 x이다. 왜냐하면 인자로 setState를 받지 않는다면 평범한 함수가 되기 떄문에 이것은 일반함수다.
로직은 UI를 변경시키기 위함이고, 함수형 컴포넌트에서 로직은 대부분 useState, useEffect 등의 Hook을 통해서 구현된다.
컴포넌트 내부에서 훅을 통해 state를 선언하고 effect를 발생시킬 수 있지만, 컴포넌트 내부에 많은 로직들이 들어가게 되면 컴포넌트가 복잡해진다. 또한 동일한 로직들을 여러 컴포넌트에 걸쳐서 재사용하기 힘들다는 단점이 있다.
일적반으로 동일한 로직이 보일경우 함수로 추출하듯이, 리액트에서도 Hook들을 이용한 동일한 로직들을 별도의 함수로 추출해서 여러 컴포넌트에 걸쳐서 사용하고자 하는 시도가 있었고 결국 커스텀 훅이란 기법을 만들게 되었다고 한다.
커스텀 훅의 조건은 다음 2가지를 만족해야 한다.
- React의 Hook들을 호출하는 함수여야 한다.
- 함수의 이름은 use로 시작해야 한다.
아래 코드는 커스텀 훅 예시이다.
import { useState } from "react";
import "./styles.css";
export default function App() {
const [isLightMode, changeMode] = useToggle(true);
return (
<>
<h1
style={{
backgroundColor: isLightMode ? "white" : "black",
color: isLightMode ? "black" : "white"
}}
>
current mode: {isLightMode ? "Light Mode" : "Dark Mode"}
</h1>
<button onClick={changeMode}>change mode</button>
</>
);
}
// useToggle 커스텀 훅
const useToggle = (defaultValue) => {
const [toggle, setToggle] = useState(defaultValue);
const changeToggle = () => {
setToggle((prev) => !prev);
};
return [toggle, changeToggle];
};
'프로그래밍에 대한 얕고 넓은 지식 쌓기' 카테고리의 다른 글
서버와 클라우드 컴퓨팅 그리고 AWS (0) | 2023.04.30 |
---|