@nyaruka/temba-components 0.16.0 → 0.18.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. package/CHANGELOG.md +29 -0
  2. package/dist/a525ddb7.js +1 -0
  3. package/dist/index.js +1 -1
  4. package/dist/sw.js +1 -1
  5. package/dist/sw.js.map +1 -1
  6. package/dist/templates/components-body.html +1 -1
  7. package/dist/templates/components-head.html +1 -1
  8. package/out-tsc/src/button/Button.js +1 -0
  9. package/out-tsc/src/button/Button.js.map +1 -1
  10. package/out-tsc/src/contacts/ContactChat.js +81 -33
  11. package/out-tsc/src/contacts/ContactChat.js.map +1 -1
  12. package/out-tsc/src/contacts/ContactDetails.js +22 -22
  13. package/out-tsc/src/contacts/ContactDetails.js.map +1 -1
  14. package/out-tsc/src/contacts/ContactHistory.js +132 -139
  15. package/out-tsc/src/contacts/ContactHistory.js.map +1 -1
  16. package/out-tsc/src/contacts/events.js +110 -47
  17. package/out-tsc/src/contacts/events.js.map +1 -1
  18. package/out-tsc/src/interfaces.js.map +1 -1
  19. package/out-tsc/src/list/ContactList.js +32 -17
  20. package/out-tsc/src/list/ContactList.js.map +1 -1
  21. package/out-tsc/src/list/TembaList.js +10 -3
  22. package/out-tsc/src/list/TembaList.js.map +1 -1
  23. package/out-tsc/src/list/TembaMenu.js +7 -2
  24. package/out-tsc/src/list/TembaMenu.js.map +1 -1
  25. package/out-tsc/src/loading/Loading.js +9 -1
  26. package/out-tsc/src/loading/Loading.js.map +1 -1
  27. package/out-tsc/src/options/Options.js +14 -2
  28. package/out-tsc/src/options/Options.js.map +1 -1
  29. package/out-tsc/src/select/Select.js +23 -5
  30. package/out-tsc/src/select/Select.js.map +1 -1
  31. package/out-tsc/src/tip/Tip.js +6 -0
  32. package/out-tsc/src/tip/Tip.js.map +1 -1
  33. package/out-tsc/src/vectoricon/VectorIcon.js +17 -5
  34. package/out-tsc/src/vectoricon/VectorIcon.js.map +1 -1
  35. package/out-tsc/test/temba-contact-history.test.js +2 -2
  36. package/out-tsc/test/temba-contact-history.test.js.map +1 -1
  37. package/package.json +1 -1
  38. package/screenshots/truth/contacts/history-expanded.png +0 -0
  39. package/screenshots/truth/contacts/history.png +0 -0
  40. package/screenshots/truth/list/items-selected.png +0 -0
  41. package/screenshots/truth/list/items-updated.png +0 -0
  42. package/screenshots/truth/list/items.png +0 -0
  43. package/screenshots/truth/modax/simple.png +0 -0
  44. package/screenshots/truth/options/block.png +0 -0
  45. package/screenshots/truth/select/disabled-multi-selection.png +0 -0
  46. package/screenshots/truth/select/disabled-selection.png +0 -0
  47. package/screenshots/truth/select/disabled.png +0 -0
  48. package/screenshots/truth/select/embedded.png +0 -0
  49. package/screenshots/truth/select/expression-selected.png +0 -0
  50. package/screenshots/truth/select/expressions.png +0 -0
  51. package/screenshots/truth/select/functions.png +0 -0
  52. package/screenshots/truth/select/local-options.png +0 -0
  53. package/screenshots/truth/select/remote-options.png +0 -0
  54. package/screenshots/truth/select/search-enabled.png +0 -0
  55. package/screenshots/truth/select/search-multi-no-matches.png +0 -0
  56. package/screenshots/truth/select/search-selected-focus.png +0 -0
  57. package/screenshots/truth/select/search-selected.png +0 -0
  58. package/screenshots/truth/select/search-with-selected.png +0 -0
  59. package/screenshots/truth/select/searching.png +0 -0
  60. package/screenshots/truth/select/selected-multi.png +0 -0
  61. package/screenshots/truth/select/selected-single.png +0 -0
  62. package/screenshots/truth/select/with-placeholder.png +0 -0
  63. package/screenshots/truth/select/without-placeholder.png +0 -0
  64. package/screenshots/truth/textinput/date-form.png +0 -0
  65. package/screenshots/truth/textinput/input-disabled.png +0 -0
  66. package/screenshots/truth/textinput/input-form.png +0 -0
  67. package/screenshots/truth/textinput/input-placeholder.png +0 -0
  68. package/screenshots/truth/textinput/input-updated.png +0 -0
  69. package/screenshots/truth/textinput/input.png +0 -0
  70. package/screenshots/truth/textinput/textarea.png +0 -0
  71. package/screenshots/truth/tip/bottom.png +0 -0
  72. package/screenshots/truth/tip/left.png +0 -0
  73. package/screenshots/truth/tip/right.png +0 -0
  74. package/screenshots/truth/tip/top.png +0 -0
  75. package/src/button/Button.ts +1 -0
  76. package/src/contacts/ContactChat.ts +93 -33
  77. package/src/contacts/ContactDetails.ts +23 -23
  78. package/src/contacts/ContactHistory.ts +157 -160
  79. package/src/contacts/events.ts +117 -48
  80. package/src/interfaces.ts +3 -0
  81. package/src/list/ContactList.ts +39 -20
  82. package/src/list/TembaList.ts +13 -4
  83. package/src/list/TembaMenu.ts +7 -2
  84. package/src/loading/Loading.ts +8 -1
  85. package/src/options/Options.ts +14 -2
  86. package/src/select/Select.ts +28 -6
  87. package/src/tip/Tip.ts +6 -0
  88. package/src/vectoricon/VectorIcon.ts +17 -5
  89. package/test/temba-contact-history.test.ts +2 -2
  90. package/test-assets/style.css +4 -1
  91. package/dist/228cf25e.js +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"ContactHistory.js","sourceRoot":"","sources":["../../../src/contacts/ContactHistory.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,OAAO,EAAE,GAAG,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAC5C,OAAO,EAAE,IAAI,EAAkB,MAAM,UAAU,CAAC;AAChD,OAAO,EAAE,eAAe,EAAU,MAAM,eAAe,CAAC;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAC;AAC/C,OAAO,EAAS,SAAS,EAAE,UAAU,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAC;AAC5E,OAAO,cAAc,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAWL,MAAM,EAEN,iBAAiB,EACjB,cAAc,EAId,6BAA6B,EAC7B,sBAAsB,EACtB,wBAAwB,EACxB,kBAAkB,EAClB,wBAAwB,EACxB,iCAAiC,EACjC,wBAAwB,EACxB,eAAe,EACf,kBAAkB,EAClB,eAAe,EACf,iBAAiB,EACjB,cAAc,EACd,iBAAiB,EACjB,iBAAiB,EACjB,iBAAiB,EACjB,kBAAkB,EAClB,oBAAoB,EACpB,kBAAkB,EAClB,iBAAiB,EACjB,kBAAkB,GAMnB,MAAM,UAAU,CAAC;AAClB,OAAO,EACL,mBAAmB,EACnB,gBAAgB,EAChB,gBAAgB,EAChB,gBAAgB,GACjB,MAAM,WAAW,CAAC;AAEnB,MAAM,OAAO,cAAe,SAAQ,YAAY;IAAhD;;QAGU,gBAAW,GAAG,CAAC,KAAmB,EAAE,EAAE;YAC5C,IAAI,KAAK,CAAC,IAAI,KAAK,MAAM,CAAC,aAAa,EAAE;gBACvC,MAAM,MAAM,GAAG,IAAI,CAAC,iBAAiB,CAAC,KAAoB,CAAC,CAAC;gBAC5D,IAAI,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,MAAM,EAAE;oBACtC,OAAO,MAAM,CAAC,IAAI,CAAC;iBACpB;aACF;QACH,CAAC,CAAC;QA4HF,gBAAW,GAAiB,EAAE,CAAC;QAG/B,eAAU,GAAG,KAAK,CAAC;QAGnB,aAAQ,GAAG,KAAK,CAAC;QAGjB,aAAQ,GAAG,KAAK,CAAC;QAMjB,UAAK,GAAG,KAAK,CAAC;QAGd,qBAAgB,GAAG,KAAK,CAAC;QAMzB,WAAM,GAAW,IAAI,CAAC;QAGtB,YAAO,GAAW,IAAI,CAAC;QAGvB,YAAO,GAAa,IAAI,CAAC;QAGzB,kBAAa,GAAW,IAAI,CAAC;QAE7B,iBAAY,GAAoC,EAAE,CAAC;QAInD,eAAU,GAAG,CAAC,CAAC;QAEf,mBAAc,GAAQ,IAAI,CAAC;QAC3B,UAAK,GAAG,KAAK,CAAC;IAsvBhB,CAAC;IA15BS,iBAAiB,CAAC,KAAkB;QAC1C,OAAO,IAAI,CAAC,SAAS,CAAE,KAAqB,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IAC5D,CAAC;IAEO,SAAS,CAAC,IAAY;QAC5B,OAAO,CAAC,IAAI,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,IAAI,KAAK,IAAI,CAAC,CAAC;IACnE,CAAC;IAED,MAAM,KAAK,MAAM;QACf,OAAO,GAAG,CAAA;QACN,cAAc,EAAE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAsGnB,CAAC;IACJ,CAAC;IAqDM,YAAY,CAAC,iBAAmC;QACrD,KAAK,CAAC,YAAY,CAAC,iBAAiB,CAAC,CAAC;QAEtC,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAE/C,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;QAC7C,MAAM,OAAO,GAAG,IAAI,cAAc,CAAC,OAAO,CAAC,EAAE;YAC3C,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE;gBAC3B,MAAM,cAAc,GAAG,KAAK,CAAC,WAAW,CAAC;gBACzC,SAAS,CAAC,KAAK,CAAC,KAAK;oBACnB,cAAc,CAAC,KAAK,GAAG,cAAc,CAAC,IAAI,GAAG,EAAE,GAAG,IAAI,CAAC;aAC1D;QACH,CAAC,CAAC,CAAC;QACH,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACxB,CAAC;IAEM,OAAO,CAAC,iBAAmC;QAChD,KAAK,CAAC,OAAO,CAAC,iBAAiB,CAAC,CAAC;QAEjC,gDAAgD;QAChD,IAAI,iBAAiB,CAAC,GAAG,CAAC,eAAe,CAAC,EAAE;YAC1C,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,cAAc,EAAE;gBACnD,OAAO,EAAE,IAAI,CAAC,aAAa;aAC5B,CAAC,CAAC;SACJ;QAED,sCAAsC;QACtC,IAAI,iBAAiB,CAAC,GAAG,CAAC,iBAAiB,CAAC,EAAE;YAC5C,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,SAAS,CAAC,CAAC;SACjD;QAED,yCAAyC;QACzC,IAAI,iBAAiB,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE;YACjC,IAAI,IAAI,CAAC,IAAI,IAAI,IAAI,EAAE;gBACrB,IAAI,CAAC,KAAK,EAAE,CAAC;aACd;iBAAM;gBACL,MAAM,QAAQ,GAAG,oBAAoB,IAAI,CAAC,IAAI,gBAAgB,CAAC;gBAE/D,IAAI,IAAI,CAAC,QAAQ,KAAK,QAAQ,EAAE;oBAC9B,IAAI,CAAC,KAAK,EAAE,CAAC;oBAEb,IAAI,IAAI,CAAC,OAAO,EAAE;wBAChB,MAAM,MAAM,GAAG,IAAI,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;wBACtC,IAAI,CAAC,UAAU,GAAG,MAAM,CAAC,OAAO,EAAE,GAAG,IAAI,GAAG,IAAI,CAAC;qBAClD;oBAED,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;oBACzB,IAAI,CAAC,cAAc,EAAE,CAAC;iBACvB;aACF;SACF;QAED,IAAI,iBAAiB,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE;YACnC,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;YACrB,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC;SAC5B;QAED,IACE,iBAAiB,CAAC,GAAG,CAAC,YAAY,CAAC;YACnC,IAAI,CAAC,UAAU;YACf,IAAI,CAAC,QAAQ,EACb;YACA,MAAM,KAAK,GAAG,CAAC,IAAI,CAAC,gBAAgB,EAAE,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC;YACnD,IAAI,SAAS,GAAG,KAAK,CAAC;YAEtB,mBAAmB,CAAC,KAAK,EAAE,IAAI,CAAC,QAAQ,EAAE,IAAI,CAAC,MAAM,EAAE,IAAI,EAAE,KAAK,CAAC;iBAChE,IAAI,CAAC,CAAC,OAA2B,EAAE,EAAE;gBACpC,IAAI,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE;oBAC/C,IAAI,CAAC,gBAAgB,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;iBAC1C;gBAED,kCAAkC;gBAClC,OAAO,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,KAAmB,EAAE,EAAE;oBAC7C,IAAI,KAAK,CAAC,IAAI,KAAK,MAAM,CAAC,aAAa,EAAE;wBACvC,MAAM,WAAW,GAAG,KAAoB,CAAC;wBACzC,IAAI,CAAC,YAAY,CAAC,WAAW,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,WAAW,CAAC;qBAC1D;gBACH,CAAC,CAAC,CAAC;gBAEH,IAAI,aAAa,GAAG,OAAO,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC;gBAE7C,2CAA2C;gBAC3C,8CAA8C;gBAC9C,aAAa,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE;oBAC1C,MAAM,KAAK,GAAG,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,IAAI,CACnC,CAAC,CAAC,EAAE,CACF,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CACb,MAAM,CAAC,EAAE,CACP,MAAM,CAAC,UAAU,KAAK,IAAI,CAAC,UAAU;wBACrC,MAAM,CAAC,IAAI,KAAK,IAAI,CAAC,IAAI,CAC5B,CACJ,CAAC;oBAEF,OAAO,CAAC,KAAK,CAAC;gBAChB,CAAC,CAAC,CAAC;gBAEH,IAAI,CAAC,gBAAgB,GAAG,aAAa,CAAC,MAAM,CAAC;gBAE7C,2EAA2E;gBAC3E,MAAM,cAAc,GAAG,CAAC,GAAG,IAAI,CAAC,WAAW,CAAC,CAAC;gBAE7C,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;oBAC/B,MAAM,MAAM,GAAG,cAAc,CAAC,MAAM,CAClC,cAAc,CAAC,MAAM,GAAG,CAAC,EACzB,CAAC,CACF,CAAC,CAAC,CAAC,CAAC;oBAEL,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC;oBACxB,aAAa,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;iBAC9C;gBAED,MAAM,OAAO,GAAG,IAAI,CAAC,cAAc,CAAC,aAAa,CAAC,CAAC;gBACnD,IAAI,OAAO,CAAC,MAAM,EAAE;oBAClB,IAAI,SAAS,EAAE;wBACb,OAAO,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,IAAI,GAAG,SAAS,CAAC;qBAC9C;oBAED,IAAI,CAAC,WAAW,GAAG,CAAC,GAAG,cAAc,EAAE,GAAG,OAAO,CAAC,CAAC;iBACpD;gBACD,IAAI,CAAC,UAAU,GAAG,KAAK,CAAC;gBACxB,IAAI,CAAC,eAAe,EAAE,CAAC;YACzB,CAAC,CAAC;iBACD,KAAK,CAAC,GAAG,EAAE;gBACV,IAAI,CAAC,UAAU,GAAG,KAAK,CAAC;gBACxB,IAAI,CAAC,eAAe,EAAE,CAAC;YACzB,CAAC,CAAC,CAAC;SACN;QAED,IAAI,iBAAiB,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,IAAI,CAAC,QAAQ,EAAE;YACtD,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE;gBACpB,IAAI,CAAC,UAAU,GAAG,IAAI,IAAI,EAAE,CAAC,OAAO,EAAE,GAAG,IAAI,GAAG,IAAI,CAAC;aACtD;YAED,IAAI,CAAC,YAAY,GAAG,mBAAmB,CACrC,IAAI,CAAC,KAAK,EACV,IAAI,CAAC,QAAQ,EACb,IAAI,CAAC,MAAM,EACX,IAAI,CAAC,UAAU,EACf,IAAI,CAAC,SAAS,CACf,CAAC,IAAI,CAAC,CAAC,OAA2B,EAAE,EAAE;gBACrC,6BAA6B;gBAC7B,IAAI,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE;oBAC/C,IAAI,CAAC,gBAAgB,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;oBAEzC,kCAAkC;oBAClC,OAAO,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,KAAmB,EAAE,EAAE;wBAC7C,IAAI,KAAK,CAAC,IAAI,KAAK,MAAM,CAAC,aAAa,EAAE;4BACvC,MAAM,WAAW,GAAG,KAAoB,CAAC;4BACzC,IAAI,CAAC,YAAY,CAAC,WAAW,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,WAAW,CAAC;yBAC1D;oBACH,CAAC,CAAC,CAAC;iBACJ;gBAED,IAAI,SAAS,GAAG,KAAK,CAAC;gBACtB,MAAM,aAAa,GAAG,OAAO,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC;gBAE/C,oEAAoE;gBACpE,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;oBAC/B,MAAM,MAAM,GAAG,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;oBAChD,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC;oBACxB,aAAa,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;iBACtC;gBAED,MAAM,OAAO,GAAG,IAAI,CAAC,cAAc,CAAC,aAAa,CAAC,CAAC;gBACnD,IAAI,OAAO,CAAC,MAAM,EAAE;oBAClB,IAAI,SAAS,EAAE;wBACb,OAAO,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,IAAI,GAAG,SAAS,CAAC;qBAC9C;oBAED,IAAI,CAAC,WAAW,GAAG,CAAC,GAAG,OAAO,EAAE,GAAG,IAAI,CAAC,WAAW,CAAC,CAAC;iBACtD;gBAED,IAAI,OAAO,CAAC,WAAW,KAAK,IAAI,CAAC,UAAU,EAAE;oBAC3C,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;iBACtB;gBAED,IAAI,CAAC,UAAU,GAAG,OAAO,CAAC,WAAW,CAAC;gBACtC,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,UAAU,CAAC;gBACpC,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;gBACtB,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;YACrB,CAAC,CAAC,CAAC;SACJ;QAED,IAAI,iBAAiB,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE;YAC3D,IAAI,IAAI,CAAC,gBAAgB,GAAG,CAAC,EAAE;gBAC7B,MAAM,MAAM,GAAG,IAAI,CAAC,aAAa,EAAE,CAAC;gBACpC,qEAAqE;gBACrE,IAAI,IAAI,CAAC,UAAU,GAAG,CAAC,EAAE;oBACvB,MAAM,WAAW,GAAG,MAAM,CAAC,YAAY,GAAG,IAAI,CAAC,UAAU,CAAC;oBAE1D,MAAM,kBAAkB,GACtB,MAAM,CAAC,YAAY;wBACnB,MAAM,CAAC,SAAS;wBAChB,WAAW;wBACX,MAAM,CAAC,YAAY,CAAC;oBAEtB,IAAI,kBAAkB,GAAG,GAAG,EAAE;wBAC5B,IAAI,CAAC,cAAc,EAAE,CAAC;qBACvB;yBAAM;wBACL,IAAI,CAAC,gBAAgB,GAAG,IAAI,CAAC;qBAC9B;iBACF;gBAED,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;oBAC/B,IAAI,CAAC,UAAU,GAAG,MAAM,CAAC,YAAY,CAAC;iBACvC;aACF;SACF;QAED,IACE,iBAAiB,CAAC,GAAG,CAAC,UAAU,CAAC;YACjC,CAAC,IAAI,CAAC,QAAQ;YACd,iBAAiB,CAAC,GAAG,CAAC,UAAU,CAAC,KAAK,SAAS,EAC/C;YACA,MAAM,MAAM,GAAG,IAAI,CAAC,aAAa,EAAE,CAAC;YAEpC,IAAI,IAAI,CAAC,UAAU,IAAI,MAAM,CAAC,YAAY,GAAG,IAAI,CAAC,UAAU,EAAE;gBAC5D,MAAM,SAAS,GACb,MAAM,CAAC,SAAS,GAAG,MAAM,CAAC,YAAY,GAAG,IAAI,CAAC,UAAU,CAAC;gBAC3D,MAAM,CAAC,SAAS,GAAG,SAAS,CAAC;aAC9B;YAED,+CAA+C;YAC/C,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE;gBACpB,IAAI,CAAC,cAAc,EAAE,CAAC;aACvB;YAED,uDAAuD;YACvD,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;gBAC/B,IAAI,CAAC,UAAU,GAAG,MAAM,CAAC,YAAY,CAAC;aACvC;SACF;QAED,IAAI,iBAAiB,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,IAAI,CAAC,QAAQ,EAAE;YACtD,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;YACrB,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC;SACnB;QAED,mEAAmE;QACnE,IAAI,iBAAiB,CAAC,GAAG,CAAC,SAAS,CAAC,EAAE;YACpC,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;YAE7C,MAAM,aAAa,GAAG,CAAC,IAAI,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC,MAAM,CAC/C,MAAM,CAAC,EAAE,CAAC,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,QAAQ,CAC/C,CAAC;YAEF,KAAK,MAAM,MAAM,IAAI,aAAa,EAAE;gBAClC,MAAM,KAAK,GAAG,SAAS,CAAC,aAAa,CACnC,oBAAoB,MAAM,CAAC,IAAI,IAAI,CACpC,CAAC;gBACF,IAAI,KAAK,EAAE;oBACT,SAAS,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC;iBAC9B;aACF;YACD,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE;gBACvB,IAAI,CAAC,mBAAmB,EAAE,CAAC;aAC5B;SACF;IACH,CAAC;IAEO,mBAAmB;QACzB,MAAM,WAAW,GAAG,CAAC,IAAI,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC,MAAM,CAC7C,MAAM,CAAC,EAAE,CAAC,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,MAAM,CAC7C,CAAC;QACF,IAAI,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;YAC1B,IAAI,CAAC,aAAa,GAAG,WAAW,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;SAC1D;IACH,CAAC;IAEO,cAAc;QACpB,IAAI,GAAG,GAAG,gCAAgC,IAAI,CAAC,IAAI,EAAE,CAAC;QACtD,IAAI,IAAI,CAAC,MAAM,EAAE;YACf,GAAG,GAAG,GAAG,GAAG,WAAW,IAAI,CAAC,MAAM,EAAE,CAAC;SACtC;QAED,SAAS,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,OAAiB,EAAE,EAAE;YACxC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;QACnC,CAAC,CAAC,CAAC;IACL,CAAC;IAEM,aAAa;QAClB,OAAO,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;IAChC,CAAC;IAEM,cAAc,CAAC,MAAM,GAAG,KAAK;QAClC,MAAM,MAAM,GAAG,IAAI,CAAC,aAAa,EAAE,CAAC;QACpC,MAAM,CAAC,QAAQ,CAAC;YACd,GAAG,EAAE,MAAM,CAAC,YAAY;YACxB,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM;SACrC,CAAC,CAAC;QACH,IAAI,CAAC,gBAAgB,GAAG,KAAK,CAAC;QAE9B,MAAM,CAAC,UAAU,CAAC,GAAG,EAAE;YACrB,MAAM,CAAC,QAAQ,CAAC;gBACd,GAAG,EAAE,MAAM,CAAC,YAAY;gBACxB,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM;aACrC,CAAC,CAAC;QACL,CAAC,EAAE,CAAC,CAAC,CAAC;IACR,CAAC;IAEM,OAAO;QACZ,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC;IAC5B,CAAC;IAEO,cAAc,CAAC,MAAsB;QAC3C,MAAM,OAAO,GAAiB,EAAE,CAAC;QACjC,IAAI,UAAU,GAAe,SAAS,CAAC;QACvC,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE;YAC1B,MAAM,qBAAqB,GAAG,iBAAiB,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;YACpE,mCAAmC;YACnC,IAAI,CAAC,UAAU,IAAI,UAAU,CAAC,IAAI,KAAK,qBAAqB,EAAE;gBAC5D,0CAA0C;gBAC1C,IAAI,UAAU,EAAE;oBACd,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;iBAC1B;gBACD,UAAU,GAAG;oBACX,IAAI,EAAE,KAAK;oBACX,OAAO,EAAE,KAAK;oBACd,MAAM,EAAE,CAAC,KAAK,CAAC;oBACf,IAAI,EAAE,qBAAqB;iBAC5B,CAAC;aACH;iBAAM;gBACL,yDAAyD;gBACzD,UAAU,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;aAC/B;SACF;QAED,IAAI,UAAU,IAAI,UAAU,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE;YAC9C,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;SAC1B;QACD,OAAO,OAAO,CAAC;IACjB,CAAC;IAEO,eAAe,CAAC,IAAI,GAAG,CAAC,CAAC;QAC/B,IAAI,WAAW,GAAG,IAAI,CAAC;QAEvB,IAAI,IAAI,KAAK,CAAC,CAAC,EAAE;YACf,MAAM,aAAa,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;YAC9C,WAAW,GAAG,IAAI,CAAC,GAAG,CACpB,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,IAAI,EAAE,CAAC,OAAO,EAAE,GAAG,aAAa,CAAC,GAAG,CAAC,EAAE,gBAAgB,CAAC,EACtE,gBAAgB,CACjB,CAAC;SACH;QAED,iCAAiC;QACjC,IAAI,IAAI,GAAG,CAAC,CAAC,IAAI,IAAI,CAAC,cAAc,EAAE;YACpC,MAAM,CAAC,YAAY,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;SAC1C;QAED,IAAI,CAAC,cAAc,GAAG,MAAM,CAAC,UAAU,CAAC,GAAG,EAAE;YAC3C,IAAI,IAAI,CAAC,UAAU,EAAE;gBACnB,IAAI,CAAC,eAAe,EAAE,CAAC;gBACvB,IAAI,CAAC,UAAU,GAAG,KAAK,CAAC;aACzB;iBAAM;gBACL,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC;aACxB;QACH,CAAC,EAAE,WAAW,CAAC,CAAC;IAClB,CAAC;IAEO,KAAK;QACX,yDAAyD;QACzD,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;QAC7C,OAAO,SAAS,CAAC,iBAAiB,GAAG,CAAC,EAAE;YACtC,SAAS,CAAC,WAAW,CAAC,SAAS,CAAC,iBAAiB,CAAC,CAAC;SACpD;QAED,IAAI,CAAC,aAAa,GAAG,IAAI,CAAC;QAC1B,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;QACrB,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;QACpB,IAAI,CAAC,YAAY,GAAG,EAAE,CAAC;QACvB,IAAI,CAAC,WAAW,GAAG,EAAE,CAAC;QACtB,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;QACtB,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;QACtB,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC;QACvB,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;QACtB,IAAI,CAAC,UAAU,GAAG,CAAC,CAAC;IACtB,CAAC;IAEO,oBAAoB,CAAC,KAAiB;QAC5C,MAAM,QAAQ,GAAG,KAAK,CAAC,aAA+B,CAAC;QACvD,MAAM,UAAU,GAAG,QAAQ,CAAC,QAAQ,CAAC,YAAY,CAAC,kBAAkB,CAAC,CAAC,CAAC;QACvE,MAAM,UAAU,GAAG,IAAI,CAAC,WAAW,CACjC,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,UAAU,GAAG,CAAC,CACzC,CAAC;QACF,UAAU,CAAC,IAAI,GAAG,IAAI,CAAC;QACvB,IAAI,CAAC,aAAa,CAAC,aAAa,CAAC,CAAC;IACpC,CAAC;IAEO,oBAAoB,CAAC,KAAiB;QAC5C,MAAM,QAAQ,GAAG,KAAK,CAAC,aAA+B,CAAC;QACvD,MAAM,UAAU,GAAG,QAAQ,CAAC,QAAQ,CAAC,YAAY,CAAC,kBAAkB,CAAC,CAAC,CAAC;QACvE,MAAM,UAAU,GAAG,IAAI,CAAC,WAAW,CACjC,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,UAAU,GAAG,CAAC,CACzC,CAAC;QAEF,qBAAqB;QACrB,UAAU,CAAC,OAAO,GAAG,IAAI,CAAC;QAC1B,IAAI,CAAC,aAAa,CAAC,aAAa,CAAC,CAAC;QAElC,4CAA4C;QAC5C,UAAU,CAAC,GAAG,EAAE;YACd,UAAU,CAAC,OAAO,GAAG,KAAK,CAAC;YAC3B,UAAU,CAAC,IAAI,GAAG,KAAK,CAAC;YACxB,IAAI,CAAC,aAAa,CAAC,aAAa,CAAC,CAAC;QACpC,CAAC,EAAE,GAAG,CAAC,CAAC;IACV,CAAC;IAEO,YAAY;QAClB,MAAM,MAAM,GAAG,IAAI,CAAC,aAAa,EAAE,CAAC;QAEpC,yDAAyD;QACzD,MAAM,QAAQ,GAAG,IAAI,CAAC,aAAa,EAAE,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC;QAClE,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;QAE7C,QAAQ,CAAC,OAAO,CAAC,CAAC,MAAsB,EAAE,EAAE;YAC1C,MAAM,cAAc,GAAG,MAAM,CAAC,SAAS,GAAG,SAAS,CAAC,YAAY,GAAG,GAAG,CAAC;YACvE,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE;gBACxC,MAAM,YAAY,GAAG,MAAM,CAAC,iBAAmC,CAAC;gBAChE,IAAI,cAAc,GAAG,MAAM,CAAC,SAAS,EAAE;oBACrC,MAAM,CAAC,KAAK,CAAC,MAAM,GAAG,YAAY,CAAC,YAAY,GAAG,IAAI,CAAC;oBACvD,MAAM,CAAC,SAAS,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;oBAC9B,MAAc,CAAC,YAAY,GAAG,YAAY,CAAC;oBAC5C,SAAS,CAAC,WAAW,CAAC,YAAY,CAAC,CAAC;oBACpC,MAAM,IAAI,GAAG,YAAY,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC;oBACzD,MAAM,MAAM,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;oBACpC,IAAI,MAAM,EAAE;wBACV,IACE,CAAC,IAAI,CAAC,aAAa;4BACnB,IAAI,CAAC,aAAa,CAAC,IAAI,KAAK,MAAM,CAAC,IAAI,EACvC;4BACA,IAAI,CAAC,aAAa,GAAG,MAAM,CAAC;yBAC7B;qBACF;iBACF;aACF;iBAAM;gBACL,MAAM,YAAY,GAAI,MAAc,CAAC,YAAY,CAAC;gBAClD,IAAI,cAAc,GAAG,MAAM,CAAC,SAAS,GAAG,MAAM,CAAC,YAAY,EAAE;oBAC3D,MAAM,CAAC,WAAW,CAAC,YAAY,CAAC,CAAC;oBACjC,MAAM,CAAC,SAAS,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;oBAElC,MAAM,IAAI,GAAG,YAAY,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC;oBACzD,IAAI,cAAc,GAAW,IAAI,CAAC;oBAClC,KAAK,MAAM,MAAM,IAAI,IAAI,CAAC,OAAO,EAAE;wBACjC,IAAI,MAAM,CAAC,IAAI,KAAK,IAAI,EAAE;4BACxB,MAAM;yBACP;wBACD,cAAc,GAAG,MAAM,CAAC;qBACzB;oBAED,IACE,cAAc;wBACd,CAAC,CAAC,IAAI,CAAC,aAAa;4BAClB,IAAI,CAAC,aAAa,CAAC,IAAI,KAAK,cAAc,CAAC,IAAI,CAAC,EAClD;wBACA,IAAI,cAAc,CAAC,MAAM,KAAK,MAAM,EAAE;4BACpC,IAAI,CAAC,aAAa,GAAG,cAAc,CAAC;yBACrC;6BAAM;4BACL,IAAI,CAAC,aAAa,GAAG,IAAI,CAAC;yBAC3B;qBACF;iBACF;aACF;QACH,CAAC,CAAC,CAAC;QAEH,IAAI,MAAM,CAAC,SAAS,IAAI,gBAAgB,EAAE;YACxC,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE;gBACnE,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;aACtB;SACF;IACH,CAAC;IAEO,gBAAgB,CAAC,QAAsB;QAC7C,IACE,CAAC,IAAI,CAAC,eAAe;YACrB,IAAI,CAAC,eAAe,CAAC,IAAI,KAAK,QAAQ,CAAC,IAAI;YAC3C,IAAI,CAAC,eAAe,CAAC,UAAU,KAAK,QAAQ,CAAC,UAAU,EACvD;YACA,IAAI,CAAC,eAAe,GAAG,QAAQ,CAAC;SACjC;IACH,CAAC;IAEO,gBAAgB;QACtB,MAAM,eAAe,GAAG,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;QACtE,IAAI,eAAe,EAAE;YACnB,MAAM,eAAe,GACnB,eAAe,CAAC,MAAM,CAAC,eAAe,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;YAC5D,OAAO,IAAI,IAAI,CAAC,eAAe,CAAC,UAAU,CAAC,CAAC,OAAO,EAAE,CAAC;SACvD;QACD,OAAO,CAAC,CAAC;IACX,CAAC;IAEM,WAAW,CAAC,KAAmB;QACpC,QAAQ,KAAK,CAAC,IAAI,EAAE;YAClB,KAAK,MAAM,CAAC,WAAW,CAAC;YACxB,KAAK,MAAM,CAAC,eAAe,CAAC;YAC5B,KAAK,MAAM,CAAC,gBAAgB,CAAC;YAC7B,KAAK,MAAM,CAAC,iBAAiB;gBAC3B,OAAO,cAAc,CAAC,KAAiB,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC;YAEvD,KAAK,MAAM,CAAC,YAAY,CAAC;YACzB,KAAK,MAAM,CAAC,WAAW;gBACrB,OAAO,eAAe,CAAC,KAAkB,CAAC,CAAC;YAE7C,KAAK,MAAM,CAAC,kBAAkB;gBAC5B,OAAO,iBAAiB,CAAC,KAA0B,CAAC,CAAC;YAEvD,KAAK,MAAM,CAAC,qBAAqB;gBAC/B,OAAO,iBAAiB,CAAC,KAAyB,CAAC,CAAC;YAEtD,KAAK,MAAM,CAAC,oBAAoB;gBAC9B,OAAO,iBAAiB,CAAC,KAAyB,CAAC,CAAC;YAEtD,KAAK,MAAM,CAAC,oBAAoB;gBAC9B,OAAO,wBAAwB,CAAC,KAAyB,CAAC,CAAC;YAE7D,KAAK,MAAM,CAAC,UAAU;gBACpB,OAAO,eAAe,CAAC,KAAuB,CAAC,CAAC;YAElD,KAAK,MAAM,CAAC,kBAAkB;gBAC5B,OAAO,iBAAiB,CAAC,KAAyB,CAAC,CAAC;YAEtD,KAAK,MAAM,CAAC,aAAa,CAAC,CAAC;gBACzB,MAAM,WAAW,GAAG,KAAoB,CAAC;gBACzC,MAAM,YAAY,GAChB,CAAC,IAAI,CAAC,MAAM,IAAI,WAAW,CAAC,MAAM,CAAC,IAAI,KAAK,IAAI,CAAC,MAAM,CAAC;gBAE1D,IAAI,YAAY,GAAG,IAAI,CAAC;gBACxB,MAAM,MAAM,GAAG,IAAI,CAAC,iBAAiB,CAAC,WAAW,CAAC,CAAC;gBACnD,IAAI,YAAY,IAAI,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,MAAM,EAAE;oBACtD,YAAY,GAAG,IAAI,CAAC,WAAW,CAAC;iBACjC;gBACD,OAAO,kBAAkB,CAAC,WAAW,EAAE,YAAY,CAAC,CAAC;aACtD;YACD,KAAK,MAAM,CAAC,iBAAiB;gBAC3B,OAAO,iBAAiB,CAAC,KAAoB,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC;YAE7D,KAAK,MAAM,CAAC,eAAe;gBACzB,OAAO,oBAAoB,CAAC,KAAoB,CAAC,CAAC;YACpD,KAAK,MAAM,CAAC,eAAe,CAAC,CAAC;gBAC3B,OAAO,kBAAkB,CAAC,KAAoB,EAAE,UAAU,CAAC,CAAC;aAC7D;YACD,KAAK,MAAM,CAAC,aAAa;gBACvB,OAAO,kBAAkB,CAAC,KAAoB,EAAE,QAAQ,CAAC,CAAC;YAE5D,KAAK,MAAM,CAAC,KAAK,CAAC;YAClB,KAAK,MAAM,CAAC,OAAO;gBACjB,OAAO,kBAAkB,CAAC,KAA0B,CAAC,CAAC;YACxD,KAAK,MAAM,CAAC,sBAAsB;gBAChC,OAAO,wBAAwB,CAAC,KAA2B,CAAC,CAAC;YAC/D,KAAK,MAAM,CAAC,cAAc;gBACxB,OAAO,kBAAkB,CAAC,KAAqB,CAAC,CAAC;YACnD,KAAK,MAAM,CAAC,mBAAmB;gBAC7B,OAAO,6BAA6B,CAAC,KAAgC,CAAC,CAAC;YACzE,KAAK,MAAM,CAAC,YAAY;gBACtB,OAAO,sBAAsB,EAAE,CAAC;YAClC,KAAK,MAAM,CAAC,cAAc;gBACxB,OAAO,wBAAwB,CAAC,KAA2B,CAAC,CAAC;YAC/D,KAAK,MAAM,CAAC,aAAa;gBACvB,OAAO,kBAAkB,CAAC,KAAqB,CAAC,CAAC;YACnD,KAAK,MAAM,CAAC,wBAAwB;gBAClC,OAAO,iCAAiC,CACtC,KAAoC,CACrC,CAAC;SACL;QAED,OAAO,IAAI,CAAA;;;;iCAIkB,KAAK,CAAC,IAAI,QAAQ,CAAC;IAClD,CAAC;IAEO,WAAW,CAAC,IAAY;QAC9B,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,6BAA6B,IAAI,EAAE,EAAE;YAChE,MAAM,EAAE,QAAQ;SACjB,CAAC;aACC,IAAI,CAAC,GAAG,EAAE;YACT,IAAI,CAAC,cAAc,EAAE,CAAC;YACtB,IAAI,CAAC,OAAO,EAAE,CAAC;YACf,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,cAAc,EAAE;gBACnD,MAAM,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE;aACnC,CAAC,CAAC;YACH,IAAI,CAAC,mBAAmB,EAAE,CAAC;QAC7B,CAAC,CAAC;aACD,KAAK,CAAC,CAAC,QAAa,EAAE,EAAE;YACvB,OAAO,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QAC1B,CAAC,CAAC,CAAC;IACP,CAAC;IAEM,4BAA4B,CAAC,KAAa;QAC/C,IAAI,IAAI,CAAC,aAAa,EAAE;YACtB,IAAI,CAAC,YAAY,GAAG,SAAS,CAC3B,+BAA+B,IAAI,CAAC,aAAa,CAAC,IAAI,EAAE,CACzD,CAAC,IAAI,CAAC,CAAC,MAAe,EAAE,EAAE;gBACzB,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE;oBACvB,MAAM,MAAM,GAAG,MAAM,CAAC,CAAC,CAAW,CAAC;oBACnC,IAAI,MAAM,CAAC,QAAQ,IAAI,MAAM,CAAC,QAAQ,CAAC,EAAE,KAAK,KAAK,EAAE;wBACnD,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,cAAc,EAAE;4BACnD,MAAM,EAAE,EAAE,IAAI,EAAE,IAAI,CAAC,aAAa,CAAC,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE;yBAC5D,CAAC,CAAC;qBACJ;yBAAM;wBACL,IAAI,CAAC,eAAe,CAAC,eAAe,CAAC,cAAc,EAAE;4BACnD,MAAM,EAAE,EAAE,IAAI,EAAE,IAAI,CAAC,aAAa,CAAC,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE;yBAC7D,CAAC,CAAC;qBACJ;iBACF;YACH,CAAC,CAAC,CAAC;SACJ;IACH,CAAC;IAEM,gBAAgB;QACrB,OAAO;YACL;gBACE,KAAK,EAAE,QAAQ;gBACf,MAAM,EAAE,QAAQ,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,CAAC;aACxC;SACF,CAAC;IACJ,CAAC;IAED,oEAAoE;IAC5D,QAAQ,CAAC,MAAc;QAC7B,OAAO,CAAC,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IACzC,CAAC;IAEO,oBAAoB,CAAC,KAAmB;QAC9C,MAAM,QAAQ,GAAG,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC;QACzC,MAAM,QAAQ,GAAG,CAAC,CAAC,QAAQ,CAAC;QAE5B,MAAM,aAAa,GAAG,IAAI,CAAA;;uBAEP,KAAK,CAAC,IAAI,IAAI,QAAQ,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,EAAE;0BACvC,QAAQ;;UAExB,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC;;QAEzB,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAA,QAAQ,IAAI,CAAC,SAAS,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI;KACzE,CAAC;QAEF,IAAI,QAAQ,EAAE;YACZ,OAAO,IAAI,CAAA,uBAAuB,aAAa,QAAQ,CAAC;SACzD;QAED,OAAO,aAAa,CAAC;IACvB,CAAC;IAEM,MAAM;QACX,0CAA0C;QAC1C,MAAM,gBAAgB,GACpB,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,IAAI,IAAI,CAAC,OAAO;YACzC,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,MAAc,EAAE,EAAE;gBAClC,IAAI,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,MAAM,EAAE;oBACtC,MAAM,MAAM,GAAG,IAAI,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,OAAO,EAAE,GAAG,IAAI,CAAC;oBAC3D,IAAI,MAAM,GAAG,IAAI,CAAC,UAAU,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE;wBACrD,MAAM,iBAAiB,GAAG;4BACxB,IAAI,EAAE,MAAM,CAAC,aAAa;4BAC1B,MAAM,EAAE;gCACN,IAAI,EAAE,MAAM,CAAC,IAAI;gCACjB,OAAO,EAAE,MAAM,CAAC,OAAO;gCACvB,IAAI,EAAE,MAAM,CAAC,IAAI;gCACjB,QAAQ,EAAE,MAAM,CAAC,QAAQ;6BAC1B;4BACD,wDAAwD;4BACxD,UAAU,EAAE,MAAM,CAAC,SAAS;yBAC7B,CAAC;wBAEF,MAAM,aAAa,GAAG,kBAAkB,CACtC,iBAAiB,EACjB,IAAI,CAAC,WAAW,CACjB,CAAC;wBACF,OAAO,IAAI,CAAA;oBACP,aAAa;uBACV,CAAC;qBACT;iBACF;YACH,CAAC,CAAC;YACJ,CAAC,CAAC,IAAI,CAAC;QAEX,OAAO,IAAI,CAAA;gCACiB,gBAAgB;QACxC,IAAI,CAAC,QAAQ;YACb,CAAC,CAAC,IAAI,CAAA,qDAAqD;YAC3D,CAAC,CAAC,IAAI,CAAA,gCAAgC;oCACV,IAAI,CAAC,YAAY;UAC3C,IAAI,CAAC,OAAO;YACZ,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,UAAsB,EAAE,KAAa,EAAE,EAAE;gBAC7D,MAAM,QAAQ,GAAG,iBAAiB,CAChC,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,EACpB,IAAI,CAAC,MAAM,CACZ,CAAC;gBACF,MAAM,UAAU,GAAG,IAAI,CAAC,WAAW,CAAC,MAAM,GAAG,KAAK,GAAG,CAAC,CAAC;gBAEvD,MAAM,OAAO,GAAG,UAAU,CAAC;oBACzB,QAAQ,EAAE,IAAI;oBACd,CAAC,QAAQ,CAAC,EAAE,IAAI;oBAChB,QAAQ,EAAE,UAAU,CAAC,IAAI;oBACzB,OAAO,EAAE,UAAU,CAAC,OAAO;iBAC5B,CAAC,CAAC;gBAEH,OAAO,IAAI,CAAA,eAAe,OAAO;kBAC7B,QAAQ,KAAK,SAAS;oBACtB,CAAC,CAAC,IAAI,CAAA;;+BAEO,IAAI,CAAC,oBAAoB;0CACd,UAAU;;wBAE5B,UAAU,CAAC,MAAM,CAAC,MAAM;wBACxB,UAAU,CAAC,MAAM,CAAC,MAAM,KAAK,CAAC;wBAC9B,CAAC,CAAC,IAAI,CAAA,OAAO;wBACb,CAAC,CAAC,IAAI,CAAA,QAAQ;2BACX;oBACT,CAAC,CAAC,IAAI;kBACN,QAAQ,KAAK,SAAS;oBACtB,CAAC,CAAC,IAAI,CAAA;;iCAES,IAAI,CAAC,oBAAoB;4CACd,UAAU;;;;;qBAKjC;oBACH,CAAC,CAAC,IAAI;kBACN,UAAU,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,KAAmB,EAAE,EAAE;oBAC9C,IACE,KAAK,CAAC,IAAI,KAAK,MAAM,CAAC,eAAe;wBACpC,KAAqB,CAAC,IAAI,EAC3B;wBACA,MAAM,SAAS,GAAG,EAAE,GAAG,KAAK,EAAE,CAAC;wBAC/B,SAAS,CAAC,IAAI,GAAG,MAAM,CAAC,iBAAiB,CAAC;wBAE1C,OAAO,IAAI,CAAA,GAAG,IAAI,CAAC,oBAAoB,CACrC,SAAS,CACV,GAAG,IAAI,CAAC,oBAAoB,CAAC,KAAK,CAAC,EAAE,CAAC;qBACxC;yBAAM;wBACL,OAAO,IAAI,CAAC,oBAAoB,CAAC,KAAK,CAAC,CAAC;qBACzC;gBACH,CAAC,CAAC;qBACG,CAAC;YACV,CAAC,CAAC;YACJ,CAAC,CAAC,IAAI;;;;;mBAKG,GAAG,EAAE;YACZ,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,CAAC;QAC5B,CAAC;gCACqB,UAAU,CAAC;YAC/B,QAAQ,EAAE,IAAI,CAAC,gBAAgB;SAChC,CAAC;;;;;KAKP,CAAC;IACJ,CAAC;CACF;AAtyBC;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;4CACd;AAGb;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;6CACb;AAGd;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC;mDACK;AAG/B;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;kDACT;AAGnB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;gDACX;AAGjB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;gDACX;AAGjB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;gDACV;AAGjB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;6CACd;AAGd;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;wDACH;AAGzB;IADC,QAAQ,CAAC,EAAE,SAAS,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;uDACf;AAG9B;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;8CACL;AAGtB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;+CACJ;AAGvB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC;+CACD;AAGzB;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;qDACE","sourcesContent":["/* eslint-disable @typescript-eslint/camelcase */\nimport { css, property } from 'lit-element';\nimport { html, TemplateResult } from 'lit-html';\nimport { CustomEventType, Ticket } from '../interfaces';\nimport { RapidElement } from '../RapidElement';\nimport { Asset, getAssets, getClasses, postJSON, throttle } from '../utils';\nimport ResizeObserver from 'resize-observer-polyfill';\nimport {\n AirtimeTransferredEvent,\n CampaignFiredEvent,\n ChannelEvent,\n ContactEvent,\n ContactGroupsEvent,\n ContactHistoryPage,\n ContactLanguageChangedEvent,\n EmailSentEvent,\n ErrorMessageEvent,\n EventGroup,\n Events,\n FlowEvent,\n getEventGroupType,\n getEventStyles,\n LabelsAddedEvent,\n MsgEvent,\n NameChangedEvent,\n renderAirtimeTransferredEvent,\n renderCallStartedEvent,\n renderCampaignFiredEvent,\n renderChannelEvent,\n renderContactGroupsEvent,\n renderContactLanguageChangedEvent,\n renderContactURNsChanged,\n renderEmailSent,\n renderErrorMessage,\n renderFlowEvent,\n renderLabelsAdded,\n renderMsgEvent,\n renderNameChanged,\n renderNoteCreated,\n renderResultEvent,\n renderTicketAction,\n renderTicketAssigned,\n renderTicketOpened,\n renderUpdateEvent,\n renderWebhookEvent,\n TicketEvent,\n UpdateFieldEvent,\n UpdateResultEvent,\n URNsChangedEvent,\n WebhookEvent,\n} from './events';\nimport {\n fetchContactHistory,\n MAX_CHAT_REFRESH,\n MIN_CHAT_REFRESH,\n SCROLL_THRESHOLD,\n} from './helpers';\n\nexport class ContactHistory extends RapidElement {\n public httpComplete: Promise<void | ContactHistoryPage>;\n\n private getStickyId = (event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticket = this.getTicketForEvent(event as TicketEvent);\n if (ticket && ticket.status === 'open') {\n return ticket.uuid;\n }\n }\n };\n\n private getTicketForEvent(event: TicketEvent) {\n return this.getTicket((event as TicketEvent).ticket.uuid);\n }\n\n private getTicket(uuid: string) {\n return (this.tickets || []).find(ticket => ticket.uuid === uuid);\n }\n\n static get styles() {\n return css`\n ${getEventStyles()}\n\n :host {\n flex-grow: 1;\n flex-direction: column;\n display: flex;\n flex-direction: column;\n align-items: items-stretch;\n }\n\n .events {\n height: 200px;\n overflow-y: scroll;\n overflow-x: hidden;\n flex-grow: 1;\n border-top-left-radius: var(--curvature);\n padding-top: 1em;\n }\n\n temba-loading {\n align-self: center;\n margin-top: 0.025em;\n position: absolute;\n z-index: 250;\n padding-top: 1em;\n }\n\n .new-messages-container {\n display: flex;\n z-index: 1;\n background: pink;\n margin-bottom: 0px;\n }\n\n .new-messages {\n pointer-events: none;\n margin: 0 auto;\n margin-top: 0em;\n margin-bottom: -2.5em;\n padding: 0.25em 1em;\n border-radius: var(--curvature);\n background: var(--color-primary-dark);\n color: var(--color-text-light);\n opacity: 0;\n cursor: pointer;\n transition: all var(--transition-speed) ease-in-out;\n box-shadow: rgb(0 0 0 / 15%) 0px 3px 3px 0px;\n }\n\n .new-messages.expanded {\n margin-top: -2.5em;\n margin-bottom: 0.5em;\n pointer-events: auto;\n opacity: 1;\n pointer: cursor;\n }\n\n .sticky-bin {\n display: flex;\n flex-direction: column;\n position: fixed;\n z-index: 2;\n border-top-left-radius: var(--curvature);\n overflow: hidden;\n background: rgba(240, 240, 240, 0.95);\n box-shadow: 0px 3px 3px 0px rgba(0, 0, 0, 0.15);\n }\n\n .sticky-bin temba-icon {\n margin-right: 0.75em;\n }\n\n .sticky-bin temba-icon[name='check'] {\n margin-right: 0;\n }\n\n .sticky {\n display: flex;\n margin: 1em -2em;\n padding: 1em 2em;\n background: rgba(240, 240, 240, 0.95);\n border-bottom: 1px solid rgba(220, 220, 220, 1);\n }\n\n .sticky.pinned {\n visibility: hidden;\n }\n\n .sticky-bin .event {\n margin: 0;\n padding: 1em 2em;\n border-radius: 0px;\n }\n\n .sticky .event {\n margin-bottom: 0;\n }\n\n .sticky .attn,\n .sticky-bin .attn {\n color: var(--color-text);\n }\n `;\n }\n\n @property({ type: String })\n uuid: string;\n\n @property({ type: Number })\n agent: number;\n\n @property({ type: Array })\n eventGroups: EventGroup[] = [];\n\n @property({ type: Boolean })\n refreshing = false;\n\n @property({ type: Boolean })\n fetching = false;\n\n @property({ type: Boolean })\n complete = false;\n\n @property({ type: String })\n endpoint: string;\n\n @property({ type: Boolean })\n debug = false;\n\n @property({ type: Boolean })\n showMessageAlert = false;\n\n @property({ attribute: false, type: Object })\n mostRecentEvent: ContactEvent;\n\n @property({ type: String })\n ticket: string = null;\n\n @property({ type: String })\n endDate: string = null;\n\n @property({ type: Array })\n tickets: Ticket[] = null;\n\n @property({ type: Object })\n currentTicket: Ticket = null;\n\n ticketEvents: { [uuid: string]: TicketEvent } = {};\n\n nextBefore: number;\n nextAfter: number;\n lastHeight = 0;\n lastRefreshAdded: number;\n refreshTimeout: any = null;\n empty = false;\n\n public firstUpdated(changedProperties: Map<string, any>) {\n super.firstUpdated(changedProperties);\n\n this.handleClose = this.handleClose.bind(this);\n\n const stickyBin = this.getDiv('.sticky-bin');\n const resizer = new ResizeObserver(entries => {\n for (const entry of entries) {\n const eventContainer = entry.contentRect;\n stickyBin.style.width =\n eventContainer.width + eventContainer.left - 16 + 'px';\n }\n });\n resizer.observe(this);\n }\n\n public updated(changedProperties: Map<string, any>) {\n super.updated(changedProperties);\n\n // fire an event when our current ticket changes\n if (changedProperties.has('currentTicket')) {\n this.fireCustomEvent(CustomEventType.ContextChanged, {\n context: this.currentTicket,\n });\n }\n\n // fire an event if we get a new event\n if (changedProperties.has('mostRecentEvent')) {\n this.fireCustomEvent(CustomEventType.Refreshed);\n }\n\n // if we don't have an endpoint infer one\n if (changedProperties.has('uuid')) {\n if (this.uuid == null) {\n this.reset();\n } else {\n const endpoint = `/contact/history/${this.uuid}/?_format=json`;\n\n if (this.endpoint !== endpoint) {\n this.reset();\n\n if (this.endDate) {\n const before = new Date(this.endDate);\n this.nextBefore = before.getTime() * 1000 + 1000;\n }\n\n this.endpoint = endpoint;\n this.refreshTickets();\n }\n }\n }\n\n if (changedProperties.has('ticket')) {\n this.endpoint = null;\n this.requestUpdate('uuid');\n }\n\n if (\n changedProperties.has('refreshing') &&\n this.refreshing &&\n this.endpoint\n ) {\n const after = (this.getLastEventTime() - 1) * 1000;\n let forceOpen = false;\n\n fetchContactHistory(false, this.endpoint, this.ticket, null, after)\n .then((results: ContactHistoryPage) => {\n if (results.events && results.events.length > 0) {\n this.updateMostRecent(results.events[0]);\n }\n\n // keep track of any ticket events\n results.events.forEach((event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticketEvent = event as TicketEvent;\n this.ticketEvents[ticketEvent.ticket.uuid] = ticketEvent;\n }\n });\n\n let fetchedEvents = results.events.reverse();\n\n // dedupe any events we get from the server\n // TODO: perhaps make this a little less crazy\n fetchedEvents = fetchedEvents.filter(item => {\n const found = !!this.eventGroups.find(\n g =>\n !!g.events.find(\n exists =>\n exists.created_on === item.created_on &&\n exists.type === item.type\n )\n );\n\n return !found;\n });\n\n this.lastRefreshAdded = fetchedEvents.length;\n\n // reflow our most recent event group in case it merges with our new groups\n const previousGroups = [...this.eventGroups];\n\n if (this.eventGroups.length > 0) {\n const sliced = previousGroups.splice(\n previousGroups.length - 1,\n 1\n )[0];\n\n forceOpen = sliced.open;\n fetchedEvents.splice(0, 0, ...sliced.events);\n }\n\n const grouped = this.getEventGroups(fetchedEvents);\n if (grouped.length) {\n if (forceOpen) {\n grouped[grouped.length - 1].open = forceOpen;\n }\n\n this.eventGroups = [...previousGroups, ...grouped];\n }\n this.refreshing = false;\n this.scheduleRefresh();\n })\n .catch(() => {\n this.refreshing = false;\n this.scheduleRefresh();\n });\n }\n\n if (changedProperties.has('fetching') && this.fetching) {\n if (!this.nextBefore) {\n this.nextBefore = new Date().getTime() * 1000 - 1000;\n }\n\n this.httpComplete = fetchContactHistory(\n this.empty,\n this.endpoint,\n this.ticket,\n this.nextBefore,\n this.nextAfter\n ).then((results: ContactHistoryPage) => {\n // see if we have a new event\n if (results.events && results.events.length > 0) {\n this.updateMostRecent(results.events[0]);\n\n // keep track of any ticket events\n results.events.forEach((event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticketEvent = event as TicketEvent;\n this.ticketEvents[ticketEvent.ticket.uuid] = ticketEvent;\n }\n });\n }\n\n let forceOpen = false;\n const fetchedEvents = results.events.reverse();\n\n // reflow our last event group in case it merges with our new groups\n if (this.eventGroups.length > 0) {\n const sliced = this.eventGroups.splice(0, 1)[0];\n forceOpen = sliced.open;\n fetchedEvents.push(...sliced.events);\n }\n\n const grouped = this.getEventGroups(fetchedEvents);\n if (grouped.length) {\n if (forceOpen) {\n grouped[grouped.length - 1].open = forceOpen;\n }\n\n this.eventGroups = [...grouped, ...this.eventGroups];\n }\n\n if (results.next_before === this.nextBefore) {\n this.complete = true;\n }\n\n this.nextBefore = results.next_before;\n this.nextAfter = results.next_after;\n this.fetching = false;\n this.empty = false;\n });\n }\n\n if (changedProperties.has('refreshing') && !this.refreshing) {\n if (this.lastRefreshAdded > 0) {\n const events = this.getEventsPane();\n // if we are near the bottom, push us to the bottom to show new stuff\n if (this.lastHeight > 0) {\n const addedHeight = events.scrollHeight - this.lastHeight;\n\n const distanceFromBottom =\n events.scrollHeight -\n events.scrollTop -\n addedHeight -\n events.clientHeight;\n\n if (distanceFromBottom < 500) {\n this.scrollToBottom();\n } else {\n this.showMessageAlert = true;\n }\n }\n\n if (this.eventGroups.length > 0) {\n this.lastHeight = events.scrollHeight;\n }\n }\n }\n\n if (\n changedProperties.has('fetching') &&\n !this.fetching &&\n changedProperties.get('fetching') !== undefined\n ) {\n const events = this.getEventsPane();\n\n if (this.lastHeight && events.scrollHeight > this.lastHeight) {\n const scrollTop =\n events.scrollTop + events.scrollHeight - this.lastHeight;\n events.scrollTop = scrollTop;\n }\n\n // scroll to the bottom if it's our first fetch\n if (!this.lastHeight) {\n this.scrollToBottom();\n }\n\n // don't record our scroll height until we have history\n if (this.eventGroups.length > 0) {\n this.lastHeight = events.scrollHeight;\n }\n }\n\n if (changedProperties.has('endpoint') && this.endpoint) {\n this.fetching = true;\n this.empty = true;\n }\n\n // when our tickets change, make sure we don't have any manual pins\n if (changedProperties.has('tickets')) {\n const stickyBin = this.getDiv('.sticky-bin');\n\n const closedTickets = (this.tickets || []).filter(\n ticket => ticket && ticket.status === 'closed'\n );\n\n for (const closed of closedTickets) {\n const child = stickyBin.querySelector(\n `[data-sticky-id=\"${closed.uuid}\"]`\n );\n if (child) {\n stickyBin.removeChild(child);\n }\n }\n if (!this.currentTicket) {\n this.updateCurrentTicket();\n }\n }\n }\n\n private updateCurrentTicket() {\n const openTickets = (this.tickets || []).filter(\n ticket => ticket && ticket.status === 'open'\n );\n if (openTickets.length > 0) {\n this.currentTicket = openTickets[openTickets.length - 1];\n }\n }\n\n private refreshTickets() {\n let url = `/api/v2/tickets.json?contact=${this.uuid}`;\n if (this.ticket) {\n url = `${url}&ticket=${this.ticket}`;\n }\n\n getAssets(url).then((tickets: Ticket[]) => {\n this.tickets = tickets.reverse();\n });\n }\n\n public getEventsPane() {\n return this.getDiv('.events');\n }\n\n public scrollToBottom(smooth = false) {\n const events = this.getEventsPane();\n events.scrollTo({\n top: events.scrollHeight,\n behavior: smooth ? 'smooth' : 'auto',\n });\n this.showMessageAlert = false;\n\n window.setTimeout(() => {\n events.scrollTo({\n top: events.scrollHeight,\n behavior: smooth ? 'smooth' : 'auto',\n });\n }, 0);\n }\n\n public refresh(): void {\n this.scheduleRefresh(500);\n }\n\n private getEventGroups(events: ContactEvent[]): EventGroup[] {\n const grouped: EventGroup[] = [];\n let eventGroup: EventGroup = undefined;\n for (const event of events) {\n const currentEventGroupType = getEventGroupType(event, this.ticket);\n // see if we need a new event group\n if (!eventGroup || eventGroup.type !== currentEventGroupType) {\n // we have a new type, save our last group\n if (eventGroup) {\n grouped.push(eventGroup);\n }\n eventGroup = {\n open: false,\n closing: false,\n events: [event],\n type: currentEventGroupType,\n };\n } else {\n // our event matches the current group, stuff it in there\n eventGroup.events.push(event);\n }\n }\n\n if (eventGroup && eventGroup.events.length > 0) {\n grouped.push(eventGroup);\n }\n return grouped;\n }\n\n private scheduleRefresh(wait = -1) {\n let refreshWait = wait;\n\n if (wait === -1) {\n const lastEventTime = this.getLastEventTime();\n refreshWait = Math.max(\n Math.min((new Date().getTime() - lastEventTime) / 2, MAX_CHAT_REFRESH),\n MIN_CHAT_REFRESH\n );\n }\n\n // cancel any outstanding timeout\n if (wait > -1 && this.refreshTimeout) {\n window.clearTimeout(this.refreshTimeout);\n }\n\n this.refreshTimeout = window.setTimeout(() => {\n if (this.refreshing) {\n this.scheduleRefresh();\n this.refreshing = false;\n } else {\n this.refreshing = true;\n }\n }, refreshWait);\n }\n\n private reset() {\n // clear out our sticky bin which we manipulated manually\n const stickyBin = this.getDiv('.sticky-bin');\n while (stickyBin.childElementCount > 0) {\n stickyBin.removeChild(stickyBin.firstElementChild);\n }\n\n this.currentTicket = null;\n this.endpoint = null;\n this.tickets = null;\n this.ticketEvents = {};\n this.eventGroups = [];\n this.fetching = false;\n this.complete = false;\n this.nextBefore = null;\n this.nextAfter = null;\n this.lastHeight = 0;\n }\n\n private handleEventGroupShow(event: MouseEvent) {\n const grouping = event.currentTarget as HTMLDivElement;\n const groupIndex = parseInt(grouping.getAttribute('data-group-index'));\n const eventGroup = this.eventGroups[\n this.eventGroups.length - groupIndex - 1\n ];\n eventGroup.open = true;\n this.requestUpdate('eventGroups');\n }\n\n private handleEventGroupHide(event: MouseEvent) {\n const grouping = event.currentTarget as HTMLDivElement;\n const groupIndex = parseInt(grouping.getAttribute('data-group-index'));\n const eventGroup = this.eventGroups[\n this.eventGroups.length - groupIndex - 1\n ];\n\n // mark us as closing\n eventGroup.closing = true;\n this.requestUpdate('eventGroups');\n\n // after our animation, close it up for real\n setTimeout(() => {\n eventGroup.closing = false;\n eventGroup.open = false;\n this.requestUpdate('eventGroups');\n }, 300);\n }\n\n private handleScroll() {\n const events = this.getEventsPane();\n\n // check if any of our sticky elements are off the screen\n const stickies = this.getEventsPane().querySelectorAll('.sticky');\n const stickyBin = this.getDiv('.sticky-bin');\n\n stickies.forEach((sticky: HTMLDivElement) => {\n const scrollBoundary = events.scrollTop + stickyBin.clientHeight + 136;\n if (!sticky.classList.contains('pinned')) {\n const eventElement = sticky.firstElementChild as HTMLDivElement;\n if (scrollBoundary > sticky.offsetTop) {\n sticky.style.height = eventElement.clientHeight + 'px';\n sticky.classList.add('pinned');\n (sticky as any).eventElement = eventElement;\n stickyBin.appendChild(eventElement);\n const uuid = eventElement.getAttribute('data-sticky-id');\n const ticket = this.getTicket(uuid);\n if (ticket) {\n if (\n !this.currentTicket ||\n this.currentTicket.uuid !== ticket.uuid\n ) {\n this.currentTicket = ticket;\n }\n }\n }\n } else {\n const eventElement = (sticky as any).eventElement;\n if (scrollBoundary < sticky.offsetTop + sticky.offsetHeight) {\n sticky.appendChild(eventElement);\n sticky.classList.remove('pinned');\n\n const uuid = eventElement.getAttribute('data-sticky-id');\n let previousTicket: Ticket = null;\n for (const ticket of this.tickets) {\n if (ticket.uuid === uuid) {\n break;\n }\n previousTicket = ticket;\n }\n\n if (\n previousTicket &&\n (!this.currentTicket ||\n this.currentTicket.uuid !== previousTicket.uuid)\n ) {\n if (previousTicket.status === 'open') {\n this.currentTicket = previousTicket;\n } else {\n this.currentTicket = null;\n }\n }\n }\n }\n });\n\n if (events.scrollTop <= SCROLL_THRESHOLD) {\n if (this.eventGroups.length > 0 && !this.fetching && !this.complete) {\n this.fetching = true;\n }\n }\n }\n\n private updateMostRecent(newEvent: ContactEvent) {\n if (\n !this.mostRecentEvent ||\n this.mostRecentEvent.type !== newEvent.type ||\n this.mostRecentEvent.created_on !== newEvent.created_on\n ) {\n this.mostRecentEvent = newEvent;\n }\n }\n\n private getLastEventTime(): number {\n const mostRecentGroup = this.eventGroups[this.eventGroups.length - 1];\n if (mostRecentGroup) {\n const mostRecentEvent =\n mostRecentGroup.events[mostRecentGroup.events.length - 1];\n return new Date(mostRecentEvent.created_on).getTime();\n }\n return 0;\n }\n\n public renderEvent(event: ContactEvent): TemplateResult {\n switch (event.type) {\n case Events.IVR_CREATED:\n case Events.MESSAGE_CREATED:\n case Events.MESSAGE_RECEIVED:\n case Events.BROADCAST_CREATED:\n return renderMsgEvent(event as MsgEvent, this.agent);\n\n case Events.FLOW_ENTERED:\n case Events.FLOW_EXITED:\n return renderFlowEvent(event as FlowEvent);\n\n case Events.RUN_RESULT_CHANGED:\n return renderResultEvent(event as UpdateResultEvent);\n\n case Events.CONTACT_FIELD_CHANGED:\n return renderUpdateEvent(event as UpdateFieldEvent);\n\n case Events.CONTACT_NAME_CHANGED:\n return renderNameChanged(event as NameChangedEvent);\n\n case Events.CONTACT_URNS_CHANGED:\n return renderContactURNsChanged(event as URNsChangedEvent);\n\n case Events.EMAIL_SENT:\n return renderEmailSent(event as EmailSentEvent);\n\n case Events.INPUT_LABELS_ADDED:\n return renderLabelsAdded(event as LabelsAddedEvent);\n\n case Events.TICKET_OPENED: {\n const ticketEvent = event as TicketEvent;\n const activeTicket =\n !this.ticket || ticketEvent.ticket.uuid === this.ticket;\n\n let closeHandler = null;\n const ticket = this.getTicketForEvent(ticketEvent);\n if (activeTicket && ticket && ticket.status === 'open') {\n closeHandler = this.handleClose;\n }\n return renderTicketOpened(ticketEvent, closeHandler);\n }\n case Events.TICKET_NOTE_ADDED:\n return renderNoteCreated(event as TicketEvent, this.agent);\n\n case Events.TICKET_ASSIGNED:\n return renderTicketAssigned(event as TicketEvent);\n case Events.TICKET_REOPENED: {\n return renderTicketAction(event as TicketEvent, 'reopened');\n }\n case Events.TICKET_CLOSED:\n return renderTicketAction(event as TicketEvent, 'closed');\n\n case Events.ERROR:\n case Events.FAILURE:\n return renderErrorMessage(event as ErrorMessageEvent);\n case Events.CONTACT_GROUPS_CHANGED:\n return renderContactGroupsEvent(event as ContactGroupsEvent);\n case Events.WEBHOOK_CALLED:\n return renderWebhookEvent(event as WebhookEvent);\n case Events.AIRTIME_TRANSFERRED:\n return renderAirtimeTransferredEvent(event as AirtimeTransferredEvent);\n case Events.CALL_STARTED:\n return renderCallStartedEvent();\n case Events.CAMPAIGN_FIRED:\n return renderCampaignFiredEvent(event as CampaignFiredEvent);\n case Events.CHANNEL_EVENT:\n return renderChannelEvent(event as ChannelEvent);\n case Events.CONTACT_LANGUAGE_CHANGED:\n return renderContactLanguageChangedEvent(\n event as ContactLanguageChangedEvent\n );\n }\n\n return html`<temba-icon\n name=\"alert-triangle\"\n style=\"fill:var(--color-error)\"\n ></temba-icon>\n <div class=\"description\">${event.type}</div>`;\n }\n\n private handleClose(uuid: string) {\n this.httpComplete = postJSON(`/api/v2/tickets.json?uuid=${uuid}`, {\n status: 'closed',\n })\n .then(() => {\n this.refreshTickets();\n this.refresh();\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid, status: 'closed' },\n });\n this.updateCurrentTicket();\n })\n .catch((response: any) => {\n console.error(response);\n });\n }\n\n public checkForAgentAssignmentEvent(agent: number) {\n if (this.currentTicket) {\n this.httpComplete = getAssets(\n `/api/v2/tickets.json?ticket=${this.currentTicket.uuid}`\n ).then((assets: Asset[]) => {\n if (assets.length === 1) {\n const ticket = assets[0] as Ticket;\n if (ticket.assignee && ticket.assignee.id === agent) {\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid: this.currentTicket.uuid, assigned: 'self' },\n });\n } else {\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid: this.currentTicket.uuid, assigned: 'other' },\n });\n }\n }\n });\n }\n }\n\n public getEventHandlers() {\n return [\n {\n event: 'scroll',\n method: throttle(this.handleScroll, 50),\n },\n ];\n }\n\n /** Check if a ticket event is no longer represented in a session */\n private isPurged(ticket: Ticket): boolean {\n return !this.ticketEvents[ticket.uuid];\n }\n\n private renderEventContainer(event: ContactEvent) {\n const stickyId = this.getStickyId(event);\n const isSticky = !!stickyId;\n\n const renderedEvent = html`\n <div\n class=\"event ${event.type} ${isSticky ? 'has-sticky' : ''}\"\n data-sticky-id=\"${stickyId}\"\n >\n ${this.renderEvent(event)}\n </div>\n ${this.debug ? html`<pre>${JSON.stringify(event, null, 2)}</pre>` : null}\n `;\n\n if (stickyId) {\n return html`<div class=\"sticky\">${renderedEvent}</div>`;\n }\n\n return renderedEvent;\n }\n\n public render(): TemplateResult {\n // render our older tickets as faux-events\n const unfetchedTickets =\n this.eventGroups.length > 0 && this.tickets\n ? this.tickets.map((ticket: Ticket) => {\n if (ticket && ticket.status === 'open') {\n const opened = new Date(ticket.opened_on).getTime() * 1000;\n if (opened < this.nextBefore || this.isPurged(ticket)) {\n const ticketOpenedEvent = {\n type: Events.TICKET_OPENED,\n ticket: {\n uuid: ticket.uuid,\n subject: ticket.subject,\n body: ticket.body,\n ticketer: ticket.ticketer,\n },\n // eslint-disable-next-line @typescript-eslint/camelcase\n created_on: ticket.opened_on,\n };\n\n const renderedEvent = renderTicketOpened(\n ticketOpenedEvent,\n this.handleClose\n );\n return html`<div class=\"event ticket_opened\">\n ${renderedEvent}\n </div>`;\n }\n }\n })\n : null;\n\n return html`\n <div class=\"sticky-bin\">${unfetchedTickets}</div>\n ${this.fetching\n ? html`<temba-loading units=\"5\" size=\"10\"></temba-loading>`\n : html`<div style=\"height:0em\"></div>`}\n <div class=\"events\" @scroll=${this.handleScroll}>\n ${this.tickets\n ? this.eventGroups.map((eventGroup: EventGroup, index: number) => {\n const grouping = getEventGroupType(\n eventGroup.events[0],\n this.ticket\n );\n const groupIndex = this.eventGroups.length - index - 1;\n\n const classes = getClasses({\n grouping: true,\n [grouping]: true,\n expanded: eventGroup.open,\n closing: eventGroup.closing,\n });\n\n return html`<div class=\"${classes}\">\n ${grouping === 'verbose'\n ? html`<div\n class=\"event-count\"\n @click=${this.handleEventGroupShow}\n data-group-index=\"${groupIndex}\"\n >\n ${eventGroup.events.length}\n ${eventGroup.events.length === 1\n ? html`event`\n : html`events`}\n </div>`\n : null}\n ${grouping === 'verbose'\n ? html`\n <temba-icon\n @click=${this.handleEventGroupHide}\n data-group-index=\"${groupIndex}\"\n class=\"grouping-close-button\"\n name=\"x\"\n clickable\n ></temba-icon>\n `\n : null}\n ${eventGroup.events.map((event: ContactEvent) => {\n if (\n event.type === Events.TICKET_ASSIGNED &&\n (event as TicketEvent).note\n ) {\n const noteEvent = { ...event };\n noteEvent.type = Events.TICKET_NOTE_ADDED;\n\n return html`${this.renderEventContainer(\n noteEvent\n )}${this.renderEventContainer(event)}`;\n } else {\n return this.renderEventContainer(event);\n }\n })}\n </div>`;\n })\n : null}\n </div>\n\n <div class=\"new-messages-container\">\n <div\n @click=${() => {\n this.scrollToBottom(true);\n }}\n class=\"new-messages ${getClasses({\n expanded: this.showMessageAlert,\n })}\"\n >\n New Messages\n </div>\n </div>\n `;\n }\n}\n"]}
