리팩터링 Chapter 2

·2021년 11월 22일
0

REFACTORING

목록 보기
1/2

Refactoring :

  • [명사] 소프트웨어의 겉보기 동작은 그대로 유지한 채, 코드를 이해하기 수정하기 쉽도록 내부 구조를 변경하는 기법
  • [동사] 소프트웨어의 겉보기 동작은 그대로 유지한 채, 여러 가지 리팩터링 기법을 적용해서 소프트웨어를 재구성하다

"리팩터링하다가 코드가 깨졌다" 고 하면 그것은 리팩터링이 아니다

Chapter 2 리팩터링 원칙

코드베이스를 정리하거나 구조를 바꾸는 모든 작업을 재구성(Restructuring)이라고 표현하며, 리팩터링은 재구성 중 하나의 형태로 본다
겉보기 동작을 그대로 유지 한다는 것은 리팩터링하기 전과 후의 코드가 똑같이 동작해야 한다는 것을 뜻한다. 따라서 리팩터링을 하는 동안에는 코드가 항상 정상 작동하여야 한다

리팩터링하는 이유

  • 소프트웨어 설계가 좋아진다
  • 소프트웨어를 이해하기 쉬워진다
  • 버그를 쉽게 찾을 수 있다

따라서 프로그래밍 속도를 높일 수 있다

설계 지구력 가설 Design Stamina Hypothesis

리팩터링을 하는데 시간이 들기 때문에 전체 개발 속도가 떨어질 것이라고 생각할 수 있지만, 새로운 기능을 추가할 수록 기존 코드베이스에 녹이기가 어려워지고, 버그가 발생할 일이 잦아지며 점점 코드를 파악하기가 난해해진다.

하지만 내부 설계가 잘 된 소프트웨어는 새로운 기능을 추가할 지점과 어떻게 고칠지를 쉽게 찾을 수 있다. 이렇게 내부 설계에 심혈을 기울이면 소프트웨어의 지구력이 높아져서 빠르게 개발할 수 있는 상태를 더 오래 지속할 수 있다.

처음부터 좋은 설계를 마련하기는 어려우니 빠른 개발이라는 목표를 달성하려면 리팩터링이 반드시 필요하다

리팩터링 언제 할까

3의 법칙 (3진 리팩터링)

  1. 그냥 개발한다.
  2. 비슷한 일을 두 번째로 하게되면.. 일단 계속 한다
  3. 또 같은 일을 세 번째 하게 되면 이제 리팩터링을 한다.

준비를 위한 리팩터링 Preparatory Refactoring : 기능을 쉽게 추가하게 만들기

새로운 기능을 추가하기 직전, 코드의 구조를 살짝 바꾸면 다른 작업을 하기가 수월해지는 부분을 찾아 리팩터링

동쪽으로 100km를 이동하려는데 그 사이에 숲이 가로막고 있다면, 좀 둘러가더라도 20km 북쪽에 있는 고속도로를 ㅍ타는 편이 세 배나 빠를 수 있다. 다들 "직진!"을 외칠 때, "잠깐, 지도를 보고 가장 빠른 경로를 찾아보자" 라고 말할 줄 알아야 한다. 준비를 위한 리팩터링이 이런 역할이다.
Jessica Kerr

이해를 위한 리팩터링 Comprehension Refactoring : 코드를 이해하기 쉽게 만들기

코드를 파악할 때, 이해한 내용이 더 잘 나타날 수 있도록 리팩터링

쓰레기 줍기 리팩터링 Litter-Pickup Refactoring : 비효율적인 코드를 깔끔하게 만들기

코드를 파악하다가 비효율적으로 처리하는 모습을 발견했을 때 리팩터링(이해를 위한 리팩터링의 변형)

계획된 리팩터링과 수시로 하는 리팩터링

기능을 추가하거나 버그를 잡는 동안에 수시로 리팩터링을 할 수도 있고, 리팩터링에 소홀했다면 따로 시간을 내서 리팩터링을 할 수도 있으나 기회가 될 때 마다 하는 것이 좋다

코드 리뷰에 리팩터링 활용하기

코드 리뷰를 할 때 리팩터링을 해 보는 것. 특히 리뷰어와 코드 작성자가 pair programming 하는 것이 가장 좋다.

리팩터링을 하지 말아야 할 때

  1. 굳이 수정할 필요가 없을 때
  2. 차라리 새로 작성하는 게 쉬울 때

리팩터링 시 고려할 문제

새 기능 속도 개발 저하

리팩터링의 본질은 코드베이스를 예쁘게 꾸미는데 있는 것이 아니라 개발 기간을 단축하고자 하는 것이다.

코드 소유권

클라이언트에 영향을 주지 않고 원하는 형태로 변경하기엔 제약이 따르며 인터페이스가 복잡해진다. 그래서 코드소유권을 팀 단위로 두거나 오픈소스의 방식을 사용하는 것이 좋다.

브랜치

마스터 브랜치와 기능별 브랜치가 분리된 상태로 작업하는 기간이 길어질수록 마스터로 통합하기가 어려워진다. 따라서 기능별 브랜치의 통합 주기를 최대한 짧게 해야하며, 이 방식을 지속적 통합(Continuous Integration)이라고 한다.

