useAppMaintenanceCheck.ts 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115
  1. // Copyright (C) 2012-2024 Zammad Foundation, https://zammad-foundation.org/
  2. import { onMounted, reactive, watch } from 'vue'
  3. import { useRouteQuery } from '@vueuse/router'
  4. import {
  5. useNotifications,
  6. NotificationTypes,
  7. } from '#shared/components/CommonNotifications/index.ts'
  8. import { useApplicationBuildChecksumQuery } from '#shared/graphql/queries/applicationBuildChecksum.api.ts'
  9. import { useAppMaintenanceSubscription } from '#shared/graphql/subscriptions/appMaintenance.api.ts'
  10. import type {
  11. ApplicationBuildChecksumQuery,
  12. ApplicationBuildChecksumQueryVariables,
  13. AppMaintenanceSubscription,
  14. AppMaintenanceSubscriptionVariables,
  15. } from '#shared/graphql/types.ts'
  16. import { EnumAppMaintenanceType } from '#shared/graphql/types.ts'
  17. import {
  18. QueryHandler,
  19. SubscriptionHandler,
  20. } from '#shared/server/apollo/handler/index.ts'
  21. import testFlags from '#shared/utils/testFlags.ts'
  22. let checksumQuery: QueryHandler<
  23. ApplicationBuildChecksumQuery,
  24. ApplicationBuildChecksumQueryVariables
  25. >
  26. let previousChecksum: string
  27. let appMaintenanceSubscription: SubscriptionHandler<
  28. AppMaintenanceSubscription,
  29. AppMaintenanceSubscriptionVariables
  30. >
  31. interface UseAppMaintenanceCheckOptions {
  32. onNeedRefresh?: () => void
  33. }
  34. const useAppMaintenanceCheck = (
  35. maintenanceOptions: UseAppMaintenanceCheckOptions = {},
  36. ) => {
  37. const notify = (message: string, callback?: () => void) => {
  38. useNotifications().notify({
  39. message,
  40. type: NotificationTypes.Warn,
  41. persistent: true,
  42. callback,
  43. })
  44. }
  45. onMounted(() => {
  46. if (checksumQuery) return
  47. // Default poll interval: every minute.
  48. const defaultPollInterval = 60 * 1000
  49. const applicationRebuildCheckInterval = useRouteQuery(
  50. 'ApplicationRebuildCheckInterval',
  51. defaultPollInterval.toString(),
  52. )
  53. const options = reactive({
  54. pollInterval: parseInt(applicationRebuildCheckInterval.value, 10),
  55. })
  56. watch(applicationRebuildCheckInterval, () => {
  57. options.pollInterval = parseInt(applicationRebuildCheckInterval.value, 10)
  58. })
  59. checksumQuery = new QueryHandler(useApplicationBuildChecksumQuery(options))
  60. const notificationMessage = __(
  61. 'A newer version of the app is available. Please reload at your earliest.',
  62. )
  63. checksumQuery.watchOnResult((queryResult): void => {
  64. if (!queryResult?.applicationBuildChecksum.length) return
  65. if (!previousChecksum) {
  66. previousChecksum = queryResult?.applicationBuildChecksum
  67. testFlags.set('useApplicationBuildChecksumQuery.firstResult')
  68. }
  69. if (queryResult?.applicationBuildChecksum !== previousChecksum) {
  70. notify(notificationMessage, maintenanceOptions.onNeedRefresh)
  71. }
  72. })
  73. appMaintenanceSubscription = new SubscriptionHandler(
  74. useAppMaintenanceSubscription(),
  75. )
  76. appMaintenanceSubscription.onResult((result) => {
  77. const type = result.data?.appMaintenance?.type
  78. let message = notificationMessage
  79. if (!type) {
  80. testFlags.set('useAppMaintenanceSubscription.subscribed')
  81. return
  82. }
  83. switch (type) {
  84. case EnumAppMaintenanceType.ConfigChanged:
  85. message = __(
  86. 'The configuration of Zammad has changed. Please reload at your earliest.',
  87. )
  88. break
  89. case EnumAppMaintenanceType.RestartAuto:
  90. case EnumAppMaintenanceType.RestartManual:
  91. // TODO: this case cannot be handled right now. Legacy interface performs a connectivity check.
  92. break
  93. default:
  94. break
  95. }
  96. notify(message, () => window.location.reload())
  97. })
  98. })
  99. }
  100. export default useAppMaintenanceCheck