1
+ {"version":3,"file":"ContactHistory.js","sourceRoot":"","sources":["../../../src/contacts/ContactHistory.ts"],"names":[],"mappings":"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","sourcesContent":["/* eslint-disable @typescript-eslint/camelcase */\nimport { css, property } from 'lit-element';\nimport { html, TemplateResult } from 'lit-html';\nimport { Contact, CustomEventType, Ticket } from '../interfaces';\nimport { RapidElement } from '../RapidElement';\nimport { Asset, getAssets, getClasses, postJSON, throttle } from '../utils';\n\nimport {\n AirtimeTransferredEvent,\n CampaignFiredEvent,\n ChannelEvent,\n ContactEvent,\n ContactGroupsEvent,\n ContactHistoryPage,\n ContactLanguageChangedEvent,\n EmailSentEvent,\n ErrorMessageEvent,\n EventGroup,\n Events,\n FlowEvent,\n getEventGroupType,\n getEventStyles,\n LabelsAddedEvent,\n MsgEvent,\n NameChangedEvent,\n renderAirtimeTransferredEvent,\n renderCallStartedEvent,\n renderCampaignFiredEvent,\n renderChannelEvent,\n renderContactGroupsEvent,\n renderContactLanguageChangedEvent,\n renderContactURNsChanged,\n renderEmailSent,\n renderErrorMessage,\n renderFlowEvent,\n renderLabelsAdded,\n renderMsgEvent,\n renderNameChanged,\n renderNoteCreated,\n renderResultEvent,\n renderTicketAction,\n renderTicketAssigned,\n renderTicketOpened,\n renderUpdateEvent,\n renderWebhookEvent,\n TicketEvent,\n UpdateFieldEvent,\n UpdateResultEvent,\n URNsChangedEvent,\n WebhookEvent,\n} from './events';\nimport {\n fetchContactHistory,\n MAX_CHAT_REFRESH,\n MIN_CHAT_REFRESH,\n SCROLL_THRESHOLD,\n} from './helpers';\n\n// when images load, make sure we are on the bottom of the scroll window if necessary\nexport const loadHandler = function (event) {\n const target = event.target as HTMLElement;\n const events = this.host.getEventsPane();\n if (target.tagName == 'IMG') {\n if (!this.host.showMessageAlert) {\n if (\n events.scrollTop > target.offsetTop - 1000 &&\n target.offsetTop > events.scrollHeight - 500\n ) {\n this.host.scrollToBottom();\n }\n }\n }\n};\n\nexport class ContactHistory extends RapidElement {\n public httpComplete: Promise<void | ContactHistoryPage>;\n\n public constructor() {\n super();\n }\n\n connectedCallback() {\n super.connectedCallback();\n this.shadowRoot.addEventListener('load', loadHandler, true);\n }\n\n disconnectedCallback() {\n super.disconnectedCallback();\n this.shadowRoot.removeEventListener('load', loadHandler, true);\n }\n\n private getStickyId = (event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticket = this.getTicketForEvent(event as TicketEvent);\n if (ticket && ticket.status === 'open') {\n return ticket.uuid;\n }\n }\n };\n\n private getTicketForEvent(event: TicketEvent) {\n return this.getTicket((event as TicketEvent).ticket.uuid);\n }\n\n private getTicket(uuid: string) {\n return (this.tickets || []).find(ticket => ticket.uuid === uuid);\n }\n\n static get styles() {\n return css`\n ${getEventStyles()}\n\n :host {\n flex-grow: 1;\n flex-direction: column;\n display: flex;\n flex-direction: column;\n align-items: items-stretch;\n }\n\n .events {\n height: 200px;\n overflow-y: scroll;\n overflow-x: hidden;\n flex-grow: 1;\n border-top-left-radius: var(--curvature);\n padding-top: 1em;\n background: #fff;\n }\n\n temba-loading {\n align-self: center;\n margin-top: 0.025em;\n position: absolute;\n z-index: 250;\n padding-top: 1em;\n }\n\n .new-messages-container {\n display: flex;\n z-index: 1;\n background: pink;\n margin-bottom: 0px;\n }\n\n .new-messages {\n pointer-events: none;\n margin: 0 auto;\n margin-top: 0em;\n margin-bottom: -2.5em;\n padding: 0.25em 1em;\n border-radius: var(--curvature);\n background: var(--color-primary-dark);\n color: var(--color-text-light);\n opacity: 0;\n cursor: pointer;\n transition: all var(--transition-speed) ease-in-out;\n box-shadow: rgb(0 0 0 / 15%) 0px 3px 3px 0px;\n }\n\n .new-messages.expanded {\n margin-top: -2.5em;\n margin-bottom: 0.5em;\n pointer-events: auto;\n opacity: 1;\n pointer: cursor;\n }\n\n .scroll-title {\n display: flex;\n flex-direction: column;\n z-index: 2;\n border-top-left-radius: var(--curvature);\n overflow: hidden;\n box-shadow: 0px 3px 3px 0px rgba(0, 0, 0, 0.15);\n background: rgb(240, 240, 240);\n padding: 1em 1.2em;\n font-size: 1.2em;\n font-weight: 400;\n }\n\n .sticky-bin {\n display: flex;\n flex-direction: column;\n z-index: 2;\n border-top-left-radius: var(--curvature);\n overflow: hidden;\n box-shadow: 0px 3px 3px 0px rgba(0, 0, 0, 0.15);\n background: rgb(240, 240, 240);\n }\n\n .sticky-bin temba-icon {\n margin-right: 0.75em;\n }\n\n .sticky-bin temba-icon[name='check'] {\n margin-right: 0;\n }\n\n .sticky {\n display: flex;\n margin: 1em -2em;\n padding: 1em 2em;\n background: rgba(240, 240, 240, 0.95);\n border-bottom: 1px solid rgba(220, 220, 220, 1);\n }\n\n .sticky.pinned {\n visibility: hidden;\n }\n\n .sticky-bin .event {\n margin: 0;\n padding: 1em 2em;\n border-radius: 0px;\n }\n\n .sticky .event {\n margin-bottom: 0;\n }\n\n .sticky .attn,\n .sticky-bin .attn {\n color: var(--color-text);\n }\n `;\n }\n\n @property({ type: Object })\n contact: Contact;\n\n @property({ type: String })\n uuid: string;\n\n @property({ type: Number })\n agent: number;\n\n @property({ type: Array })\n eventGroups: EventGroup[] = [];\n\n @property({ type: Boolean })\n refreshing = false;\n\n @property({ type: Boolean })\n fetching = false;\n\n @property({ type: Boolean })\n complete = false;\n\n @property({ type: String })\n endpoint: string;\n\n @property({ type: Boolean })\n debug = false;\n\n @property({ type: Boolean })\n showMessageAlert = false;\n\n @property({ attribute: false, type: Object })\n mostRecentEvent: ContactEvent;\n\n @property({ type: String })\n ticket: string = null;\n\n @property({ type: String })\n endDate: string = null;\n\n @property({ type: Array })\n tickets: Ticket[] = null;\n\n ticketEvents: { [uuid: string]: TicketEvent } = {};\n\n nextBefore: number;\n nextAfter: number;\n lastHeight = 0;\n lastRefreshAdded: number;\n refreshTimeout: any = null;\n empty = false;\n\n public firstUpdated(changedProperties: Map<string, any>) {\n super.firstUpdated(changedProperties);\n this.handleClose = this.handleClose.bind(this);\n }\n\n public updated(changedProperties: Map<string, any>) {\n super.updated(changedProperties);\n\n // fire an event if we get a new event\n if (changedProperties.has('mostRecentEvent')) {\n this.fireCustomEvent(CustomEventType.Refreshed);\n }\n\n if (changedProperties.has('endDate')) {\n if (this.refreshTimeout && this.endDate) {\n window.clearTimeout(this.refreshTimeout);\n }\n }\n\n // if we don't have an endpoint infer one\n if (changedProperties.has('uuid')) {\n if (this.uuid == null) {\n this.reset();\n } else {\n const endpoint = `/contact/history/${this.uuid}/?_format=json`;\n\n if (this.endpoint !== endpoint) {\n this.reset();\n\n if (this.endDate) {\n const before = new Date(this.endDate);\n this.nextBefore = before.getTime() * 1000 + 1000;\n }\n\n this.endpoint = endpoint;\n this.refreshTickets();\n }\n }\n }\n\n if (changedProperties.has('ticket')) {\n this.endpoint = null;\n this.requestUpdate('uuid');\n }\n\n if (\n changedProperties.has('refreshing') &&\n this.refreshing &&\n this.endpoint &&\n !this.endDate\n ) {\n const after = (this.getLastEventTime() - 1) * 1000;\n let forceOpen = false;\n\n fetchContactHistory(false, this.endpoint, this.ticket, null, after)\n .then((results: ContactHistoryPage) => {\n if (results.events && results.events.length > 0) {\n this.updateMostRecent(results.events[0]);\n }\n\n // keep track of any ticket events\n results.events.forEach((event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticketEvent = event as TicketEvent;\n this.ticketEvents[ticketEvent.ticket.uuid] = ticketEvent;\n }\n });\n\n let fetchedEvents = results.events.reverse();\n\n // dedupe any events we get from the server\n // TODO: perhaps make this a little less crazy\n fetchedEvents = fetchedEvents.filter(item => {\n const found = !!this.eventGroups.find(\n g =>\n !!g.events.find(\n exists =>\n exists.created_on === item.created_on &&\n exists.type === item.type\n )\n );\n\n return !found;\n });\n\n this.lastRefreshAdded = fetchedEvents.length;\n\n // reflow our most recent event group in case it merges with our new groups\n const previousGroups = [...this.eventGroups];\n\n if (this.eventGroups.length > 0) {\n const sliced = previousGroups.splice(\n previousGroups.length - 1,\n 1\n )[0];\n\n forceOpen = sliced.open;\n fetchedEvents.splice(0, 0, ...sliced.events);\n }\n\n const grouped = this.getEventGroups(fetchedEvents);\n if (grouped.length) {\n if (forceOpen) {\n grouped[grouped.length - 1].open = forceOpen;\n }\n\n this.eventGroups = [...previousGroups, ...grouped];\n }\n this.refreshing = false;\n this.scheduleRefresh();\n })\n .catch(() => {\n this.refreshing = false;\n this.scheduleRefresh();\n });\n }\n\n if (changedProperties.has('fetching') && this.fetching) {\n if (!this.nextBefore) {\n this.nextBefore = new Date().getTime() * 1000 - 1000;\n }\n\n this.httpComplete = fetchContactHistory(\n this.empty,\n this.endpoint,\n this.ticket,\n this.nextBefore,\n this.nextAfter\n ).then((results: ContactHistoryPage) => {\n // see if we have a new event\n if (results.events && results.events.length > 0) {\n this.updateMostRecent(results.events[0]);\n\n // keep track of any ticket events\n results.events.forEach((event: ContactEvent) => {\n if (event.type === Events.TICKET_OPENED) {\n const ticketEvent = event as TicketEvent;\n this.ticketEvents[ticketEvent.ticket.uuid] = ticketEvent;\n }\n });\n }\n\n let forceOpen = false;\n const fetchedEvents = results.events.reverse();\n\n // reflow our last event group in case it merges with our new groups\n if (this.eventGroups.length > 0) {\n const sliced = this.eventGroups.splice(0, 1)[0];\n forceOpen = sliced.open;\n fetchedEvents.push(...sliced.events);\n }\n\n const grouped = this.getEventGroups(fetchedEvents);\n if (grouped.length) {\n if (forceOpen) {\n grouped[grouped.length - 1].open = forceOpen;\n }\n\n this.eventGroups = [...grouped, ...this.eventGroups];\n }\n\n if (results.next_before === this.nextBefore) {\n this.complete = true;\n }\n\n this.nextBefore = results.next_before;\n this.nextAfter = results.next_after;\n this.fetching = false;\n this.empty = false;\n });\n }\n\n if (changedProperties.has('refreshing') && !this.refreshing) {\n if (this.lastRefreshAdded > 0) {\n const events = this.getEventsPane();\n // if we are near the bottom, push us to the bottom to show new stuff\n if (this.lastHeight > 0) {\n const addedHeight = events.scrollHeight - this.lastHeight;\n\n const distanceFromBottom =\n events.scrollHeight -\n events.scrollTop -\n addedHeight -\n events.clientHeight;\n\n if (distanceFromBottom < 500) {\n this.scrollToBottom();\n } else {\n this.showMessageAlert = true;\n }\n }\n\n if (this.eventGroups.length > 0) {\n this.lastHeight = events.scrollHeight;\n }\n }\n }\n\n if (\n changedProperties.has('fetching') &&\n !this.fetching &&\n changedProperties.get('fetching') !== undefined\n ) {\n const events = this.getEventsPane();\n\n if (this.lastHeight && events.scrollHeight > this.lastHeight) {\n const scrollTop =\n events.scrollTop + events.scrollHeight - this.lastHeight;\n events.scrollTop = scrollTop;\n }\n\n // scroll to the bottom if it's our first fetch\n if (!this.lastHeight) {\n this.scrollToBottom();\n }\n\n // don't record our scroll height until we have history\n if (this.eventGroups.length > 0) {\n this.lastHeight = events.scrollHeight;\n }\n }\n\n if (changedProperties.has('endpoint') && this.endpoint) {\n this.fetching = true;\n this.empty = true;\n }\n\n // when our tickets change, make sure we don't have any manual pins\n if (changedProperties.has('tickets')) {\n const stickyBin = this.getDiv('.sticky-bin');\n\n const closedTickets = (this.tickets || []).filter(\n ticket => ticket && ticket.status === 'closed'\n );\n\n for (const closed of closedTickets) {\n const child = stickyBin.querySelector(\n `[data-sticky-id=\"${closed.uuid}\"]`\n );\n if (child) {\n stickyBin.removeChild(child);\n }\n }\n }\n }\n\n private refreshTickets() {\n if (this.ticket) {\n let url = `/api/v2/tickets.json?contact=${this.uuid}`;\n if (this.ticket) {\n url = `${url}&ticket=${this.ticket}`;\n }\n\n getAssets(url).then((tickets: Ticket[]) => {\n this.tickets = tickets.reverse();\n });\n }\n }\n\n public getEventsPane() {\n return this.getDiv('.events');\n }\n\n public scrollToBottom(smooth = false) {\n const events = this.getEventsPane();\n events.scrollTo({\n top: events.scrollHeight,\n behavior: smooth ? 'smooth' : 'auto',\n });\n this.showMessageAlert = false;\n\n window.setTimeout(() => {\n events.scrollTo({\n top: events.scrollHeight,\n behavior: smooth ? 'smooth' : 'auto',\n });\n }, 0);\n }\n\n public refresh(): void {\n this.scheduleRefresh(500);\n }\n\n private getEventGroups(events: ContactEvent[]): EventGroup[] {\n const grouped: EventGroup[] = [];\n let eventGroup: EventGroup = undefined;\n for (const event of events) {\n const currentEventGroupType = getEventGroupType(event, this.ticket);\n // see if we need a new event group\n if (!eventGroup || eventGroup.type !== currentEventGroupType) {\n // we have a new type, save our last group\n if (eventGroup) {\n grouped.push(eventGroup);\n }\n eventGroup = {\n open: false,\n closing: false,\n events: [event],\n type: currentEventGroupType,\n };\n } else {\n // our event matches the current group, stuff it in there\n eventGroup.events.push(event);\n }\n }\n\n if (eventGroup && eventGroup.events.length > 0) {\n grouped.push(eventGroup);\n }\n return grouped;\n }\n\n private scheduleRefresh(wait = -1) {\n if (this.endDate) {\n return;\n }\n\n let refreshWait = wait;\n\n if (wait === -1) {\n const lastEventTime = this.getLastEventTime();\n refreshWait = Math.max(\n Math.min((new Date().getTime() - lastEventTime) / 2, MAX_CHAT_REFRESH),\n MIN_CHAT_REFRESH\n );\n }\n\n // cancel any outstanding timeout\n if (wait > -1 && this.refreshTimeout) {\n window.clearTimeout(this.refreshTimeout);\n }\n\n this.refreshTimeout = window.setTimeout(() => {\n if (this.refreshing) {\n this.scheduleRefresh();\n this.refreshing = false;\n } else {\n this.refreshing = true;\n }\n }, refreshWait);\n }\n\n private reset() {\n // clear out our sticky bin which we manipulated manually\n const stickyBin = this.getDiv('.sticky-bin');\n if (stickyBin) {\n while (stickyBin.childElementCount > 0) {\n stickyBin.removeChild(stickyBin.firstElementChild);\n }\n }\n\n this.endpoint = null;\n this.tickets = null;\n this.ticketEvents = {};\n this.eventGroups = [];\n this.fetching = false;\n this.complete = false;\n this.nextBefore = null;\n this.nextAfter = null;\n this.lastHeight = 0;\n }\n\n private handleEventGroupShow(event: MouseEvent) {\n const grouping = event.currentTarget as HTMLDivElement;\n const groupIndex = parseInt(grouping.getAttribute('data-group-index'));\n const eventGroup = this.eventGroups[\n this.eventGroups.length - groupIndex - 1\n ];\n eventGroup.open = true;\n this.requestUpdate('eventGroups');\n }\n\n private handleEventGroupHide(event: MouseEvent) {\n const grouping = event.currentTarget as HTMLDivElement;\n const groupIndex = parseInt(grouping.getAttribute('data-group-index'));\n const eventGroup = this.eventGroups[\n this.eventGroups.length - groupIndex - 1\n ];\n\n // mark us as closing\n eventGroup.closing = true;\n this.requestUpdate('eventGroups');\n\n // after our animation, close it up for real\n setTimeout(() => {\n eventGroup.closing = false;\n eventGroup.open = false;\n this.requestUpdate('eventGroups');\n }, 300);\n }\n\n private handleScroll() {\n const events = this.getEventsPane();\n\n // check if any of our sticky elements are off the screen\n const stickies = this.getEventsPane().querySelectorAll('.sticky');\n const stickyBin = this.getDiv('.sticky-bin');\n\n stickies.forEach((sticky: HTMLDivElement) => {\n const scrollBoundary = events.scrollTop + stickyBin.clientHeight + 136;\n if (!sticky.classList.contains('pinned')) {\n const eventElement = sticky.firstElementChild as HTMLDivElement;\n if (scrollBoundary > sticky.offsetTop) {\n sticky.style.height = eventElement.clientHeight + 'px';\n sticky.classList.add('pinned');\n (sticky as any).eventElement = eventElement;\n stickyBin.appendChild(eventElement);\n }\n } else {\n const eventElement = (sticky as any).eventElement;\n if (scrollBoundary < sticky.offsetTop + sticky.offsetHeight) {\n sticky.appendChild(eventElement);\n sticky.classList.remove('pinned');\n }\n }\n });\n\n if (events.scrollTop <= SCROLL_THRESHOLD) {\n if (this.eventGroups.length > 0 && !this.fetching && !this.complete) {\n this.fetching = true;\n }\n }\n }\n\n private updateMostRecent(newEvent: ContactEvent) {\n if (\n !this.mostRecentEvent ||\n this.mostRecentEvent.type !== newEvent.type ||\n this.mostRecentEvent.created_on !== newEvent.created_on\n ) {\n this.mostRecentEvent = newEvent;\n }\n }\n\n private getLastEventTime(): number {\n const mostRecentGroup = this.eventGroups[this.eventGroups.length - 1];\n if (mostRecentGroup) {\n const mostRecentEvent =\n mostRecentGroup.events[mostRecentGroup.events.length - 1];\n return new Date(mostRecentEvent.created_on).getTime();\n }\n return 0;\n }\n\n public renderEvent(event: ContactEvent): TemplateResult {\n switch (event.type) {\n case Events.IVR_CREATED:\n case Events.MESSAGE_CREATED:\n case Events.MESSAGE_RECEIVED:\n case Events.BROADCAST_CREATED:\n return renderMsgEvent(event as MsgEvent, this.agent);\n\n case Events.FLOW_ENTERED:\n case Events.FLOW_EXITED:\n return renderFlowEvent(event as FlowEvent);\n\n case Events.RUN_RESULT_CHANGED:\n return renderResultEvent(event as UpdateResultEvent);\n\n case Events.CONTACT_FIELD_CHANGED:\n return renderUpdateEvent(event as UpdateFieldEvent);\n\n case Events.CONTACT_NAME_CHANGED:\n return renderNameChanged(event as NameChangedEvent);\n\n case Events.CONTACT_URNS_CHANGED:\n return renderContactURNsChanged(event as URNsChangedEvent);\n\n case Events.EMAIL_SENT:\n return renderEmailSent(event as EmailSentEvent);\n\n case Events.INPUT_LABELS_ADDED:\n return renderLabelsAdded(event as LabelsAddedEvent);\n\n case Events.TICKET_OPENED: {\n const ticketEvent = event as TicketEvent;\n const activeTicket =\n !this.ticket || ticketEvent.ticket.uuid === this.ticket;\n\n let closeHandler = null;\n const ticket = this.getTicketForEvent(ticketEvent);\n if (activeTicket && ticket && ticket.status === 'open') {\n closeHandler = this.handleClose;\n }\n return renderTicketOpened(ticketEvent, closeHandler, !this.ticket);\n }\n case Events.TICKET_NOTE_ADDED:\n return renderNoteCreated(event as TicketEvent, this.agent);\n\n case Events.TICKET_ASSIGNED:\n return renderTicketAssigned(event as TicketEvent);\n case Events.TICKET_REOPENED: {\n return renderTicketAction(\n event as TicketEvent,\n 'reopened',\n !this.ticket\n );\n }\n case Events.TICKET_CLOSED:\n return renderTicketAction(event as TicketEvent, 'closed', !this.ticket);\n\n case Events.ERROR:\n case Events.FAILURE:\n return renderErrorMessage(event as ErrorMessageEvent);\n case Events.CONTACT_GROUPS_CHANGED:\n return renderContactGroupsEvent(event as ContactGroupsEvent);\n case Events.WEBHOOK_CALLED:\n return renderWebhookEvent(event as WebhookEvent);\n case Events.AIRTIME_TRANSFERRED:\n return renderAirtimeTransferredEvent(event as AirtimeTransferredEvent);\n case Events.CALL_STARTED:\n return renderCallStartedEvent();\n case Events.CAMPAIGN_FIRED:\n return renderCampaignFiredEvent(event as CampaignFiredEvent);\n case Events.CHANNEL_EVENT:\n return renderChannelEvent(event as ChannelEvent);\n case Events.CONTACT_LANGUAGE_CHANGED:\n return renderContactLanguageChangedEvent(\n event as ContactLanguageChangedEvent\n );\n }\n\n return html`<temba-icon\n name=\"alert-triangle\"\n style=\"fill:var(--color-error)\"\n ></temba-icon>\n <div class=\"description\">${event.type}</div>`;\n }\n\n private handleClose(uuid: string) {\n this.httpComplete = postJSON(`/api/v2/tickets.json?uuid=${uuid}`, {\n status: 'closed',\n })\n .then(() => {\n this.refreshTickets();\n this.refresh();\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid, status: 'closed' },\n });\n })\n .catch((response: any) => {\n console.error(response);\n });\n }\n\n public checkForAgentAssignmentEvent(agent: number) {\n this.httpComplete = getAssets(\n `/api/v2/tickets.json?ticket=${this.ticket}`\n ).then((assets: Asset[]) => {\n if (assets.length === 1) {\n const ticket = assets[0] as Ticket;\n if (ticket.assignee && ticket.assignee.id === agent) {\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid: this.ticket, assigned: 'self' },\n });\n } else {\n this.fireCustomEvent(CustomEventType.ContentChanged, {\n ticket: { uuid: this.ticket, assigned: 'other' },\n });\n }\n }\n });\n }\n\n public getEventHandlers() {\n return [\n {\n event: 'scroll',\n method: throttle(this.handleScroll, 50),\n },\n ];\n }\n\n /** Check if a ticket event is no longer represented in a session */\n private isPurged(ticket: Ticket): boolean {\n return !this.ticketEvents[ticket.uuid];\n }\n\n private renderEventContainer(event: ContactEvent) {\n const stickyId = this.getStickyId(event);\n const isSticky = !!stickyId;\n\n const renderedEvent = html`\n <div\n class=\"${this.ticket\n ? 'active-ticket'\n : ''} event ${event.type} ${isSticky ? 'has-sticky' : ''}\"\n data-sticky-id=\"${stickyId}\"\n >\n ${this.renderEvent(event)}\n </div>\n ${this.debug ? html`<pre>${JSON.stringify(event, null, 2)}</pre>` : null}\n `;\n\n if (stickyId) {\n return html`<div class=\"sticky\">${renderedEvent}</div>`;\n }\n\n return renderedEvent;\n }\n\n public render(): TemplateResult {\n // render our older tickets as faux-events\n const unfetchedTickets =\n this.eventGroups.length > 0 && this.tickets\n ? this.tickets.map((ticket: Ticket) => {\n if (ticket && ticket.status === 'open') {\n const opened = new Date(ticket.opened_on).getTime() * 1000;\n if (opened < this.nextBefore || this.isPurged(ticket)) {\n const ticketOpenedEvent = {\n type: Events.TICKET_OPENED,\n ticket: {\n uuid: ticket.uuid,\n topic: ticket.topic,\n body: ticket.body,\n ticketer: ticket.ticketer,\n },\n // eslint-disable-next-line @typescript-eslint/camelcase\n created_on: ticket.opened_on,\n };\n\n const renderedEvent = renderTicketOpened(\n ticketOpenedEvent,\n this.handleClose,\n !this.ticket\n );\n return html`<div class=\"event ticket_opened\">\n ${renderedEvent}\n </div>`;\n }\n }\n })\n : null;\n\n return html`\n ${this.ticket\n ? html`<div class=\"sticky-bin\">${unfetchedTickets}</div>`\n : this.contact\n ? html`<div class=\"scroll-title\">${this.contact.name}</div>`\n : null}\n ${this.fetching\n ? html`<temba-loading units=\"5\" size=\"10\"></temba-loading>`\n : html`<div style=\"height:0em\"></div>`}\n <div class=\"events\" @scroll=${this.handleScroll}>\n ${this.eventGroups.map((eventGroup: EventGroup, index: number) => {\n const grouping = getEventGroupType(eventGroup.events[0], this.ticket);\n const groupIndex = this.eventGroups.length - index - 1;\n\n const classes = getClasses({\n grouping: true,\n [grouping]: true,\n expanded: eventGroup.open,\n closing: eventGroup.closing,\n });\n\n return html`<div class=\"${classes}\">\n ${grouping === 'verbose'\n ? html`<div\n class=\"event-count\"\n @click=${this.handleEventGroupShow}\n data-group-index=\"${groupIndex}\"\n >\n ${eventGroup.events.length}\n ${eventGroup.events.length === 1 ? html`event` : html`events`}\n </div>`\n : null}\n ${grouping === 'verbose'\n ? html`\n <temba-icon\n @click=${this.handleEventGroupHide}\n data-group-index=\"${groupIndex}\"\n class=\"grouping-close-button\"\n name=\"x\"\n clickable\n ></temba-icon>\n `\n : null}\n ${eventGroup.events.map((event: ContactEvent) => {\n if (\n event.type === Events.TICKET_ASSIGNED &&\n (event as TicketEvent).note\n ) {\n const noteEvent = { ...event };\n noteEvent.type = Events.TICKET_NOTE_ADDED;\n\n return html`${this.renderEventContainer(\n noteEvent\n )}${this.renderEventContainer(event)}`;\n } else {\n return this.renderEventContainer(event);\n }\n })}\n </div>`;\n })}\n </div>\n\n <div class=\"new-messages-container\">\n <div\n @click=${() => {\n this.scrollToBottom(true);\n }}\n class=\"new-messages ${getClasses({\n expanded: this.showMessageAlert,\n })}\"\n >\n New Messages\n </div>\n </div>\n `;\n }\n}\n"]}
@@ -282,7 +282,7 @@ export const getEventStyles = () => {
282
282
  fill: rgba(223, 65, 159, 1);
283
283
  }
