55
66import javax .validation .Valid ;
77import java .util .List ;
8- import java .util .Random ;
8+ import java .util .Optional ;
9+ import java .util .stream .Collectors ;
910
1011import bitxon .api .model .Account ;
1112import bitxon .api .model .MoneyTransfer ;
13+ import bitxon .micronaut .db .AccountDao ;
14+ import bitxon .micronaut .mapper .AccountMapper ;
1215import io .micronaut .core .annotation .Nullable ;
1316import io .micronaut .http .HttpStatus ;
1417import io .micronaut .http .annotation .Body ;
1821import io .micronaut .http .annotation .PathVariable ;
1922import io .micronaut .http .annotation .Post ;
2023import io .micronaut .http .annotation .Status ;
24+ import io .micronaut .scheduling .TaskExecutors ;
25+ import io .micronaut .scheduling .annotation .ExecuteOn ;
26+ import io .micronaut .transaction .annotation .ReadOnly ;
27+ import io .micronaut .transaction .annotation .TransactionalAdvice ;
28+ import lombok .RequiredArgsConstructor ;
2129
22-
30+ @ ExecuteOn ( TaskExecutors . IO )
2331@ Controller ("/accounts" )
32+ @ RequiredArgsConstructor
2433public class AccountController {
2534
35+ private final AccountDao dao ;
36+ private final AccountMapper mapper ;
37+
2638 @ Get
39+ @ ReadOnly
2740 public List <Account > getAll () {
28- return List .of ();
41+ return dao .findAll ().stream ()
42+ .map (mapper ::mapToApi )
43+ .collect (Collectors .toList ());
2944 }
3045
3146 @ Get ("/{id}" )
47+ @ ReadOnly
3248 public Account getById (@ PathVariable ("id" ) Long id ) {
33- return Account .builder ().id (id ).build ();
49+ return dao .findById (id )
50+ .map (mapper ::mapToApi )
51+ .orElseThrow (() -> new RuntimeException ("Resource not found" ));
3452 }
3553
3654 @ Post
55+ @ TransactionalAdvice
3756 public Account create (@ Body @ Valid Account account ) {
38- return Account .builder ()
39- .id (new Random ().nextLong (0 , Long .MAX_VALUE ))
40- .email (account .getEmail ())
41- .currency (account .getCurrency ())
42- .moneyAmount (account .getMoneyAmount ())
43- .build ();
57+ return Optional .of (account )
58+ .map (mapper ::mapToDb )
59+ .map (dao ::save )
60+ .map (mapper ::mapToApi )
61+ .get ();
4462 }
4563
4664 @ Post ("/transfers" )
4765 @ Status (HttpStatus .NO_CONTENT )
66+ @ TransactionalAdvice
4867 public void create (@ Body @ Valid MoneyTransfer transfer ,
4968 @ Header (value = DIRTY_TRICK_HEADER ) @ Nullable String dirtyTrick ) {
69+ var sender = dao .findById (transfer .getSenderId ())
70+ .orElseThrow (() -> new RuntimeException ("Sender not found" ));
71+
72+ var recipient = dao .findById (transfer .getRecipientId ())
73+ .orElseThrow (() -> new RuntimeException ("Recipient not found" ));
74+
75+ var exchangeRateValue = 1.0d ;
76+ //exchangeClient.getExchangeRate(sender.getCurrency()).getRates().getOrDefault(recipient.getCurrency(), 1.0);
77+
78+ sender .setMoneyAmount (sender .getMoneyAmount () - transfer .getMoneyAmount ());
79+ dao .save (sender );
80+
81+ if (FAIL_TRANSFER .equals (dirtyTrick )) {
82+ throw new RuntimeException ("Error during money transfer" );
83+ }
84+
85+ recipient .setMoneyAmount (recipient .getMoneyAmount () + (int ) (transfer .getMoneyAmount () * exchangeRateValue ));
86+ dao .save (recipient );
5087
5188 }
89+
90+
5291}
0 commit comments