migrationProgress.js 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. /**
  2. * Migration Progress Component
  3. * Displays detailed progress for comprehensive board migration
  4. */
  5. import { ReactiveVar } from 'meteor/reactive-var';
  6. import { ReactiveCache } from '/imports/reactiveCache';
  7. // Reactive variables for migration progress
  8. export const migrationProgress = new ReactiveVar(0);
  9. export const migrationStatus = new ReactiveVar('');
  10. export const migrationStepName = new ReactiveVar('');
  11. export const migrationStepProgress = new ReactiveVar(0);
  12. export const migrationStepStatus = new ReactiveVar('');
  13. export const migrationStepDetails = new ReactiveVar(null);
  14. export const migrationCurrentStep = new ReactiveVar(0);
  15. export const migrationTotalSteps = new ReactiveVar(0);
  16. export const isMigrating = new ReactiveVar(false);
  17. class MigrationProgressManager {
  18. constructor() {
  19. this.progressHistory = [];
  20. }
  21. /**
  22. * Update migration progress
  23. */
  24. updateProgress(progressData) {
  25. const {
  26. overallProgress,
  27. currentStep,
  28. totalSteps,
  29. stepName,
  30. stepProgress,
  31. stepStatus,
  32. stepDetails,
  33. boardId
  34. } = progressData;
  35. // Update reactive variables
  36. migrationProgress.set(overallProgress);
  37. migrationCurrentStep.set(currentStep);
  38. migrationTotalSteps.set(totalSteps);
  39. migrationStepName.set(stepName);
  40. migrationStepProgress.set(stepProgress);
  41. migrationStepStatus.set(stepStatus);
  42. migrationStepDetails.set(stepDetails);
  43. // Store in history
  44. this.progressHistory.push({
  45. timestamp: new Date(),
  46. ...progressData
  47. });
  48. // Update overall status
  49. migrationStatus.set(`${stepName}: ${stepStatus}`);
  50. }
  51. /**
  52. * Start migration
  53. */
  54. startMigration() {
  55. isMigrating.set(true);
  56. migrationProgress.set(0);
  57. migrationStatus.set('Starting migration...');
  58. migrationStepName.set('');
  59. migrationStepProgress.set(0);
  60. migrationStepStatus.set('');
  61. migrationStepDetails.set(null);
  62. migrationCurrentStep.set(0);
  63. migrationTotalSteps.set(0);
  64. this.progressHistory = [];
  65. }
  66. /**
  67. * Complete migration
  68. */
  69. completeMigration() {
  70. isMigrating.set(false);
  71. migrationProgress.set(100);
  72. migrationStatus.set('Migration completed successfully!');
  73. // Clear step details after a delay
  74. setTimeout(() => {
  75. migrationStepName.set('');
  76. migrationStepProgress.set(0);
  77. migrationStepStatus.set('');
  78. migrationStepDetails.set(null);
  79. migrationCurrentStep.set(0);
  80. migrationTotalSteps.set(0);
  81. }, 3000);
  82. }
  83. /**
  84. * Fail migration
  85. */
  86. failMigration(error) {
  87. isMigrating.set(false);
  88. migrationStatus.set(`Migration failed: ${error.message || error}`);
  89. migrationStepStatus.set('Error occurred');
  90. }
  91. /**
  92. * Get progress history
  93. */
  94. getProgressHistory() {
  95. return this.progressHistory;
  96. }
  97. /**
  98. * Clear progress
  99. */
  100. clearProgress() {
  101. isMigrating.set(false);
  102. migrationProgress.set(0);
  103. migrationStatus.set('');
  104. migrationStepName.set('');
  105. migrationStepProgress.set(0);
  106. migrationStepStatus.set('');
  107. migrationStepDetails.set(null);
  108. migrationCurrentStep.set(0);
  109. migrationTotalSteps.set(0);
  110. this.progressHistory = [];
  111. }
  112. }
  113. // Export singleton instance
  114. export const migrationProgressManager = new MigrationProgressManager();
  115. // Template helpers
  116. Template.migrationProgress.helpers({
  117. isMigrating() {
  118. return isMigrating.get();
  119. },
  120. overallProgress() {
  121. return migrationProgress.get();
  122. },
  123. overallStatus() {
  124. return migrationStatus.get();
  125. },
  126. currentStep() {
  127. return migrationCurrentStep.get();
  128. },
  129. totalSteps() {
  130. return migrationTotalSteps.get();
  131. },
  132. stepName() {
  133. return migrationStepName.get();
  134. },
  135. stepProgress() {
  136. return migrationStepProgress.get();
  137. },
  138. stepStatus() {
  139. return migrationStepStatus.get();
  140. },
  141. stepDetails() {
  142. return migrationStepDetails.get();
  143. },
  144. progressBarStyle() {
  145. const progress = migrationProgress.get();
  146. return `width: ${progress}%`;
  147. },
  148. stepProgressBarStyle() {
  149. const progress = migrationStepProgress.get();
  150. return `width: ${progress}%`;
  151. },
  152. stepNameFormatted() {
  153. const stepName = migrationStepName.get();
  154. if (!stepName) return '';
  155. // Convert snake_case to Title Case
  156. return stepName
  157. .split('_')
  158. .map(word => word.charAt(0).toUpperCase() + word.slice(1))
  159. .join(' ');
  160. },
  161. stepDetailsFormatted() {
  162. const details = migrationStepDetails.get();
  163. if (!details) return '';
  164. const formatted = [];
  165. for (const [key, value] of Object.entries(details)) {
  166. const formattedKey = key
  167. .split(/(?=[A-Z])/)
  168. .join(' ')
  169. .toLowerCase()
  170. .replace(/^\w/, c => c.toUpperCase());
  171. formatted.push(`${formattedKey}: ${value}`);
  172. }
  173. return formatted.join(', ');
  174. }
  175. });
  176. // Template events
  177. Template.migrationProgress.events({
  178. 'click .js-close-migration-progress'() {
  179. migrationProgressManager.clearProgress();
  180. }
  181. });