auto optimize import : preferences > Editor > General > Auto import > Optimize imports on the fly

usages(사용수를 보여줌) : preferences > Editor > Inlay Hints > Java > Code vision > Usages

2,3년전부터 은퇴에 대한 두려움이 생겼다.

회사를 짤리면 어떻하지.. 나이먹고 아프면 어떻하지.. 아이 학비는.. 언젠가 회사를 그만두게 될텐데 그러면 무슨돈으로 생활하지.. 등등

어떤 책에서 은퇴를 하려면 구체적으로 얼마가 필요할지 계산해보라는 내용을 읽었고, 계산을 해보니 30억 정도가 필요해 보였다. 현재 내나이에 10년정도 일을 더 할 수 있다면 맥스일텐데 30억을 모으기는 도저히 불가능해 보였다. 17,8년을 일을 하면서 모은돈을 생각해 봤을때 정말 택도 없는 금액이었다.

그러면서 투자에 대해 고민하게 되었고, 투자말고는 방법이 없어보였다. 그리고 투자를 시작했다. 

 

2010년 결혼 4년차 아들이 태어나면서 안정적인 주거에 대한 필요가 생겼고, 부동산 시세와 관계없이 살기 좋은 곳으로 주택을 마련했다. 살기 좋은 곳에 대한 우리의 기준은 당시 맞벌이 였기 때문에 아이를 돌봐줄 수 있는 부모님 댁 근처, 출퇴근이 편한 역세권 이 두가지가 가장 큰 기준이었던것 같다.

비록 2/3는 대출이고 22평의 작고 낡은 아파트였지만 전세에서 자가로 바뀌면서 느껴지는 안정감은 생각보다 훨씬 더 컸던것 같다. 당시 대출이자가 지금에 비하면 엄청 높았지만, 맞벌이 였기 때문에 큰 부담은 없었다. 후에 아내가 회사를 그만두고 외벌이를 하게 되었지만, 금리가 내려가 낮은 이율로 대출을 갈아타면서 이자부담이 줄어 들었고, 아내가 재택근무로 할수 있는 일을 하게되어 내 심적인 부담도 줄어들었었다. 

아들이 점점 자라서 초등학교를 입학할때가 되다보니 좀 더 넒은집이 필요해졌고 새아파트로 가고 싶은 생각이 들어 청약을 알아보게 되었고, 몇 군데 모델하우스를 둘러보고 청약에 당첨되었고 2018년 새집에 입주하게 되었다. 

이때부터 자연스럽게 투자에 대해 조금씩 관심이 생기기 시작했다. 살고 있던 집이 점점 가격이 올라가고 있었고 입주할때쯤에는 매매가가 두배쯤 올라 있었다. 분위기는 좀 더 올라갈것 같았고, 입주시점에 기존집을 매도하지 않고 일시적 2주택비과세로 가져가기로 하고 전세를 주었다. 당시에는 일시적 2주택 비과세기준이 3년내 양도 였기 때문에 3년동안 더 보유할 수 있었다.

 

2019년부터 은퇴에 대한 불안함이 생기고 양도 차익이 많지는 않았지만 그래도 평생 처음으로 여유자금이란 것을 가지게 되다보니 투자에 더 많은 관심을 가지게 되었다. 주식은 한번 실패한 경험이 있어, 부동산 투자가 더 끌렸던것 같다. 부동산 투자로 방향을 정하고 강의를 듣고 관련책을 사서 보고 임장을 다녔다. 2020년부터 코로나로 인해 부동산을 간다거나 집을 본다거나 할수는 없었고, 차안에서나 도보로 주변을 둘러보는게 임장의 전부 였지만, 와이프와 함께 다니면서 맛있는 것도 사먹고 투자를 한다는 새로운것에 대한 도전으로 재미도 있었던것 같다. 이때부터 은퇴에 대한 불안함도 조금씩 줄어들었다.

 

2020년 입주후 2년이 되는 시점에 기존 집을 매도하기로 결정하고 4월에 계약하고 6월말에 잔금을 치뤘다. 10년을 갖고 있던 집이지만 3,4년 사이에 엄청올라 매수금액보다 2.5배 정도 올라 있었다. 매도 후 1년사이에 처음 매수했던 금액만큼 더 올라 있었지만 아쉽다기 보다는 참 놀라운 경험이었던거 같다. 

그 돈을 시드머니로 새로운 투자처를 찾기위해 강동, 일산, 의정부, 평촌, 분당, 김포, 부천, 울산등을 둘러보았다. 다른곳은 너무 비싸서 엄두가 안나고 결과적으로 기존 집 계약 후 잔금 치루기 전 5월에 비조정지역이었던 일산과 의정부의 분양권을 매수했다. 김포도 하나더 살까 하다가 일산과 지역이 겹치고 검단의 공급량으로 인해 한동안은 안오를것 같다고 판단했다. 완전한 오판이었다.

잔금은 기존 집 잔금일 이후로 계약을 했는데 그 사이에 6.17 대책이 나오면서 일산과 의정부가 조정지역으로 변경되어 중도금 대출이 안될 위기에 처했고, 입주기간이 많이 남은 일산은 잔금 일정을 당겨서 6/18에 잔금을 치뤄 중도금 대출을 받고, 의정부는 입주기간이 얼마남지 않았기도 해서중도금 대출을 받지 않고 기존 집 매도후 남은 잔금과 신용대출을 이용해서 겨우 잔금을 치룰 수 있었다.

 

2020년말 의정부가 입주를 시작했고 전세로 세를 놓았지만, 생각보다 쉽게 전세가 빠지지 않았고, 마음은 점점 조급해져가고 있는데 부동산에서는 월세는 생각이 없느냐고 물어왔다. 아내와 고민을 해보고 취득세 중과때문에 어차피 더이상 투자는 힘들것이라 생각되어 월세를 놓기로 결정하고 그후로 얼마나 후회를 했는지 모른다. 아파트가 아니라고 해도 오피스텔, 지산, 상가등 투자처는 많았고 난 돈이 없을 뿐이었다.

 

2021년 일산, 의정부, 현재 사는집까지 모두 오르고 있는데 실제 수중에 들어오는 돈은 없고 일산까지 등기치게되면 종부세도 부담이 될것 같고 팔자니 양도세가 너무 많았다. 결국 난생처음으로 세무상담이란것을 받아봤다. 상담 결과는 일시적 2주택 비과세에 초점이 맞춰졌고, 일산 등기후 의정부를 팔면 일시적 1가구 2주택 비과세가 가능하여 의정부, 현재 집, 일산 순으로 매도를 하고 똘똘한 한채로 가기로 결정하였다. 하지만 의정부가 월세로 되어 있어 매도가 안될것 같았다. 다 포기하고 다주택자로 버텨보기로 했다.

 

