[Effective Kotlin] 아이템 28 : API 안정성을 확인하라

0

세상에 있는 자동차의 운전방법이 다르다면, 자동차를 운전하기 전에 모든 운전방법을 배야한다.
이처럼 일시적으로 사용되는 인터페이스를 배우는것은 굉장히 귀찮고 의미없다.

프로그래밍에서도 안정적이고 표준적인 API를 선호한다.

주요 이유는 다음과 같다.

  • API가 변경되고 개발자가 업데이트했다면, 변경에 대응하기가 곤란해진다.
    특히 다른 개발자가 API를 사용한 경우에는 익숙하지도 않아 더욱 어려울 것이다.
    개발자가 안정적인 라이브러리로 업데이트 하는것을 두려워하는것은 매우좋지 않은 상황이다.

  • 사용자가 새로운 API를 배워야 한다.
    새로 배운다는것은 꽤힘들고 고통스럽기 때문에 많은 사람이 이를 피하나, 오래된 지식때문에 보안문제가 발생한다.
    따라서 안정적이지 않은 모듈을 많이 공부하는 것보다 안정적인 모듈부터 공부해 두는것이 좋다.

하지만 좋은 API를 한번에 설계할수 없기때문에, 계속해서 API를 안정적으로 유지하기 위해 의견을 제시해야 한다.

일반적으로는 시멘틱 버저닝 방법(Major, Minor, Patch)을 사용한다.

  • Major : 호환되지 않는 수준의 API 변경
  • Minor : 이전 변경과 호환되는 기능을 추가
  • Patch : 간단한 버그 수정

Major를 올릴때는 Minor와 Patch를 0으로 돌린다.
Minor를 증가시킬땐 Patch를 0으로 돌려둔다.

베타버전이 오래 유지되는것을 싫어하는사람도 있지만,
이시기에 많은것이 바뀌기 때문에 가장 중요한 시기이기도 하다.

안정적인 API에 새로운 요소를 추가할때, 아직 해당 요소가 안정적이지 않다면,
다른 브랜치에 해당 요소를 두는것이 좋다.

또한 일부 사용자가 사용하게 한다면, Experimantal 메타 어노테이션을 붙이는것이 좋다.

@Experimental(level = Experimental.Level.Warning)
annotaion class ExperimentalNewApi

@ExperimentalNewApi
suspend fun getUsers() : List<User> {

}

이러한 요소는 언제든지 변경될수 있다.
하지만 실험적 기능으로 유지하는것을 두워하지 말라.

더오래동안 좋은 API를 설계하는데 도움이 된다.

안정적인 API의 일부를 변경야한다면, 전환하는데 시간을 두고 Deprecated 어노테이션을 활용하다.

@Deprecated
fun getUsers(callback : List<User> -> Unit)

또한 직접적인 대안이 있다면, `ReplaceWith를 붙여주면 더욱 좋다.

@Deprecated
ReplaceWith("getUsers()")
fun getUsers(callback : List<User> -> Unit)

이렇게 적용하고 난뒤, 사용자가 이러한 변경에 적용할 시간을 제공해야한다.
널리 사용되는 API는 이러한 적용시간을 몇년으로 잡기도 한다.

이러한 시간이 지난뒤,(major release)에서 이 요소를 제거하면 된다.

정리

안정적인 API를 사용하는것이 좋다.
그렇기에 모듈과 라이브러리를 만드는사람은 이들을 사용하는 사람들과 커뮤니케이션이 제일 중요하다.
또한 안정적인 API에 변경을 가할 때는 사용자가 적응할 시간을 충분히 줘야한다.


후담

예전에 저의 사수가 3년전 Deprecated된 AsyncTask를 쓰는걸 보고, 왜 구글은 Deprecated된것을 안 없앨까 생각했었는데, 막상 변화를 두려워하는 사용자가 있기에 냅두는것이라는것을 알게되었습니다.
최근 gitHub에 올라오는 라이브러리를 생각하시면 될것같아요.

profile
쉽게 가르칠수 있도록 노력하자

0개의 댓글