use-log-events.ts 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. import { useCallback, useEffect } from 'react'
  2. import { useLayoutContext } from '@/shared/context/layout-context'
  3. import { useIsNewEditorEnabled } from '@/features/ide-redesign/utils/new-editor-utils'
  4. import { useRailContext } from '@/features/ide-redesign/contexts/rail-context'
  5. import { useEditorContext } from '@/shared/context/editor-context'
  6. /**
  7. * This hook adds an event listener for events dispatched from the editor to the compile logs pane
  8. */
  9. export const useLogEvents = (setShowLogs: (show: boolean) => void) => {
  10. const { pdfLayout, setView } = useLayoutContext()
  11. const newEditor = useIsNewEditorEnabled()
  12. const { openTab: openRailTab } = useRailContext()
  13. const { hasPremiumSuggestion } = useEditorContext()
  14. const handleViewCompileLogEntryEventOldEditor = useCallback(
  15. (event: Event) => {
  16. const { id, suggestFix } = (
  17. event as CustomEvent<{ id: string; suggestFix?: boolean }>
  18. ).detail
  19. setShowLogs(true)
  20. if (pdfLayout === 'flat') {
  21. setView('pdf')
  22. }
  23. window.setTimeout(() => {
  24. const element = document.querySelector(
  25. `.log-entry[data-log-entry-id="${id}"]`
  26. )
  27. if (element) {
  28. element.scrollIntoView({
  29. block: 'start',
  30. inline: 'nearest',
  31. })
  32. if (suggestFix) {
  33. // if they are paywalled, click that instead
  34. const paywall = document.querySelector<HTMLButtonElement>(
  35. 'button[data-action="assistant-paywall-show"]'
  36. )
  37. if (paywall) {
  38. paywall.scrollIntoView({
  39. block: 'start',
  40. inline: 'nearest',
  41. })
  42. paywall.click()
  43. } else {
  44. element
  45. .querySelector<HTMLButtonElement>(
  46. 'button[data-action="suggest-fix"]'
  47. )
  48. ?.click()
  49. }
  50. }
  51. }
  52. })
  53. },
  54. [pdfLayout, setView, setShowLogs]
  55. )
  56. const handleViewCompileLogEntryEventNewEditor = useCallback(
  57. (event: Event) => {
  58. const { id, suggestFix } = (
  59. event as CustomEvent<{ id: string; suggestFix?: boolean }>
  60. ).detail
  61. openRailTab('errors')
  62. window.setTimeout(() => {
  63. const logEntry = document.querySelector(
  64. `.log-entry[data-log-entry-id="${id}"]`
  65. )
  66. if (logEntry) {
  67. logEntry.scrollIntoView({
  68. block: 'start',
  69. inline: 'nearest',
  70. })
  71. const expandCollapseButton =
  72. logEntry.querySelector<HTMLButtonElement>(
  73. 'button[data-action="expand-collapse"]'
  74. )
  75. const collapsed = expandCollapseButton?.dataset.collapsed === 'true'
  76. if (collapsed) {
  77. expandCollapseButton.click()
  78. }
  79. if (suggestFix) {
  80. if (hasPremiumSuggestion) {
  81. logEntry
  82. .querySelector<HTMLButtonElement>(
  83. 'button[data-action="suggest-fix"]'
  84. )
  85. ?.click()
  86. } else {
  87. window.dispatchEvent(
  88. new CustomEvent('aiAssist:showPaywall', {
  89. detail: { origin: 'suggest-fix' },
  90. })
  91. )
  92. }
  93. }
  94. }
  95. })
  96. },
  97. [openRailTab, hasPremiumSuggestion]
  98. )
  99. useEffect(() => {
  100. const listener = (event: Event) => {
  101. if (newEditor) {
  102. handleViewCompileLogEntryEventNewEditor(event)
  103. } else {
  104. handleViewCompileLogEntryEventOldEditor(event)
  105. }
  106. }
  107. window.addEventListener('editor:view-compile-log-entry', listener)
  108. return () => {
  109. window.removeEventListener('editor:view-compile-log-entry', listener)
  110. }
  111. }, [
  112. handleViewCompileLogEntryEventNewEditor,
  113. handleViewCompileLogEntryEventOldEditor,
  114. newEditor,
  115. ])
  116. }