2021년말 의정부 세입자한테서 연락이 왔다. 내년 1월에 분양받은 집으로 입주를 해야 해서 집을 빼야 한단다. 너무 기뻤다. 드디어 의정부를 팔 수 있게 되었구나. 하지만 세상일은 그렇게 쉽게 흘러가지 않았다. 11월 3주택에서 한채 매도후 일시적 1가구 2주택에 대한 유권해석이 기재부에서 나왔고, 결국 계획했던대로 진행할 수는 없었다. 다시 고민이 시작됐고 새로운 플랜을 세웠다. 의정부를 팔더라도 일산이 비조정지역이었기 때문에 3년내에 현재집을 팔면 일시적 1가구 2주택이 가능하다는 것을 알게 되었다. 일산 등기 후 의정부를 1년내에 매도하고, 현재 집을 최종 1주택 조건에 맞춰 2년을 더 가지고 있다가 일산 등기 후 3년이 되기전에 팔기로 플랜을 세웠다.

의정부를 매도로 내놨지만 갑작스런 거래절벽으로 집을 보러 오는 사람이 없다. 일산 비과세를 위해서는 입주를 해야 하는데 아내가 아들 초등학교 졸업전에는 일산으로 갈 수 없다고 하여 등기 1년후 입주를 하기로 하고 단기 임대 월세를 주었는데.. 의정부가 팔려야 내년초에 잔금을 치룰 수 있다 그런데 거래 절벽 ㅎㅎㅎ 

이제 내년 잔금을 어떻게 치룰지 대책을 마련중이다. 빨리 의정부가 팔리길 기도하고 있다.

참 쉽지가 않네.

 

일산과 의정부의 분양권을 산것은 아무런 전략없이 돈이 부족하다보니 투자금이 적게 들어가는 비조정지역 분양권을 산거였는데 일산의 경우는 비과세까지 가능하게 되어 참 운이 좋았던것 같다. 좋은 부동산중개사를 만난것도 행운이었다. 일산과 의정부가 동일한 조건이었는데 일산의 경우는 부동산에서 잔금일을 당기도록 조언도 해주고 매도자와 협의도 해줘서 비조정일때  잔금을 치룰수 있었고 이로인해 많은 이득을 볼 수 있게 되었다.

 

사람이 참 간사한게 투자를 처음 시작할때는 양도세는 어차피 번거에서 내는거니 양도세를 낼 수 있으면 좋겠다 생각했었는데 내야할 세금이 내 수중에 들어오는 돈보다 많아지니 세금을 어떻게 줄일 수 있을지를 고민하게 되더군. 

 

짧은 경험과 두번의 상담 결과 자산이 어느정도 수준에 이르기까지는 일시적 1가구 2주택 비과세를 잘 활용해야 할 것 같다

 

은퇴를 고민하게 되며 투자를 시작하게 된건 참 다행인것 같다. 그리고 그동안 열심히 살아왔던것도 잘 한일 같다. 어느정도 수준의 근로소득이 있었기 때문에 투자도 할 수 있었던 것이라 생각한다. 지금은 투자와 근로소득(일) 의 균형을 맞추며 일을 할 수 없을때까지 즐겁게 두가지를 병행할 수 있을것 같다.

 

투자를 부부가 같이 한다는 것도 중요한 것 같다. 내가 신경을 쓸 수 없는 근무시간에는 아내가 주로 투자와 관련된일을 하고, 매수/매도에 대한 결정을 할때는 아내와 논의해서 결정할 수 있고, 임장도 같이 갈 수 있고 어떤 일을 아내와 한다는 것이 가끔은 전우애 같은것을 느끼기고 했던것 같다. 

 

내 관점에서 쓰다보니 후에 기억력이 줄어들때쯤 이글을 내가 다시 본다면 투자를 내가 한것처럼 느낄지도 모르겠다. 아니다 속지마라 모든 투자의 주는 아내였고 나는 부였다.

 

아직 은퇴를 위한 목표 금액을 다 모으지 못했지만 은퇴까지 남은 기간동안 목표달성을 위해 계속 투자할 것이다

스톡옵션을 행사하며 알게 된 사항들을 정리함

국내의 경우는 다를지도 모름

 

스톡옵션의 단계

  • grant(부여) -> vest -> exercise(행사) -> 양도

행사

  • 행사시점부터 세금을 내도록 되어 있고 예전에는 을종근로소득이라 불렸으나 현재는 갑종과 을종을 구분하지 않는듯 보임.
  • 어쨌든 근로소득이라 근로소득세를 내야 함
  • 근로소득세 = (행사시점의 가격 - 부여시점의 가격) * 베스팅 수 * 과세율
  • 행사시점의 가격은 행사 시점에 회사에서 알려줌
  • 세금 신고 시점 및 방법
    • 행사 후 다음 해 5월 개인이 신고
    • 납세 조합을 통한 세금신고
      • 행사 후 익월 5일까지 세금 납부 시 5.5% 를 공제해 줌
      • 다음 해 연말정산에 포함됨
      • 비용발생 : 만원(납세조합에 따라 다를지도 모름)

양도

  • 해외주식 양도세 22%(양도세 + 주민세)
  • 양도세 = (시가 - 행사가) * 매매 주식 수 * 0.22
  • 양도 다음해 5월까지 개인 세금 신고
  • 양도세는 납세조합을 이용할 수 없음

 

 

