Transaction.js 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. import Format from "../Format.js";
  2. import Notifier from "../Notifier.js";
  3. export default class Transaction{
  4. constructor(parent, id, iv, date, data){
  5. this._parent = parent;
  6. this._id = id;
  7. this._iv = iv;
  8. this._date = date;
  9. this._category = data.category;
  10. this._categoryId = data.categoryId;
  11. this._amount = data.amount;
  12. this._tags = data.tags;
  13. this._location = data.location;
  14. this._note = data.note;
  15. }
  16. get date(){
  17. return this._date;
  18. }
  19. get category(){
  20. return this._parent.getCategory(this._category, this._categoryId);
  21. }
  22. get rawCategory(){
  23. return this._category;
  24. }
  25. get location(){
  26. return this._location;
  27. }
  28. get amount(){
  29. return Format.centsToDollars(this._amount);
  30. }
  31. get tags(){
  32. return this._tags;
  33. }
  34. get note(){
  35. return this._note;
  36. }
  37. static create(account, date, amount, tags, location, note, category){
  38. let categoryId = null;
  39. if(category !== "discretionary"){
  40. let categorySplit = category.split(":");
  41. category = categorySplit[0];
  42. categoryId = categorySplit[1];
  43. }
  44. return new Transaction(
  45. account,
  46. null,
  47. encryptionHandler.generateIv(),
  48. Format.transactionDate(date),
  49. {
  50. category: category,
  51. categoryId: categoryId,
  52. amount: Format.dollarsToCents(amount),
  53. tags: tags.split(","),
  54. location: location,
  55. note: note
  56. }
  57. );
  58. }
  59. static async fetch(account, from, to){
  60. let response;
  61. try{
  62. response = await fetch("/api/transaction/search", {
  63. method: "POST",
  64. headers: {"Content-Type": "application/json"},
  65. body: JSON.stringify({account, from, to})
  66. });
  67. response = await response.json();
  68. const promises = [];
  69. for(let i = 0; i < response.length; i++){
  70. promises.push(Transaction.decrypt(response[i]));
  71. }
  72. return await Promise.all(promises);
  73. }catch(e){
  74. new Notifier("error", "Something went wrong, try refreshing the page");
  75. }
  76. if(response.error){
  77. new Notifier("error", response.error.message);
  78. return;
  79. }
  80. }
  81. static async decrypt(transaction){
  82. let data = await encryptionHandler.decrypt(transaction.data, transaction.iv);
  83. return new Transaction(
  84. user.account,
  85. transaction.id,
  86. transaction.iv,
  87. transaction.date,
  88. data
  89. );
  90. }
  91. serialize(){
  92. return {
  93. category: this._category,
  94. categoryId: this._categoryId,
  95. amount: this._amount,
  96. tags: this._tags,
  97. location: this._location,
  98. note: this._note
  99. };
  100. }
  101. async save(isNew = false){
  102. const data = await encryptionHandler.encrypt(this.serialize(), this._iv);
  103. let method, body;
  104. if(isNew){
  105. method = "POST";
  106. body = {
  107. account: this._parent.id,
  108. date: this._date,
  109. data: data,
  110. iv: this._iv
  111. };
  112. }
  113. fetch("/api/transaction", {
  114. method: method,
  115. headers: {"Content-Type": "application/json"},
  116. body: JSON.stringify(body)
  117. })
  118. .then(r=>r.json())
  119. .then((response)=>{
  120. if(response.error){
  121. new Notifier("error", response.error.message);
  122. this._parent.removeTransaction(this);
  123. }else{
  124. this._id = response.id;
  125. }
  126. })
  127. .catch((err)=>{
  128. new Notifier("error", "Something went wrong, try refreshing the page");
  129. this._parent.removeTransaction(this);
  130. });
  131. }
  132. }