테스팅

겉보기 동작을 유지하기 위해서 테스트 코드가 필요하다. 테스트코드는 통합 과정에서 발생하는 의미 충돌을 잡는 메커니즘으로 활용할 수 있어서 자연스럽게 CI와도 밀접하게 연관 된다. 이는 지속적 배포(Continous Delivery)의 핵심이기도 하다.

레거시코드

테스트코드의 보강이 필요

데이터베이스

프로덕션 환경에 여러 단계로 나눠서 릴리즈하는 것이 좋다는 점에서 다른 리팩터링과 차이를 보인다

  1. 필드 추가(사용 X)
  2. 기존 필드와 새 필드가 동시에 업데이트 되게 설정
  3. 데이터베이스를 읽는 클라이언트들을 새 필드를 사용하는 버전으로 점진적 교체
  4. 기존 필드 삭제

리팩터링, 아키텍처, 애그니(YAGNI)

You are not going to neet it - 간결한 설계(Simple degisn), 점진적 설계(Incremental design)
미래를 추측하지 않고, 현재까지 파악한 요구사항만을 해결하는 소프트웨어를 구축하되 최대한 멋지게 해결하도록 한다.
진행하면서 요구사항을 더 잘 이해하게 되면 리팩터링을 한다.
필요할 것 같아서 미리 구현해둔 기능 상당수가 결국 전혀 쓰이지 않거나, 미래의 요구사항을 제대로 반영하지 못하여 수정이 더 어려워 지는 경우가 많다

리팩터링과 성능

리팩터링은 이해하기 쉬운 코드를 위해 성능이 느려지는 방향인 경우가 많다. 하지만 성능을 튜닝하기가 쉬워지기 때문에 오히려 성능이 좋아진다.
대부분 프로그램은 극히 일부에서 대부분의 시간을 소모하기 때문에 전체적인 코드의 최적화 보다는 문제가 있는 부분을 최적화 하는것이 효과적이다. 따라서 리팩터링을 잘 되어 있다면 시간을 많이 소모하는 부분을 찾기가 수월해지기 때문에 튜닝하기가 쉬워지는 것.

Chapter 2를 읽고나서

리팩터링을 하는 이유에 대해서는 책을 읽기 전에도 대략 이러이러 할 것이라는 것을 예상하였고 내가 생각한 부분과 맞아 떨어졌다.

그런데 리팩터링을 언제 해야 할까에 대한 생각은 미처 하지 못했었는데 책에서 얘기한 내용에 따르면 코드를 파악 할 때가 반복해서 언급이 되었다. 그래서 내가 봤을 때는 리팩토링을 할 때를 여러가지로 나눠서 설명을 하였지만 다 하나로 귀결되는 것으로 보인다. 바로 리팩토링을 해서 코드가 더 좋아질 때
그렇다면 좋은 코드는 어떤 코드인가에 대해 물음표가 남지만 지금까지 읽은 내용으로 봤을 때 차차 설명해 줄 것으로 보인다.

코드를 새로 작성하는 게 더 쉬울 때는 리팩터링을 하지 말라고 쓰여져 있는데 책의 저자도 새로 작성하는 게 더 쉬울지 리팩터링을 하는 것이 쉬울지 해보지 않는 이상 판단하기가 쉽지 않다고 하였다. 이는 더 많은 경험과 판단력이 필요하다고 하는데 나에게는 아직 먼 이야기로 보인다

이 챕터에서는 계속해서 테스트코드의 중요성을 강조하고 있다. 지금까지 테스트코드를 따로 작성하지 않고 개발을 했는데.. 지금이라도 잘 하면 되니까..!! 테스트코드를 습관화 해야겠다. 뒷 장에 테스트 구축에 관한 내용이 도움이 많이 되기를 희망한다.

이 챕터를 읽으면서 가장 인상적이 였던 부분은 이해하기 쉬운 코드를 위해 어느정도 성능을 희생하는 리팩터링이 자주 이루어진다는 것이다.
개인적으로 개발 할 때 필요할 것 같은 기능들을 생각하며 확장성을 고려하며 코드를 짜려고 고민하는 편인데 현재까지 파악한 요구사항만 잘 해결하면 된다고 하니 신박했다.
또한 가독성을 위해 성능을 어느정도 희생한다는 부분은 내 고개를 갸우뚱 하게 했으나 오히려 그 것이 전체적인 성능을 향상 시킨다는 내용이 뒤통수를 세게 맞은 느낌이 들었다.

아직까지 나의 생각의 범위가 넓지 않다는 것을 다시 한번 체감할 수 있었으나 좋은코드의 실루엣을 살짝 엿본 기분이라 앞으로 나아갈 가능성이 많이 남아있다는 것에 설렌다.
옛날에 영어 공부할 때 이런 느낌이 드는 순간이 있었는데 오랜만에 느끼는 공부의 설렘이다
(학교 다닐 때 그랬으면 참 좋았을 텐데)

이 책은 주니어 개발자 들에게는 필독서가 아닐까 생각해본다

profile
You only get one life. It's actually your duty to live it as fully as possible.

0개의 댓글