패턴 및 설계상의 일반적인 의사 결정

  • 적절한 마이크로서비스 경계 설정
    • DDD의 Bounded Context 개념
    • Bounded Context는 일반적으로 결합도가 낮으며, 때로는 아예 연결돼 있지 않기도 한다. 하나의 마이크로서비스에 대응 가능
    • 조직 구조도에 내재된 문제가 없다면 조직구조도에 따라 Bounded Context를 설정하는것이 현실적으로 가장 단순한 방법
    • 하향식 도메인 분해도 Bounded Context를 도출하는데 도움이 된다.
    • 마이크로서비스의 경계를 설계하는 가장 실용적인 방법은 가능한 여러가지 선택사항에 대해 서비스 리트머스 테스트를 했던 것처럼 손으로 시나리오를 돌려보는 것이다
      • 자율적인 기능 : 입력을 받아 내부의 로직과 데이터로 계산해서 결과를 반환
      • 암호화 엔진, 알림엔진 같은 유틸리티 기능이 적합
    • 배포단위의 크기 : 관리할 수 있는 수준 이내로 유지할 수 있어야 함
    • 분리하기에 가장 적합한 기능 또는 서브도메인
      • 자원소모량, 소유비용, 비즈니스 효용성, 유연성 등이 분석 기준
    • 폴리글랏 아키텍처
    • 선택적 확장 : 모든 기능 모듈이 모두 동일한 수준의 확장성을 필요로 하지는 않는다
      • 확장에 관한 요구사항을 기준으로 마이크로서비스의 경계를 결정
    • 작고 애자일한 팀
      • 전체 중에서 서로 다른 일부를 개발하는 데 집중할 수 있는 작고 집중력 있는 팀 구성을 통해 애자일 방식의 개발을 가능하게 해준다
    • 단일 책임
      • 책임을 비즈니스 범위 또는 하나의 기술 범위로 치환해서 생각하는 것이 더 현실적임
      • 하나의 마이크로서비스는 여러가지 책임을 담당해서는 안 된다
    • 복제가능성과 변경 가능성
      • 마이크로서비스가 전체 시스템에서 최소한의 재작성 비용 투입만으로 쉽게 떼어져 나올 수 있는지를 기준으로 식별돼야 한다.
    • 결합과 응집
      • 기능분해도는 의존관계트리와 함께 마이크로서비스의 경계를 수립하는데 도움을 줌
      • 트랜잭션 범위가 하나의 마이크로서비스의 범위를 넘어서 여러 마이크로서비스에 걸치지 않게 하는 것도 중요
      • 이벤트를 입력으로 받아 내부적으로 몇개의 함수를 호출하고 최종적으로 새로운이벤트를 반환하는 방식으로 반응하는 것이 기본
    • 마이크로서비스를 하나의 제품으로 생각하기
  • 통신 방식 설계
    • 먼저 요청-응답 동기방식으로 시작해서 나중에 필요하다고 판단될 때 비동기 방식으로 리팩터링
  • 마이크로서비스 조립(composability)
    • 오케스트레이션(orchestration) 방식과 연출(choreography)방식이 있음
    • 여러개의 서비스를 모아 하나의 완전한 기능을 만들고 오케스트레이터가 중앙의 두뇌 역할 담당
      • SOA에서는 ESB가 담당
    • 연출방식은 이벤트 생산자가 이벤트를 생상하고 소비자가 대기하고 있다가 소비하는 방식
    • MSA에서는 연출방식이 더 적합하지만 모든 사례에 연출방식으로 모델링하는 것은 불가능 함
  • 마이크로서비스 하나에 얼마나 많은 종단점을 둘 것인가?
    • 종단점의 수는 중요한 결정 사항이 아니다. 하나의 마이크로서비스는 하나 또는 그 이상의 종단점을 가질 수 있다. 마이크로서비스 크기에 적합하게 경계지어진 컨텍스트를 적절하게 설계하는 것이 훨씬 더 중요
  • 가상머신 하나당 하나의 마이크로서비스 또는 다수의 마이크로서비스?
    • 가상머신이 최대 사용치를 기준으로 두 걔의 서비스를 운영하기에 용량이 부족한가?
    • SLA를 충족시키기 위해 서비스들이 별도로 처리돼야 하는가?
    • 자원 요구사항이 서로 충돌되지는 않는가?
    • 3가지 질무에 No라고 답할 수 있다면 가능하지만 서비스들이 서로 어떤것도 공유하지 않으며, OS 프로세스와 독립적으로 실행된다는 점이 보장돼어야 함
  • 룰 엔진 공유 또는 내장?
    • 룰 엔진은 생산성을 높이고, 룰, 사실정보, 용어의 재사용을 가능하게 하며, rete알고리듬을 통해 룰을 더 빨리 실행할 수 있게 해준다
    • 룰이 단순하고 수적으로도 적고 서비스의 경계 내에서만 사용되며 룰 작성이 외부의 비즈니스 사용자에게 공개되지 않는다면 코딩하는것이 더 나을 수 있음
    • 룰이 복잡하고 서비스 컨텍스트에 국한되며 비즈니스 사용자에게 부여되지 않는다면 서비스 내부에 내장된 룰 엔진을 두는 편이 더 낫다
    • 룰이 비즈니스에 의해 작성되고 관리되거나, 룰이 복잡하거나, 룰이 서비스도메인 외부에서도 재사용된다면 외부에 있는 중앙저장소와 시스템 내부에 내장된 실행 엔진을 사용하는 것이 좋다
  • BPM의 역할과 작업흐름
    • 시스템과 사람의 상호작용을 자동화함으로써 전 구간의 여러기능에 걸쳐있는 비즈니스 프로세스를 모델링하는 상황에서 여러개의 마이크로서비스를 조합하는 상위 수준에서 사용가능
  • 마이크로서비스가 데이터 스토어를 공유할 수 있는가?
    • 공유데이터 모델, 공유 스키마, 공유테이블은 좋지 못한 방법이며, 마이크로서비스 개발을 재앙으로 이끌수도 있다
  • 서비스 종단점 설계 고려 사항
    • 계약설계
      • KISS(keep it simple stupid) : 더 나은 양질의 서비스를 더 빠르게 구축하고 유지 관리와 교체에 드는 비용을 줄여준다. YAGNI(you ain't Gonna need it). 단순함 중시
      • 소비자 중심 계약(Consumer Driven Contracts) : 사용자가 원하는 기대 사항을 서비스 제공자에게 테스트 케이스의 형태로 제공하게 함으로써 서비스 계약이 변경될 때마다 서비스 제공자가 통합테스트할 수 있게 해준다
    • 프로토콜 선택
      • 메시지지향서비스 : JMS/AMQP 프로토콜로 json 데이터 교환, 처리시간이 오래걸리는 작업에 적합
      • HTTP : 호환성, 프로토콜 처리, 트래픽 라우팅, 로드 밸런싱, 보안시스템등에 적합
      • REST : MSA 기본 선택 옵션, 
      • 최적화된 통신 프로토콜 : Avro, Protocol Buffers, Thrift 성능은 높이고 호환성은 떨어지게 됨
    • API 문서화 : Swagger, RAML, API Blueprint
  • 공유 라이브러리 처리
    • 자율성과 자기완비성 원칙을 준수하기 위해 코드와 라이브러리를 복제해야 하는 상황이 있을 수 있다
    • 비즈니스 범위나 분류관점에서 봤을때 하나의 마이크로서비스로 분류되지 않는 부분을 공통이라는 이유만으로 별도의 마이크로서비스로 떼어낸다면 효용보다 복잡성 증가라는 비용이 더 클 수도 있다
  • 마이크로서비스에서 API게이트웨이 사용
    • 서버는 화면까지 제공하기보다 RESTful서비스를 노출하는 방식으로 개발
    • 계약에 대한 기대사항의 불일치, 하나의 페이지를 렌더링하기 위해 서버에 여러번의 요청을 날리는 문제점이 있음
    • 해결방안
      • HATEOAS방식으로 최소한의 정보만을 링크정보와 함께 전달
      • 클라이언트가 요청 시 쿼리 문자열로 필요한 필드를 지정해서 요청
      • 간접화 개념 사용, 클라이언트와 서버 사이에 있는 게이트웨이 컴포넌트가 데이터 소비자의 명세에 따라 데이터를 변환
    • API 게이트웨이를 사용하는 목적에 따라 선택이 달라짐
      • 리버스 프록시 용도 : Apigee, Mashery 같은 서비스를 공유되는 플랫폼으로 사용
      • 트래픽 유형에 따른 세부적인 제어가 필요하고 복잡한 데이터 변환이 수반된다면 서비스당 독자저인 API게이트웨이 사용
  • ESB 및 iPass와 마이크로서비스의 사용
    • ESB의 역할
      • MSA에 적합하게 기능이 제한된 ESB역할은 API 게이트웨이로 대체
      • 오케스트레이션 역할은 ESB 버스에서 마이크로 서비스로 이동
      • 프로토콜 중재 역시 더 범용적인 메시지 교환 방식사용으로 필요하지 않음
      • 레거시 시스템과 연결해주는 어댑터 기능은 서비스 스스로가 구체적인 구현체를 제공하므로 필요 없음
      • 엔터프라이즈 수준에서 레거시와의 통합과 솔루션 회사의 애플리케이션을 통합하는데 존재 가치가 있음
  • 서비스 버저닝 고려사항
    • 시맨틱 버전이 널리 사용됨
      • 메이저, 마이너, 패치의 세가지 컴포넌트로 구성
      • 메이저 : 호환이 안될수도 있는 대규모 변경
      • 마이너 : 하위 호환을 유지하는 한도 내에서의 변경
      • 패치 : 버그수정
    • REST 버저닝 방식
      • URI 버저닝 : 대부분이 사용
      • 미디어 타입 버저닝
      • 커스텀 헤더
  • 크로스 오리진 설계
    • 마이크로서비스에서는 서비스가 동일한 호스트나 동일한 도메인에서 운영된다는 보장이 없음
    • 신뢰하는 다른 도메인으로부터의 크로스오리진 요청을 모든 마이크로서비스가 허용하게 하는 것
    • 클라이언트가 신뢰하는 도메인에 API 게이트웨이를 두는 것
  • 공유 참조 데이터 처리
    • 상대적으로 정적이고 변경될 가능성이 전혀 없는 데이터는 각 서비스에서 하드코드로 관리
    • 공통으로 사용되는 데이터를 별도의 마이크로서비스로 분리
    • 데이터를 모든 서비스에 복제
    • 필요한 데이터를 로컬에 캐시
  • 마이크로서비스와 대규모 데이터 작업
    • 데이터가 생성될때 사전 집계
    • 배치 API

 마이크로서비스의 과제

  • 데이터 섬
    • 마이크로서비스를 적용하면 데이터가 파편화돼 이질적인 데이터 섬으로 구성되는 상황을 맞이하게 됨
    • 데이터웨어하우스 : 배치성
    • 데이터 호수 : 하둡, NoSQL등을 이용한 준 실시간 처리
    • 데이터 호수의 경우 데이터의 사용목적을 가정하지 않고 그대로 저장
    • 데이터 전송 방안
      • 데이터 처리상황이 발생할 때 이벤트 발송
      • 스프링 데이터 플로우, kafka, flume등 사용
  • 로깅과 모니터링
  • 의존관계 관리
    • 서비스 경계를 적절하게 설정해서 의존성을 낮춰라
    • 의존성을 가능한 느슨하게 설계해서 변경에 의한 영향을 낮춰라. 또한 비동기 통신방식을 통해 서비스 간 상호작용이 일어나게 설계하라
    • 서킷 브레이커 같은 패턴을 사용해서 의존성 문제의 전파를 차단하라
    • 의존 관계 그래프 같은 시각화를 통해 의존 관계를 모니터링하라
  • 조직 문화
  • 관리체계문제
    • 분권화된 관리체계 필요
    • 더 나은 서비스를 만들기 위해 표준, 모범사례, 가이드라인 제정 필요
    • 모든 이해관계자가 개발된 모든 서비스를 보는 것 뿐 아니라, 모든 문서, 계약, 서비스 수준 합의도 볼 수 있어야 한다
  • 운영오버헤드
  • 마이크로서비스 테스팅
    • 서비스의 전 구간을 아우르는 동작을 평가하는 테스트는 어떻게 수행할 수 있을까?
      • 서비스 가상화 또는 목킹
      • 서비스 사용자 주도 계약
  • 인프라스트럭처 프로비저닝
마이크로서비스 역량 모델
  • 핵심역량
    • 서비스 리스너(HTTP 리스너/메시지 리스너)
    • 저장 기능
    • 비즈니스 범위 정의
    • 이벤트소싱
    • 서비스 종단점 및 통신 프로토콜
    • API 게이트웨이 : Zuul, Mastery, Apigee, 3scale
    • 사용자인터페이스
  • 지원역량
    • 소프트웨어 정의 로드 밸런서 : Ribbon, Eureka, Zuul
    • 중앙집중형 로그 관리
    • 서비스레지스트리 : Eureka, Zookeeper, Etcd
    • 보안서비스 : OAuth
    • 서비스 환경설정 : 스프링 클라우드 Config, Archaius
    • 테스팅 도구(anti-fragile, RUM) : netflix Simian Army
    • 모니터링 및 대시보드 : Turbine, Hystrix Dashboard, AppDynamic, New Relic, Dynatrace, said, Sense, Spigo
    • 의존 관계와 CI 관리 : CMDB
    • 데이터호수 : 스프링 데이터 플로우, Flume, Kafka, HDFS, Cassandra
  • 인프라스트럭처 역량
    • 클라우드
    • 컨테이너/가상머신
    • 클러스터 제어 및 프로비저닝 : Mesos, Kubernetes
    • 애플리케이션 라이프 사이클 관리 : Marathon
  • 프로세스 및 통제역량
    • 데브옵스
    • 데브옵스 도구
    • 마이크로서비스 저장소 : Nexsus, 도커레지스트리
    • 마이크로서비스 문서화 : Swagger, API Blueprint
    • 참조 아키텍처 및 라이브러리


마이크로 서비스로의 진화

- 기업은 소셜미디어, 모바일, 클라우드, 빅데이터, 사물인터넷드을 주요 수단으로 활용하며 시장에 빠르게 진입하기위한 방법에 관심을 갖게 되었으며, 그러한 것을 가능하게 하기위해 애자일성, 변경 및 배포 신속성, 확장성 같은 요소들에 관심을 갖게 되었다. 

- 기술적으로 다양한 관점에서 모든 계층의 구조를 다시 고려하게 하는 기술들이 개발 되었다. 프론트엔드의 Angular, Ember, Backbone등, 클라우드 환경의 AWS, 컨테이너 관련 Docker, 데이터베이스 영역에서는 NoSQL이 등장하였고  Hadoop, Cassandra, CochDB, Neo4j등이 있다.


마이크로서비스란 무엇인가?

- 물리적으로 분리할 수 있는 모듈화된 애플리케이션을 만들 수 있는 아키텍처 스타일이다.

- IT 시스템을 자율적이고, 자기 완비적(self-contained)이면서도 느슨하게 연결된 비즈니스 범위의 집합으로 만드는 아키텍처 스타일이다.

- 마이크로서비스 사이의 통신이나 전송방식에 정해진 표준은 없으나, 일반적으로 HTTP REST같은 경량프로토콜, AMQP같은 메시징 프로토콜을 주로 사용한다. 필요에 따라 Thrift, ZeroMQ, Protocol Buffers, Avro처럼 특수한 목적에 최적화된 통신프로토콜을 사용할 수도 있다.

- 마이크로서비스를 적용하기위해서 조직의 변화도 중요하다 기술에 대한 내재화, 개발과 운영의 간극을 좁히기 위한 DevOps같은 개념이 필연적이다


마이크로서비스의 원칙

- 서비스 하나에책임도 하나 : 클래스든 함수든 서비스든 간에 하나의 단위 요소는 반드시 하나의 책임만을 가져야 한다

- 마이크로 서비스는 자율적 : 자기 완비적이고, 독립적으로 배포할 수 있으며, 자율적인 서비스로서 비즈니스의 범위와 실행에 대해 전적인 책임을 진다.

- MSA 와 SOA의 차이점은 자율성 수준의 차이다. SOA는 서비스 수준의 추상화, MSA는 실행환경까지도 추상화


마이크로서비스의 특징

- 서비스는 일급 시민

- 서비스 계약

- 느슨한 결합

- 서비스 추상화

- 서비스 재사용

- 무상태

- 서비스 발견성

- 서비스 호환성

- 서비스 조립성

- 마이크로서비스는 경량

- 다양한 언어로 구성 가능

- 개발에서 배포까지 쉬운 자동화

- 마이크로서비스를 지원하는 생태계

- 동적이고 분산돼 있는 마이크로서비스

- 붕괴 저항성, 빨리 실패하기, 자체 치유


마이크로서비스의 장점

- 폴리글랏 아키텍처 지원 : 각 서비스는 자신만의 아키텍처와 여러가지 기술을 적용하여 구축 운영

- 실험과 혁신 유도

- 탄력적이고 선택적인 확장

- 대체 가능성

- 유기적 시스템 구축 유도 : 시간이 지남에 따라 점점 더 많은 기능을 추가하면서 성장해가는 시스템

- 기술적 부채 경감

- 다양한 버전의 공존

- 자기 조직화 시스템 구축 지원

- 이벤트 주도 아키텍처 지원

- 데브옵스 지원


다른 아키텍처 스타일과의 관계

SOA와의 관계 : SOA를 도입하는 방식에 따라 같기도 하고 다르기도 하다

- 서비스 지향 통합 : 다름

- 기존 시스템의 현행화 : 다름

- 서비스 지향 애플리케이션 : 마이크로서비스를 현재 도입한 SOA의 논리적인 다음 단계

12 요소 애플리케이션과의 관계

- 클라우드에서 운영 가능한 현대적인 애플리케이션에서 기대할 수 있는 특징을 기술하는 방법론

- 단일 코드 베이스 : 각 마이크로서비스는 자체적인 코드베이스를 가져야하고 다른 마이크로서비스와 공유되지 않는다(git/subversion)

- 의존성 꾸러미(bundling dependencies) : 모든 애플리케이션은 필요한 모든의존성을 애플리케이션과 함께 하나의 꾸러미에 담아야 한다(Maven/Gradle)

-  환경설정 외부화(externalizing configurations) 

- 후방 지원 서비스 접근성(backing service)

- 빌드, 출시, 운영의 격리

- 무상태, 비공유 프로세스

- 서비스를 포트에 바인딩해서 노출

- 확장을 위한 동시성 : 프로세스가 복제를 통해 확장될 수 있게 설계

- 폐기 영향 최소화(disposability with minimal overhead) : 애플리케이션의 시동과 종료에 필요한 시간을 최소화하고, 서버가 종료될때에는 필요한 처리가 모두 수행되어야 함(lazy loading)

- 개발과 운영의 짝 맞춤(Development and production parity) : 개발 환경과 운영 환경을 가능한 한 동일하게 유지

- 로그 외부화 : 로그파일을 절대로 자기 자신안에 담지 않는다. 중앙집중식 로깅 프레임워크사용(Splunk, Greylog, Logstash, Logplex, Loggly) 로그백 추가자를 통해 로그를 중앙 저장소에 적재하고, 적재 도구의 종단점에 로그를 쓰는 방법

- 패키지 관리자 프로세스 : 관리자 태스크를 위한 코드도 애플리케이션 코드와 함께 패키징되어야 한다.


마이크로서비스 사용 사례

- 일체형의 전환

- 넷플릭스, 우버, 에어비앤비, 오비츠, 이베이, 아마존, 길트, 트위터, 나이키


참고자료

- hexagonal architecture : http://alistair.cockburn.us/Hexagonal+architecture

- avro : http://avro.apache.org/docs/current/

- DevOps : http://dev2ops.org/2010/02/what-is-devops/

- 일급시민 : https://ko.wikipedia.org/wiki/일급_객체

2013년인가 14년도 즈음에 프로젝트에서 회고를 진행하였고 급 관심이 생겨 애자일회고라는 책을 샀다. 그때는 책을 사서 한번 읽어보고 재미는 있겠는데 현실적이진 않다고 생각했었다. 


얼마전 회고를 진행하게 되어 다시 책을 읽어봤고, 처음 읽었을때와는 다르게 활동하나하나가 재밌고 유익하게 느껴졌다. 


책의 진행방식에 따라 아래와 같은 순서로 회고를 진행해 보았다.


1. 사전준비

- 처음으로 회고를 진행하는 나와 팀원들의 어색함을 달래주기 위해 체크인 활동을 했다

2. 자료모으기

- 예상치 못한 팀의 변고로 인해 스프린트가 길어졌고 긴 스프린트를 돌이켜 보기위해 시간축 활동을 했다

3. 통찰 이끌어내기

- 브레인 스토밍학습매트릭스 활동을 하려했으나 시간 부족 및 진행 미숙으로 브레인 스토밍만 진행했다

4. 무엇을 할지 결정하기

- 스마트 목표 활동을 하려 했으나 역시 시간부족과 진행 미숙으로 브레인스토밍과 액션아이템을 뽑는 작업이 같이 이루어 졌다

5. 회고 끝내기 

- 끝낼때는 감사표현하기 활동으로 돌아가며 감사의 말을 하려고 했으나 어색함속에 간단한 형식적인 감사의 말로 급하게 마무리 되었다


첫 회고 진행 이어서 미숙하고 각 활동의 목표를 달성하지는 못했지만 액션아이템도 뽑고 모두 웃으며 지루하지 않고 재미있는 회고 였던것 같다


  • 모델링 과정을 매우 복잡한 도메인까지 확장하는 원리
  • 성공적인 모델 : 규모와는 상관없이 모순되거나 정의가 겹치지 않고 처음부터 끝까지 논리적인 일관성 유지
  • Bounded Context 
  • Distillation
  • 대규모 구조 : 전혀 공통점이 없는 부분들이 맞물려 돌아가도록 일관성을 가져다 줌
    • Responsibility Layer
    • Evolving Order(발전하는 질서)
모델의 무결성 유지
  • 각 모델이 적용되는 경계를 분명하게 합의하는 것에서 출발
  • 단일화(unification) : 각 용어가 모호하지 않고 모순되는 규칙이 없는 모델의 내적 일관성
  • 다른 여러 모델 간의 경계와 관계를 표시해줄 수단 필요
    • Context Map : 프로젝트 분야를 매핑, 각 컨텍스트 간의 관계의 전체적인 개관
    • Bounded Context : 각 모델의 적용가능성의 범위 정의
    • Continuous Integration : 프로세스를 토대로 모델의 단일화 유지
    • Shared Kernel
    • Separate Ways
Bounded Context
  • 규모가 큰 프로젝트에는 다수의 모델이 공존하며, 서로 다른 모델은 서로 다른 컨텍스트에 적용된다
  • 한 팀 내에서도 다수의 모델이 공존할 수 있다
  • 다수의 모델 탓에 발생하는 문제의 해결 방법
    • 소프트웨어 내의 제한된 부분으로 특정 모델의 범위를 명확하게 정의
    • 팀의 구성과 조화
    • 컨텍스트의 경계를 팀 조직, 애플리케이션의 특정 부분에서의 사용법, 코드 기반이나 데이터베이스스키마와 같은 물리적인 형태의 관점에서 명시적으로 설정
    • 경계 내에서는 모델을 엄격하게 일관된 상태로 유지하고 경계 바깥의 이슈 때문에 초점이 흐려지거나 혼란스러워져서는 안된다
    • 모델을 책임지는 팀에서는 영속화를 비롯한 각 객체의 전체 생명주기를 다룬다

Bounded Context안의 균열 인식

  • 코드로 작성된 인터페이스가 서로 맞지 않는 경우
  • 예상치 못한 행위
  • 언어를 혼동한 상태로 구사
  • 중복개념 : 실제로 같은 개념을 나타내는 두개의 모델 요소가 존재하는 것
  • 허위동족언어(false cognates) : 같은 용어를 사용하는 두 사람이 서로 같은 것을 이야기하고 있다고 생각하지만 실제로는 그렇지 않은 경우, 개념상의 충돌
  • 해결방안
    • Continuous Integration
    • Context Map
    • Shared Kernel
    • Customer/Supplier Development Team
    • Conformist
    • Anticorruption Layer
    • Separate Ways
    • Open Host Service
    • Published Language

Continuous Integration

  • 내부적으로 균열이 발생할 때 이를 빠르게 포착하고 정정할 수 있을 정도로 컨텍스트 내의 모든 작업을 빈번하게 병합해서 일관성 유지
  • 모델 개념의 통합
    • 팀 구성원 간의 부단한 의사소통을 토대로 통합
  • 구현 수준에서의 통합
    • 모델내의 균열을 조기에 드러내는 체계적인 병합/빌드/테스트 프로세스를 토대로 통합
  • 프로세스
    • 단계적이고 재생 가능한 병합/빌드 기법    
    • 자동화된 테스트 스위트
    • 수정사항이 통합되지 않은 상태로 존재할 수 있는 시간을 적당히 짧게 유지하는 규칙

Context Map

  • Bounded Context간에 코드를 재사용하는 것음 위험하므로 기능과 데이터는 번역 과정을 거쳐 통합해야 한다.
  • 서로다른 컨텍스트간의 관계를 정의하고 프로젝트상의 모든 모델 컨텍스트를 아우르는 전체적인 뷰를 만들면 혼란을 줄일 수 있다
  • Context Map은 프로젝트 관리와 소프트웨어 설계 영역 사이에 걸쳐있는 개념
  • 의사소통을 위해 컨텍스트 간의 번역에 대한 윤곽을 명확하게 표현
  • 컨텍스트 간에 공유해야 하는 정보를 강조
  • 모델과 모델이 만나는 경계 지점 서술
  • Bounded Context간의 관계 패턴
    • Shared Kernel
    • Customer/Supplier(현재 가장 많이 적용되어 있는 패턴)
    • Separate Ways
    • Open Host Service
    • Anticorruption Layer(wrapper, translator, facade, service)

디스틸레이션

  • 혼합된 요소를 분리해서 본질을 좀더 값지고 유용한 형태로 뽑아내는 과정
  • Generic subdomain - 모델에서 가장 특색이 없는 측면 제거
  • Coherent Mechanism - 용도가 다양하고, 의미전달이 용이하며, 유연한 설계를 통해 캡슐화
  • Segregated Core
  • Abstract Core - 가장 근본적인 개념과 관계를 순수한 형태로 표현
  • Core Domain
    • Domain Vision Statement - 최소한의 투자로 기본개념과 가치를 
    • Highlighted Core - 의사소통을 향상시키고 의사결정에 도움

Core Domain

  • 도메인 모델을 가치있는 자산으로 만들려면 모델의 핵심적인 측면을 다루기 수월해야 하고 애플리케이션의 기능성을 만들어내는 데 충분히 활용할 수 있어야 한다
  • Core Domain은 시스템에서 가장 큰 가치가 더해지는 곳이다
  • 시스템의 비전을 수행하기에 충분한 심층 모델을 찾고 유연한 설계를 개발할 수 있게 코어에 노력을 쏟아라

Generic Subdomain

  • 모델은 일반 원칙(누구나 알고 있는것)이나 세부사항(보조적인 역할을 수행하는 전문 분야에 속하는 것) 탓에 정체된다
  • 개발 시 선택사항
    • 기성 솔루션(상용 또는 오픈소스)
    • 공표된 설계나 모델
    • 외주 제작
    • 사내구현
  • 일반화가 재사용 가능하다는 의미는 아니다
  • 필요한 만큼만 투자
  • 쉽기 때문에 보조 시스템을 먼저 구축할 경우 위험관리의 목적을 헛되게 할 수 있음

Domain vision Statement

  • 도메인 모델의 본질과 해당 도메인 모델이 얼마나 기업에 가치 있는가에 초점을 맞춘다
  • 팀 내에서 방향성을 공유하게 해 줌
  • 작성방법
    • Core Domain을 짧게 기술하고 그것이 가져올 가치에 해당하는 가치제안을 작성
    • 이 도메인 모델과 다른것과 구별하는데 도움되지 않는 측면은 무시
    • 도메인 모델이 어떻게 다양한 관심사를 충족하고 균형을 이루는지 보여라
    • 한정된 범위에서 내용을 유지하라
    • 초기에 이 선언문을 작성하고 새로운 통찰력을 얻을 때마다 선언문을 개정하라


Highlighted Core

  • 어떤 모델에서 특별히 중요한 부분을 그것을 구체화한 구현과 함께 표시할 필요가 있는데, 이러한 표시는 모델에 대한 설명이지 반드시 모델 자체의 한 부분일 필요는 없다
  • 기법
    • 디스틸레이션 문서 : Core Domain과 Core의 구성요소 사이에서 일어나는 상호작용을 기술하는(3에서 7페이지 가량의) 매우 간결한 문서를 작성하라
    • 표시된 Core : 모델의 주요 저장소 안에 있는 Core Domain의 구성요소에 대해 그것의 역할을 설명하려하지 말고 표시하라. 개발자가 힘들이지 않고도 Core의 안과 밖을 알 수 있게 하라

Cohesive Mechanism

  • 의도를 드러내는 이름이 이정된 메서드에 복잡한 알고리즘을 숨기면 "무엇"이 "어떻게"와 분리된다
  • 문제해결을 위한 알고리즘을 제공하는 수많은 메서드가 문제를 표현하는 메서드를 분분명하게 만드는 경우
    • 개념적으로 Cohesive Mechanism을 별도의 경량 프레임워크로 분할
    • Intention-Revealing Interface로 프레임워크의 기능을 노출
    • 해법의 복잡성("어떻게")을 프레임워크에 위임해서 문제("무엇")을 표현하는데 집중    

Segregated Core

  • 설계자가 가장 중요한 관계를 분명하게 볼 수 없다면 취약한 설계로 이어지는 결과가 나타난다
  • 모든 일반적이거나 보조적인 역할을 하는 구성요소를 다른 객체로 추출해서 다른 패키지에 배치하라
Abstract Core
  • 모델의 가장 근본적인 개념을 식별해서 그것을 별도의 클래스나 추상 클래스, 또는 인터페이스로 추출하라
  • 이 추상 모델이 중요 컴포넌트 간에 발생하는 상호작용을 대부분 표현할 수 있게끔 설계하라
  • 특화되고 세부적인 구현클래스는 하위 도메인을 기준으로 정의된 자체적인 모듈에 남겨둔 상태에서 이 추상적이면서 전체적인 모델을 자체적인 모듈에 배치하라

리팩토링의 대상선택

  • 문제의 근원에 Core Domain이나, Core 와 지원요소와의 관계가 있는지 살핀다. 그렇다면 가장먼저 고쳐야 한다
  • 마음껏 리팩토링할 수 있는 상황이라면 제일먼저 Core Domain을 더 잘 분해하고 Core의 격리를 개선하며, 보조적인 하위 도메인이 Generic하게 만드는 데 집중한다.


리팩터링은 엔트로피와의 싸움이며 레거시 시스템이 퇴보하는 것을 막는 최전선에 놓여 있다.


암시적인 개념을 명확하게

  • 도메인 전문가가 사용하는 언어에 귀 기울여라
    • 어색한 부분을 조사하라
    • 설명하기 힘들만큼 복잡한 작업을 수행하는 프로시저와 관련된 부분이나 새로운 요구사항 탓에 복잡성이 증가하는 부분
    • 모순점에 대해 깊이 고민하라
  • 서적을 참고하라
  • 시도하고 또 시도하라
    • 모델러/설계자는 자신의 아이디어에 집착해서는 안된다
다소 불명확한 개념을 모델링하는 법
1. 명시적인 제약조건
  • 제약조건을 별도의 메서드로 분리하고 제약조건의 의미를 분명하고 명확하게 표현할 수 있게 메서드의 이름을 짓는다
  • 부여된 이름을 사용해서 제약조건에 관한 토의가 가능
  • 잘못된 제약조건 설계의 식별
    • 제약조건을 평가하려면 해당 객체의 정의에 적합하지 않은 데이터가 필요하다
    • 관련된 규칙이 여러 객체에 걸쳐 나타나며, 동일한 계층구조에 속하지 않는 객체 간에 중복 또는 상속 관계를 강요한다
    • 설계와 요구사항에 관한 다양한 논의는 제약조건에 초점을 맞춰 이뤄지지만 정작 구현단계에서는 절차적인 코드에 묻혀 명시적으로 표현되지 않는다.
2. 도메인 객체로서의 프로세스
  • 객체는 절차를 캡슐화해서 절차 대신 객체의 목표 의도에 관해 생각하게 해야 한다
  • 어떤 프로세스를 선택할 것인가는 곧 어떤 객체를 선택할 것인가가 되고, 각 객체는 각기 다른 Strategy를 표현한다

3. 명세(Specification)

  • 어떤 객체가 특정기준을 만족하는지 판단하는 술어다.
  • 다른객체에 대한 제약조건을 기술하며, 제약조건은 존재할 수도 존재하지 않을 수도 있다
  • 특별한 목적을 위해 술어와 유사한 명시적인 Value Object를 만들어라

유연한 설계

  • 너무 과도한 추상 계층과 간접 계층이 존재하면 오히려 유연성에 방해가 된다
  • 정교한 시스템을 목적으로 조립가능하고 이해하기 어렵지 않은 요소를 만들어내려면 적당한 수준의 엄밀한 설계형식과 접목하고자 노력해야 한다

1. 의도를 드러내는 인터페이스(Intention-Revealing Interface)

  • 캡슐화로 클라이언트 코드는 단순해지고 상위 수준의 개념 관점에서 코드를 이해할 수 있다
  • 인터페이스를 구성하는 각 요소(타입, 메서드, 인자 이름)의 이름을 토대로 설계 의도를 드러낸다
  • 결과와 목적만을 표현하도록 클래스와 연산의 이름을 부여(Ubiquitous Language 기반)
  • 행위에 대한 테스트를 먼저 작성
  • 방법이 아닌 의도를 표현하는 추상적인 인터페이스위로 모든 까다로운 메커니즘을 캡슐화
2. 부수효과가 없는 함수(Side-Effect-Free-Function)
  • 부수효과를 일으키지 않으면서 결과를 반환하는 연산을 함수라 한다
  • 함수는 여러번 호출해도 무방하며 매번 동일한 값을 반환한다
  • 명령과 질의를 엄격하게 분리 - 변경을 발생시키는 메서드는 도메인 데이터를 반환하지 않아야하고 가능한 단순하게 유지해야 한다
  • 명령과 질의를 분리하는 대신 연산의 결과를 표현하는 새로운 Value Object를 생성해서 반환
  • 상태변경을 수반하는 로직과 계산이 혼합된 연산은 리팩터링을 거쳐 두개의 연산으로 분리해야 한다
  • 복잡한 계산을 처리하는 책임을 Value Object로 옮긴다

3. 단언(Assertion)

  • 연산의 사후 조건과 클래스 및 Aggregate의 불변식을 명시하라
  • 개발자들이 의도된 단언을 추측할 수 있게 인도하고, 쉽게 배울수 있고 모순된 코드를 작성하는 위험을 줄이는 응집도 높은 개념이 포함된 모델을 만들려고 노력하라
4. 개념적 윤곽(Conceptuel Contour)
  • 이 개념이 현재 모델과 코드에 포함된 관계를 기준으로 했을때 적절한가, 또는 현재 기반을 이루는 도메인과 유사한 윤곽을 나타내는가?
  • 변경되는 부분과 변경되지 않는 부분을 나누는 중심 축을 식별하고, 변경을 분리하기 위한 패턴을 명확하게 표현하는 개념적 윤곽을 찾아라
  • 객체와 메서드를 와해시킬 정도로 광범위한 변경을 야기하는 요구사항이 나타났다는 것은 도메인에 관해 알고 있는 지식을 개선해야 한다는 메시지다
4. 독립형 클래스(Standalone Class)
  • Module과 Aggregate 모두 지나치게 얽히고 설키는 상호의존성을 방지하는 것이 목적이다
  • 명시적인 참조에 비해 암시적인 개념이 훨씬 더 많은 정신적 과부하를 초래한다.
  • 현재 상황과 무관한 모든 개념을 제거하라
  • 클래스가 완전히 독립적으로 바뀌고 단독으로 검토하고 이해할 수 있을 것이다
  • 모든 비본질적인 의존성을 제거하는 것이 목표다
  • 가장 복잡다단한 계산을 Standalone class로 도출하려고 노력하라
  • Standalone Class는 극단적으로 결합도를 낮춘 것이다

5. 연산의 닫힘(Closure of Operation)

  • 구현자(implementer)가 연산에 사용되는 상태를 포함하고 있다면 연산의 인자로 구현자를 사용하는 것이 효과적이므로 인자의 타입과 반환 타입을 구현자의 타입과 동일하게 정의한다. 이런 방식으로 정의된 연산은 해당 타입의 ㅇ니스턴스 집합에 닫혀 있다. 닫힌 연산은 부차적인 개념을 사용하지 않고도 고수준의 인터페이스를 제공한다.
  • 일반적으로 Entity는 어떤 계산의 수행결과를 표현하는 개념이 아니다. 따라서 대부분의 경우 Value Object에서 이 패턴을 적용할 기회를 찾을 수 있다.
6. 선언적 설계
  • 일반적으로 일종의 실행 가능한 명세(executable specification)로서 프로그램 전체 혹은 프로그램의 일부를 작성하는 방식
  • 특성(properties)을 매우 정확하게 기술함으로써 소프트웨어를 제어하는 것
  • 선언적인 프로그램의 이점을 누리려면 모든 개발자가 프레임워크의 규칙을 준수 해야 한다
  • 아주 좁은 범위로 한정된 프레임워크를 사용해서 영속성과 객체관계형 매핑과 같이 매우 지루하고 오류가 발생하기 쉬운 설계 측면을 자동화한 경우에 큰 가치를 얻었다
  • 규칙기반(rule base)
    • 원칙적으로는 선언적이지만 대부분의 시스템은 성능 최적화를 위해 제어술어(control predicate)를 포함
    • 이러한 제어코드는 부수효과를 수반하므로 더는 선언된 규칙만으로는 완전한 행위를 지시할 수 없다
7. 도메인 특화 언어
  • 특정 도메인을 위해 구축된 특정 모델에 맞게 조정된 프로그래밍 언어를 사용해 클라이언트 코드 작성
  • 프로그램의 표현력을 월등히 향상시킬 수 있음
  • Ubiquitous Language와도 가장 높은 일관성을 유지 할 수 있음
8. 하위 도메인으로 분할하라
  • 조금씩 뜯어내어 접근
  • 모델의 일부 영역이 전문적인 영역이거나, 상태변경에 제약을 가하는 복잡한 규칙을 적용한다면 끄집어내어 별도의 모델이나 규칙을 선언적으로 표현해주는 간단한 프레임워크 내부로 옮긴다
  • 하나의 영역에 집중

9. 가능하다면 정립된 정형화를 활용하라

  • 오랜 시간 동안 정립되어 온 개념적인 체계 이용
  • 수학적인 개념 - 도메인에 적절히 특화된 수학은 깔끔한 동시에 명확한 규칙과 결합할 수 있어서 사람들이 이해하기도 쉽다
모델과 디자인 패턴의 연결
  • 기술저인 문제에 대한 해법뿐 아니라 개념적인 도메인에 관한 해법도 제공해야 한다는 것이 디자인 패턴을 도메인 패턴으로 적용하기 위한 유일한 요구사항이다
1. Strategy(전략, 정책 패턴)
  • 여러프로세스의 선택이라는 문제를 해결
  • 프로세스의 규칙과 프로세스를 제어하는 행위를 서로 분리
  • 도메인 패턴으로 사용하는 관점에서는 프로세스 또는 정책적인 규칙과 같은 하나의 개념을 표현하는 능력에 중점

2. Composite

  • Composite내부에 포함된 모든 구성요소를 포괄하는 추상 타입을 정의
  • 계층구조상의 모든 수준에서 동일한 행위를 제공
  • 크고 작은 각 부분이 전체 구조를 투명하게 반영


Layered Architecture

  • SoC를 아키텍처 레벨에서 가능하게 해주는 패턴
  • 계층을 나누어 각 계층의 관심사에 집중할 수 있도록 한다.
  • 일반적으로 사용자 인터페이스, 응용, 도메인, 인프라스트럭쳐 계층이 있다.


도메인 모델 빌딩블럭

엔티티(Entity)

  • 어떤 객체를 일차적으로 해당 객체의 식별성으로 정의
  • 객체의 생명주기 내내 이어지는 추상적인 연속성
  • 엔티티의 속성 보다는 정체성에 초점


Value Object

  • 개념적 식별성을 갖지 않으면서 도메인의 서술적 측면을 나타내는 객체
  • 모델에 포함된 어떤 요소의 속성에만 관심
  • 불변적
  • 객체의 수가 많아질 수 있으므로 객체를 고유하여 최적화 가능


Service

  • 모델에서 독립적인 인터페이스로 제공되는 연산
  • 다른 객체와의 관계를 강조
  • 연산의 명칭은 Ubiquitous language에 도입되어야 함
  • 매개변수와 결과는 도메인 객체여야 함
  • 도메인 계층에서만 이용되는 것은 아님
  • 각 계층의 서비스와 도메인 서비스를 적절하게 나누는 것이 중요 함


Module

  • 패키지
  • 일련의 응집력있는 개념
  • 모듈의 이름은 도메인에 통찰력을 줄 수 있어야 함


도메인 객체의 생명주기


도메인객체의 관리 문제

  • 생명주기 동안의 무결성 유지하기
  • 생명주기 관리의 복잡성으로 모델이 난해해지는 것을 방지하기

해결방법

Aggregate

  • 소유권과 경계를 명확히 정의하여 객체 간의 연관관계가 복잡해지지 않도록 한다
  • 도메인 객체의 무결성 유지에 중요 함
  • 생명주기의 전 단계에서 불변식이 유지돼야 할 범위를 표시

Factory

  • 생명주기의 초기단계
  • 복잡한 객체와 Aggregate를 생성하고 재구성

Repository

  • 생명주기의 중간과 마지막
  • 영속 객체를 찾아 조회하는 수단
Aggregate
  • root와 boundary
  • boundary : 무엇이 포함되고 무엇이 포함되지 않는지 정의
  • root : 단 하나만 존재, 특정 엔티티
  • 경계 바깥의 객체는 해당 Aggregate의 구성요소 가운데 root 만 참조 가능
  • 불변식 : 데이터가 변경될 때마다 유지돼야 하는 일관성 규칙
  • 구현 규칙
    • 루트 엔티티는 전역 식별성을 지니며 불변식을 검사할 책임이 있다
    • 루트는 Value Object의 복사본을 단른 객체에 전달해 줄 수 있다
    • 삭제 연산은 경계안의 모든 요소를 한번에 제거해야 한다.
    • 변경시 전체 불변식은 반드시 지켜져야 한다




전역식별성

지역식별성

모델

  1. 중요한 사실이나 사상의 일부 측면을 나타냄 
  2. 대상을 단순화 한것
  3. 당면한 문제와 관련된 것을 추상화

도메인

  • 사용자가 프로그램을 사용하는 대상 영역
  • 컴퓨터와 거의 관련이 없음
도메인 모델
  • 특정한 다이어 그램이 아니라 전달하고자 하는 아이디어
  • 지식을 엄격하게 구성하고 선택적으로 추상화한 것
  • 모델과 핵심 설계는 서로 영향을 주며 구체화 된다
  • 모델은 모든 팀 구성원이 사용하는 언어의 중추
  • 모델은 지식의 정수만을 뽑아낸 것이다
Ubiquitous language
  • 클래스, 주요 연산등의 이름
  • 명시적으로 드러나는 규칙을 토론하기 위한 용어
  • 도메인 모델에 적용하는 패턴의 이름
  • 공통언어(도메인 전문가와 개발팀간)로서 모델과 코드에서 사용해야 한다.
  • 모델, 설계, 구현 전체를 연결하는 핵심 키

도메인 모델 작성시 가장 중요하다고 생각하는 것은 추상화이다. 특히 기존 코드를 분석하여 모델을 만드는 경우 코드의 세세한 부분까지 모델에 표현하려는 욕심은 자제해야 한다.



+ Recent posts