SIDE)계약, 거래의 트랜잭션 관계 맺기
계약과 거래와 같은 서로 정보를 주고 받을 때
📜 제목으로 보기
계약과 거래를 하는 트랜잭션 관계
계약하기
- 형태
-
을인 doctor가 reception들에게 [void setter/boolean 거래 제안기능]을 통해, [거래조건]과 함께 먼저 알고서 데리고 온다.
- [거래 제안기능]은 내부에서 갑인 reception의 [boolean 거래 수락기능]을 통해 결과를 받아와서, 결국엔 내부 필드에 계약자들을 저장하는 void setter받기기능과 유사한 형태며, boolean으로 doctor를 사용하는 사람에게 알려줘도 된다.
-
갑인 reception은 [boolean 거래 수락기능]을 통해, doctor와 [거래조건]을 알고서 데려가 검증한 뒤, 성공시 필드에 거래조건과 함께 저장하며, boolean으로 수락여부를 을인 doctor에게 알려준다.
- 계약이든 거래든 갑이 데리고 가서 검증/결정후 결과를 반환해서 알려주면 을은 결과에 따라서 행동한다.
-
을인 doctor가 reception들에게 [void setter/boolean 거래 제안기능]을 통해, [거래조건]과 함께 먼저 알고서 데리고 온다.
-
을(doctor)가 먼저 [boolean 거래제안 기능]을 거래대상인 갑(reception)에게 [거래조건]과 함께 제안한다.
-
doctor의 계약제안 기능의 내부에서는
-
갑의 [boolean 계약수락 기능]을 호출한 뒤, 반환받은 결과에 따라 행동한다.
-
추가로 이미 계약중(컬렉션필드 -> CRUD 생각 -> CREATE시 중복검증)되면 안된다.
- if A && B 여야만 수행 -> 컬렉션에 계약자로 추가
-
**if not A not B -> return false (early return) -> 수행** - 만족(if A) 시 수행이라면 not A early return을 고려한다.
-
**둘다 만족시(if A && B) 수행이라면, not A not B early return을 고려한다.** -
**둘다 return값이 동일하다면, 로 묶어서 한번에 early return**
-
- not A return (early) false ;
- not B return (early) false;
- 수행
-
==
not Anot B reutrn (early) false; -
==
수행
-
-
- if A && B 여야만 수행 -> 컬렉션에 계약자로 추가
-
Set컬렉션을 쓰고 있으므로 중복검증(A)는 생략한다.
- if not B early return 후 수행만 하면 된다.
-
-
reception의 거래수락 기능 내부에서는
- 거래대상과, 거래조건을 매칭해서 저장할 HashMap 필드를 만들고
- (거래는 상대방의 돈검증) 이미 계약중인지,
거래대상 검증(중복검증)
을 한다. - (거래는 내가 줄 물건검증) 계약대상과 계약조건을 내부필드에 저장하여 계약한다.
- (거래는 상대방 돈차감 -> 물건반환) 수락여부true를 반환한다. (검증실패시 false)
-
계약 제안/수락 기능처럼, 계약취소 제안/수락기능도 있다.
-
계약취소 제안기능(DELETE)
-
A: 계약취소 대상자 존재 검증 && B:갑의 계약취소 수락기능의 결과가 true
- 둘다 만족해야지 수행
-
**not A not B early return한다.**
-
- 둘다 만족해야지 수행
-
-
계약취소 수락기능(DELETE)
-
갑으로서 누구의 결과를 기다리지 않으니, 삭제 전 존재 검증만 하면 된다.
-
-
거래하기
-
참고
-
Patient가 [void setter구매기능]을 통해 거래를 제안한다.
-
Coordinator는 최초 [getter물건 판매기능]을 제공하고, Patient에게 결과를 [물건반환]으로 알려주는데, 실패시 NULL객체를 반환한다. (NULL객체를 쓰는 순간, boolean의 반환이 필요없어진다.)
- A(돈 검증) && B(물건 검증)시 상대방의 돈을 차감한다. 돈 가산은 물건을 주는 Reception에게 미룬다.
-
not A not B early NULL객체 return을 해도 될 것 같지만. - if A 와 if B 사이에 로직이 존재하여 early return이 불가하다.
- 이 땐, 실패의 else마다 똑같은 값이 반환되므로, 애초에 반환값을 EMPTY(NULL객체)로 변수로 선언해놓고 시작하고, 성공시 재할당하여, 마지막에만 해당 변수를 return한다.
-
-
[상대방 돈 검증] 하기 전, 검증기준인 [물건의 가격을 계산]해야한다.
-
Coordinator는 계산의 책임을 수수료를 챙겨서 계산하는 Reception에게 [물건 가격 계산]도 위임한다.
-
사실, 물건가격계산은, 정책이 적용될 Specialty객체로 바로 할 수 있지만, 의존성이 1곳에서만 생기도록 Reception에게 위임한다.
-
-
[상대방 돈 검증]
-
[건네줄 물건 검증]을 하기 전, 검증 기준은 [물건]을 받아와야한다.
- Coordinator는 최초 물건 발행권자인 Doctor로부터 생성해서 받아와야하므로 [getter물건 판매기능]을 Coordinator -> Reception -> Doctor까지 연쇄적으로 호출해서 물건을 받아온다.
-
[받아온 물건 검증]
-
[상대방 돈차감]
- 돈 가산은 계산의 책임이 있는 Reception에서, Reception의 [판매기능]내에서 이루어지게 한다.
-
[물건 반환]
- A(돈 검증) && B(물건 검증)시 상대방의 돈을 차감한다. 돈 가산은 물건을 주는 Reception에게 미룬다.
-
Reception
- 연쇄적인 [getter물건 판매기능]안에서 들어오는 [구매정보 검증]을 한다.
- 돈 검증은 구매자와 최초연결된 Coordinator에서 담당한다.
- [정보 검증]을 통해, Doctor로 가서 Package발행 전에 NULL객체를 물건으로 반환해서 미리 컷한다.
- [물건 검증]전, 물건을 Doctor의 [getter물건 판매기능]으로 떼온다.
- 수량제한에 걸려서 Doctor가 NULL을 건네줄 수 있다.
- [물건 검증]
- [돈 가산]
- 물건이 검증되면, Coordinator의 돈차감과 같은 레벨로 [돈 가산]을 해야한다.
- 구매정보에 담긴 (정책적용객체) Specialty에서 물건가격을 계산하고
- **구매정보의 doctor와 계약된 commisionRate를 꺼내서, 수수료를 계산해, [내 자본금을 가산] **한 뒤
-
물건가격 -수수료 만큼을 [발행권자 doctor에게 가산]해준다.
- 계산은 Reception에서만 이루어져서 나도 챙기고, 발행권자도 챙겨준다.
- [물건 반환]
- 연쇄적인 [getter물건 판매기능]안에서 들어오는 [구매정보 검증]을 한다.
-
Doctor
- 연쇄적인 [getter물건 판매기능]을 통해 물건을 생성해야하는데
- 내가 소유하고 있는 정보로 [구매정보 검증]한다.
- Reception에서 컷 안당했지만, doctor만의 소유정보로 컷 당할 수 있다.
- 예를 들어, Specialty - Treatment들의 매칭 정보
-
[발행 전
발행가능 갯수
검증]을 한다.-
발행가능 갯수는 Treatment의 count로 명시되어있으며, 생성될때마다 감산되어야한다.
- 발행가능한지 검증(trigger) 실패시 runtime에러를 낸다.
-
발행가능 갯수는 Treatment의 count로 명시되어있으며, 생성될때마다 감산되어야한다.
- [물건 발행하여 반환]한다.
-
-
환자는 [void setter 구매기능]을 통해 Coordinator(거래대상, 갑) 이외에
구매package정보들
from 발행doctor내부정보와구매 갯수
를 같이 인자로 넘긴다. -
구매기능 내부에서는, 거래의 갑인 Coordinator의 [getter물건 판매기능]을 이용하여 반환받아 저장한다.
- 실패시 NULL객체가 반환되도록 짤 예정이므로 바로 필드에 저장만 하면 된다.
-
coordinator(seller)의 판매기능은 거래 성공의 조건이 if + 로직 + if로 복잡하고 까다롭기 때문에
- 그외 많은 경우가 실패이므로 early return없이 default NULL객체가 반환되도록 미리 반환변수를 NULL객체로 선언하고, 성공의 경우 재할당해주도록 짠다.
- 쿠폰 유무의 경우의 수를 if + else 로 하기 싫다면 if + if 혹은
if-earlyreturn + NoIf
를 선택한다.
-
일반적인 쿠폰이 없는 경우부터 작성한다. Seller가 먼저 상대방의 돈 검증을 시행해서 돈 없으면 컷 해야한다. 그러기 위해선, 돈 검증 전에, 물건(Package)의 가격을 계산해야한다.
-
- 가격계산은 가격정책이 적용될 예정 && fee를 가지고 있는 Specialty객체로 할 수 있다.
-
그러나, specialty를
Coordinator내부
에서 사용할 경우 vs 전달만 할 경우 의존성을 가지냐 안가지냐의 차이를 가지므로specialty를 받아가고, 계산도 할 Reception에게 가격 계산의 책임을 위임
한다. - 구매 물건의 가격을 계산시,
1개당 가격정보를 포함하는 Specialty
+몇개 살 것인지 Count
도 같이 받아야지 총 금액이 계산된다.- 또한, 차후 정책조건의 trigger에서 sequence/time 등을 조건판단 정보로 주려고,
지금은 사용하지 않는 treatment
도 같이 넘겨준다.
- 또한, 차후 정책조건의 trigger에서 sequence/time 등을 조건판단 정보로 주려고,
-
reception의 판매기능 내부에서도 결국 가격은 fee필드를 가진 specialty가 한다.
-
정책이 없다면, specialty는 내부 1개당 가격 X count를 해준다. 나중에 NONE POLICY에서 이걸 반환하면 될 듯 하다.
-
맞는지는 모르겠지만, count만큼 돌면서 money를 더해서 곱하기를 만들었다.
-
-
구매자 돈 검증
-
물건 검증 전에, 물건 떼오기 from Reception
- 물건을 생성해주는 Doctor까지 위해 정보들을 다 전달해줘야한다.
-
Coordinator와 연결된 Reception에게 doctor부터 물건정보 + 갯수까지 다 전달한다.
-
물건을 떼오는 것도, reception입장에서는 getter물건 판매기능으로서, 실패시 NULL객체를 반환, 성공시 정상물건이 온다.
- 이 때, default NULL객체의 물건반환변수에 재할당한다.
-
reception은 앞에서 이미 상대방 돈검증으로 미리 컷 가능하게 했으니, 구매정보 검증을 통해 doctor에게 가기전 컷(NULL객체로 물건반환)할 수 있게한다.
-
3가지 구매정보 검증( A&& B&& C)을 다 통과해야하지, 판매가 진행되므로
-
**not A not B not C** -> early return false대신 NULL객체를 사용한다.
-
-
doctor가 제공하는 isValidMatching
-
treatment가 제공하는 구매가능갯수 검증
-
-
doctor는 [getter물건 판매기능]으로 물건을 만들어서 반환해줘야한다.
-
내부에서는 생성전, 구매정보 검증하여 미리 컷(NULL객체 반환)
- 돈 검증 대신 구매정보 검증한다.
-
발행(생산)전, 구매갯수가능 검증 및 차감
- 물건검증->돈차감 대신 생산가능갯수 검증 및 갯수 차감을 한다. 차감의 책임은 treatment에 있으며, count필드로 조정한다.
-
물건 생성하여 반환
-
-
reception은 떼온 물건을 검증한다.
-
reception은 구매자돈차감(Coordinator)대신 돈 가산(reception-커미션, doctor-나머지 금액)을 한다.
-
recpetion은 물건을 반환한다.
- if 물건검증 통과시만 돈계산이 이루어지고, 내부에서 반환은 안한다.
- if 내부에서하지 않아도 이미 물건떼오기에서 반환받은 물건은
if와 무관하게반환될 물건은 결정된 상황
이기 때문이다. - 반환될 물건은 이미 결정,
if 정상물건일시, 돈계산 추가
- if 내부에서하지 않아도 이미 물건떼오기에서 반환받은 물건은
- if 물건검증 통과시만 돈계산이 이루어지고, 내부에서 반환은 안한다.
-
떼온 물건 검증 후 -> 환자(구매자)의 돈차감
-
쿠폰이 있는 경우는, Coordinator가 어떻게 해야할까
- 돈계산 -> 돈검증안한다.
- 물건 떼오기 -> 물건 검증 -> 돈차감이 아니라 쿠폰차감 with count만큼
-
일단 reception에게 물건을 공짜로 가져온다.
-
reception에서는 doctor에게 발행하여 물건 받아오는 과정이 완전히 동일하기 때문에
- sellPackage 메서드를 그대로 쓴다.
- doctor의 기능은 돈계산이 없이 정보검증 -> 구매가능갯수 차감 -> 발행의 3단계만 거치기 때문이다.
-
reception은 물건검증 성공시 돈차감했었는데, 돈차감이 없으니 물건검증도 생략한다.
-
-
Coordinator에서는 물건 검증이 되면, 돈차감 대신 patient의 쿠폰을 차감한다.
여러개 골랐으면 갯수만큼 차감
해야한다. -
patient는 Coupon coupon = Coupon.EMPTY로 1개 밖에 못들고 있게 설계되었다.
-
여러개 쿠폰을 가질 수 있게 coupon필드를 컬렉션으로 바꿔줘야한다.
- 필드를 바꾸면 getter나 eq/hC도 변경해준다.
- setter도 할당이 아니라 add로 바꿔준다. / remove도 NULL객체 할당에서 remove(0)으로 바꿔준다.
-
컬렉션 필드의 검증은 EMTPY(NULL객체)가 아니라 size로 하도록 다시 다 바꿔줘야한다.
-
-
돈계산 ->
돈검증
대신, 돈검증 자리에구매count만큼 Coupon을 들고 있는지도 검증
한다. -
원래로직을 유지하고 (뒤에 쿠폰없는 상황에 대한 early return이 껴있는 상황)
- 쿠폰 갯수가 모자랄 땐, 에러메세지로 알려주도록 early thr를 던졌다.
- 그대로 두면, 쿠폰갯수가 모자라면 NULL객체로 갈텐데, 그것보다 직접 알려준다.
-
Doctor -> Paitent 쿠폰 주는 것에 대해, 갯수를 정해서 주고, 차감시에도 여러개 차감하게 한다.
-
쿠폰 직접주기 in Doctor by Client
-
쿠폰 차감 in Patient by Coordinator (돈 차감 대신)
-
-
Package와 Coupon을 발행하는 Doctor(생산자)는 Patient(구매자)가 가진 데이터객체(Package)를 확인하는 검증을 한다.
- Doctor는 필드에 무리하게 Many테이블의 정보를 컬렉션으로 모은 상태의 정보전문가로 만들어놨다.
- 원래 DB에서는 Many테이블의 One테이블의 정보를 fk로 가진다.
-
Doctor가 Paitent들의 구매한 Package들을 검증한다.
- Doctor는 필드에 무리하게 Many테이블의 정보를 컬렉션으로 모은 상태의 정보전문가로 만들어놨다.
-
Doctor는 내부정보로 검증할 예정이므로 Patient를 인자로 받아서
-
물건 제공받기 by getter
- 물건 검증(기본) : NULL객체 검증
-
물건 기본정보(필드) 검증 by getter
- 발행권자로 받은 것(Doctor자신)
-
상하위도메인 매칭정보 검증
- Treatment는 사기전 count필드와 사고난 후 count필드가 변한다
-
구매정보 비교시,
구매 전후로 변하는 필드
인 Counteq/hC에서 제외
한다.
- 구매한 갯수 vs 검증할 갯수 검증
-
물건 제공받기 by getter
-
A && B && C && D
의 검증은검증마다 early thr
를 날려서 어떤 것에 검증실패했는지 알려주도록 변경한다.