284
284
 
285
- .ticket_opened {
285
+ .active-ticket.ticket_opened {
286
286
  padding: 0em 1em;
287
287
  }
288
288
 
@@ -361,6 +361,13 @@ export const getEventStyles = () => {
361
361
  margin-left: 1px;
362
362
  }
363
363
 
364
+ .unsupported {
365
+ border: 1px solid #f2f2f2;
366
+ color: #999;
367
+ padding: 0.5em 1em;
368
+ border-radius: var(--curvature);
369
+ }
370
+
364
371
  .time {
365
372
  padding: 0.3em 1px;
366
373
  }
@@ -483,7 +490,10 @@ export const getEventGroupType = (event, ticket) => {
483
490
  case Events.TICKET_OPENED:
484
491
  case Events.TICKET_CLOSED:
485
492
  case Events.TICKET_REOPENED:
486
- if (!ticket || event.ticket.uuid === ticket) {
493
+ if (!ticket) {
494
+ return 'verbose';
495
+ }
496
+ if (event.ticket.uuid === ticket) {
487
497
  return 'tickets';
488
498
  }
489
499
  break;
@@ -530,12 +540,51 @@ export const renderAvatar = (user, agent = -1) => {
530
540
  </temba-tip>`;
531
541
  }
532
542
  };
543
+ export const renderAttachment = (attachment) => {
544
+ const idx = attachment.indexOf(':');
545
+ const attType = attachment.substr(0, idx);
546
+ const url = attachment.substr(idx + 1);
547
+ const [mediaType, ext] = attType.split('/', 2);
548
+ let inner = null;
549
+ if (mediaType === 'image') {
550
+ inner = html `<a href="${url}"><img src="${url}" style="width:100%;height:auto;display:block"></img></a>`;
551
+ }
552
+ else if (ext === 'pdf') {
553
+ return html `<div
554
+ style="width:100%;height:300px;border-radius:var(--curvature);box-shadow:0px 0px 10px -1px rgb(160 160 160);overflow:hidden"
555
+ ><embed src="${url}#view=Fit" type="application/pdf" frameBorder="0" scrolling="auto" height="100%" width="100%"></embed></div>`;
556
+ }
557
+ else if (mediaType === 'video') {
558
+ return html `<video max-width="400px" height="auto" controls="controls">
559
+ <source src="${url}" type="video/mp4" />
560
+ </video> `;
561
+ }
562
+ else {
563
+ return html `<div style="display:flex">
564
+ <temba-icon name="download"></temba-icon>
565
+ <div>Attachment ${ext}</div>
566
+ </div>`;
567
+ }
568
+ return html `<div
569
+ style="width:100%;max-width:300px;border-radius:var(--curvature); box-shadow:0px 0px 10px -1px rgb(160 160 160);overflow:hidden"
570
+ >
571
+ ${inner}
572
+ </div>`;
573
+ };
533
574
  export const renderMsgEvent = (event, agent) => {
534
575
  const isInbound = event.type === Events.MESSAGE_RECEIVED;
535
576
  const isError = event.status === 'E' || event.status === 'F';
536
- return html ` <div style="display:flex;align-items:flex-start">
577
+ const msg = html `<div style="display:flex;align-items:flex-start">
537
578
  <div style="display:flex;flex-direction:column">
538
- <div class="msg">${event.msg.text}</div>
579
+ ${event.msg.text ? html `<div class="msg">${event.msg.text}</div>` : null}
580
+ ${event.msg.attachments
581
+ ? html `<div class="attachments">
582
+ ${event.msg.attachments.map(attachment => renderAttachment(attachment))}
583
+ </div> `
584
+ : null}
585
+ ${!event.msg.text && !event.msg.attachments
586
+ ? html `<div class="unsupported">Unsupported Message</div>`
587
+ : null}
539
588
  <div
540
589
  class="msg-summary"
541
590
  style="flex-direction:row${isInbound ? '-reverse' : ''}"
@@ -575,6 +624,7 @@ export const renderMsgEvent = (event, agent) => {
575
624
  </div>`
576
625
  : null}
577
626
  </div>`;
627
+ return msg;
578
628
  };
579
629
  export const renderFlowEvent = (event) => {
580
630
  let verb = 'Interrupted';
@@ -621,10 +671,13 @@ export const renderUpdateEvent = (event) => {
621
671
  return html `
622
672
  <temba-icon name="contact"></temba-icon>
623
673
  <div class="description">
624
- Updated
625
- <div class="attn">${event.field.name}</div>
626
- to
627
- <div class="attn">${event.value.text}</div>
674
+ ${event.value
675
+ ? html `Updated
676
+ <div class="attn">${event.field.name}</div>
677
+ to
678
+ <div class="attn">${event.value.text}</div>`
679
+ : html `Cleared
680
+ <div class="attn">${event.field.name}</div>`}
628
681
  </div>
629
682
  `;
630
683
  };
@@ -685,19 +738,6 @@ export const renderNoteCreated = (event, agent) => {
685
738
  </div>
686
739
  </div>`;
687
740
  };
688
- export const renderTicketClosed = (event) => {
689
- const closed = new Date(event.ticket.opened_on);
690
- return html `
691
- <div class="assigned active">
692
- <div style="text-align:center">
693
- ${getDisplayName(event.created_by)} closed this ticket
694
- </div>
695
- <div class="subtext" style="justify-content:center">
696
- ${timeSince(closed, { hideRecentText: true, suffix: ' ago' })}
697
- </div>
698
- </div>
699
- `;
700
- };
701
741
  const getTicketIcon = (event) => {
702
742
  let icon = 'inbox';
703
743
  if (event.ticket.ticketer.name.indexOf('Email') > -1) {
@@ -708,8 +748,18 @@ const getTicketIcon = (event) => {
708
748
  }
709
749
  return icon;
710
750
  };
711
- export const renderTicketAction = (event, action) => {
751
+ export const renderTicketAction = (event, action, grouped) => {
712
752
  const reopened = new Date(event.created_on);
753
+ const icon = getTicketIcon(event);
754
+ if (grouped) {
755
+ return html `<div class="" style="display: flex">
756
+ <temba-icon name="${icon}"></temba-icon>
757
+ <div class="description">
758
+ ${getDisplayName(event.created_by)} ${action} a
759
+ <a href="/tickets/all/open/${event.ticket.uuid}">ticket</a>
760
+ </div>
761
+ </div>`;
762
+ }
713
763
  return html `
714
764
  <div class="assigned active">
715
765
  <div style="text-align:center">
@@ -739,32 +789,45 @@ export const renderTicketAssigned = (event) => {
739
789
  </div>
740
790
  `;
741
791
  };
742
- export const renderTicketOpened = (event, handleClose) => {
792
+ export const renderTicketOpened = (event, handleClose, grouped) => {
743
793
  const icon = getTicketIcon(event);
744
- return html `
745
- <temba-icon size="1.5" name="${icon}"></temba-icon>
746
-
747
- <div class="active" style="flex-grow:1;">
748
- Opened
749
- <div class="attn">${event.ticket.subject}</div>
750
- <div class="subtext">${timeSince(new Date(event.created_on))}</div>
751
- </div>
752
- ${handleClose
753
- ? html `
754
- <temba-tip text="Resolve" position="left" style="width:1.5em">
755
- <temba-icon
756
- class="clickable"
757
- size="1.5"
758
- name="check"
759
- @click=${() => {
760
- handleClose(event.ticket.uuid);
761
- }}
762
- ?clickable=${open}
763
- />
764
- </temba-tip>
765
- `
766
- : null}
767
- `;
794
+ if (grouped) {
795
+ return html `<div class="" style="display: flex">
796
+ <temba-icon name="${icon}"></temba-icon>
797
+ <div class="description">
798
+ ${event.ticket.topic.name}
799
+ <a href="/tickets/all/open/${event.ticket.uuid}">ticket</a> was opened
800
+ </div>
801
+ </div>`;
802
+ }
803
+ else {
804
+ return html `
805
+ <temba-icon size="1.5" name="${icon}"></temba-icon>
806
+
807
+ <div class="active" style="flex-grow:1;">
808
+ Opened
809
+ <div class="attn">
810
+ ${event.ticket.topic ? event.ticket.topic.name : 'General'}
811
+ </div>
812
+ <div class="subtext">${timeSince(new Date(event.created_on))}</div>
813
+ </div>
814
+ ${handleClose
815
+ ? html `
816
+ <temba-tip text="Resolve" position="left" style="width:1.5em">
817
+ <temba-icon
818
+ class="clickable"
819
+ size="1.5"
820
+ name="check"
821
+ @click=${() => {
822
+ handleClose(event.ticket.uuid);
823
+ }}
824
+ ?clickable=${open}
825
+ />
826
+ </temba-tip>
827
+ `
828
+ : null}
829
+ `;
830
+ }
768
831
  };
769
832
  export const renderErrorMessage = (event) => {
770
833
  return html `