@@ -45,6 +45,8 @@ public function __construct(
4545 }
4646
4747 /**
48+ * Get the message
49+ *
4850 * @return string
4951 */
5052 public function getNotUpToDateMessage () : string
@@ -53,6 +55,8 @@ public function getNotUpToDateMessage() : string
5355 }
5456
5557 /**
58+ * Check calculate schema differences
59+ *
5660 * @return bool
5761 */
5862 public function isUpToDate () : bool
@@ -97,7 +101,7 @@ private function calculateDiff() : array
97101 * @param array $diffData
98102 * @return array
99103 */
100- private function buildSummary (array $ diffData ) : array
104+ private function buildSummary (array $ diffData ): array
101105 {
102106 $ summary = [
103107 'timestamp ' => date ('Y-m-d H:i:s ' ),
@@ -106,85 +110,117 @@ private function buildSummary(array $diffData) : array
106110 'affected_tables ' => [],
107111 'changes ' => []
108112 ];
109-
110113 try {
111- foreach ($ diffData as $ key => $ operations ) {
114+ foreach ($ diffData as $ operations ) {
112115 if (!is_array ($ operations )) {
113116 continue ;
114117 }
115-
116118 foreach ($ operations as $ operationType => $ changes ) {
117- if (!isset ($ summary ['by_change_type ' ][$ operationType ])) {
118- $ summary ['by_change_type ' ][$ operationType ] = 0 ;
119- }
119+ $ this ->initChangeTypeCount ($ summary , $ operationType );
120120
121121 $ changeCount = is_array ($ changes ) ? count ($ changes ) : 1 ;
122122 $ summary ['by_change_type ' ][$ operationType ] += $ changeCount ;
123123 $ summary ['total_differences ' ] += $ changeCount ;
124124
125- if (is_array ($ changes )) {
126- foreach ($ changes as $ changeIndex => $ change ) {
127- $ changeInfo = [
128- 'operation ' => $ operationType ,
129- 'index ' => $ changeIndex
130- ];
131-
132- $ tableName = $ this ->safeGetTableName ($ change );
133- if ($ tableName ) {
134- $ changeInfo ['table ' ] = $ tableName ;
135-
136- if (!isset ($ summary ['affected_tables ' ][$ tableName ])) {
137- $ summary ['affected_tables ' ][$ tableName ] = [];
138- }
139-
140- if (!isset ($ summary ['affected_tables ' ][$ tableName ][$ operationType ])) {
141- $ summary ['affected_tables ' ][$ tableName ][$ operationType ] = 0 ;
142- }
143-
144- $ summary ['affected_tables ' ][$ tableName ][$ operationType ]++;
145- }
146-
147- // Add any other safely extractable information
148- if ($ change instanceof ElementHistory) {
149- $ changeInfo = $ this ->processElementHistory ($ change , $ changeInfo );
150- } elseif (is_array ($ change ) && isset ($ change ['name ' ])) {
151- $ changeInfo ['name ' ] = $ change ['name ' ];
152- } elseif (is_object ($ change ) && method_exists ($ change , 'getName ' )) {
153- $ changeInfo ['name ' ] = $ change ->getName ();
154-
155- // Special handling for index elements
156- if (method_exists ($ change , 'getType ' ) && ($ change ->getType () === 'index ' || $ change ->getType () === 'constraint ' )) {
157- $ changeInfo ['type ' ] = $ change ->getType ();
158-
159- // Try to get the index columns if available
160- if (method_exists ($ change , 'getColumns ' )) {
161- $ columns = $ change ->getColumns ();
162- if (is_array ($ columns )) {
163- $ changeInfo ['columns ' ] = [];
164- foreach ($ columns as $ column ) {
165- if (is_object ($ column ) && method_exists ($ column , 'getName ' )) {
166- $ changeInfo ['columns ' ][] = $ column ->getName ();
167- } elseif (is_string ($ column )) {
168- $ changeInfo ['columns ' ][] = $ column ;
169- }
170- }
171- }
172- }
173- }
174- }
175-
176- $ summary ['changes ' ][] = $ changeInfo ;
177- }
125+ if (!is_array ($ changes )) {
126+ continue ;
127+ }
128+
129+ foreach ($ changes as $ changeIndex => $ change ) {
130+ $ changeInfo = $ this ->buildChangeInfo ($ change , $ operationType , $ changeIndex , $ summary );
131+ $ summary ['changes ' ][] = $ changeInfo ;
178132 }
179133 }
180134 }
181135 } catch (\Exception $ e ) {
182136 $ summary ['error ' ] = $ e ->getMessage ();
183137 }
184-
185138 return $ summary ;
186139 }
187140
141+ /**
142+ * Initialize the counter for a given operation type in the summary if not already set.
143+ *
144+ * @param array &$summary
145+ * @param string $operationType
146+ */
147+ private function initChangeTypeCount (array &$ summary , string $ operationType ): void
148+ {
149+ if (!isset ($ summary ['by_change_type ' ][$ operationType ])) {
150+ $ summary ['by_change_type ' ][$ operationType ] = 0 ;
151+ }
152+ }
153+
154+ /**
155+ * Build a structured array with information about a single change operation.
156+ *
157+ * @param mixed $change
158+ * @param string $operationType
159+ * @param int|string $changeIndex
160+ * @param array $summary
161+ * @return array
162+ */
163+ private function buildChangeInfo ($ change , $ operationType , $ changeIndex , &$ summary ): array
164+ {
165+ $ changeInfo = [
166+ 'operation ' => $ operationType ,
167+ 'index ' => $ changeIndex
168+ ];
169+
170+ $ tableName = $ this ->safeGetTableName ($ change );
171+ if ($ tableName ) {
172+ $ changeInfo ['table ' ] = $ tableName ;
173+
174+ if (!isset ($ summary ['affected_tables ' ][$ tableName ])) {
175+ $ summary ['affected_tables ' ][$ tableName ] = [];
176+ }
177+ if (!isset ($ summary ['affected_tables ' ][$ tableName ][$ operationType ])) {
178+ $ summary ['affected_tables ' ][$ tableName ][$ operationType ] = 0 ;
179+ }
180+ $ summary ['affected_tables ' ][$ tableName ][$ operationType ]++;
181+ }
182+
183+ if ($ change instanceof ElementHistory) {
184+ $ changeInfo = $ this ->processElementHistory ($ change , $ changeInfo );
185+ } elseif (is_array ($ change ) && isset ($ change ['name ' ])) {
186+ $ changeInfo ['name ' ] = $ change ['name ' ];
187+ } elseif (is_object ($ change ) && method_exists ($ change , 'getName ' )) {
188+ $ changeInfo ['name ' ] = $ change ->getName ();
189+
190+ if (method_exists ($ change , 'getType ' )) {
191+ $ this ->isMethodExists ($ change , $ changeInfo );
192+ }
193+ }
194+ return $ changeInfo ;
195+ }
196+
197+ /**
198+ * Build a structured array with method exist information.
199+ *
200+ * @param mixed $change
201+ * @param array $changeInfo
202+ */
203+ private function isMethodExists (mixed $ change , array $ changeInfo ): void
204+ {
205+ $ type = $ change ->getType ();
206+ if ($ type === 'index ' || $ type === 'constraint ' ) {
207+ $ changeInfo ['type ' ] = $ type ;
208+ if (method_exists ($ change , 'getColumns ' )) {
209+ $ columns = $ change ->getColumns ();
210+ if (is_array ($ columns )) {
211+ $ changeInfo ['columns ' ] = array_map (function ($ column ) {
212+ if (is_object ($ column ) && method_exists ($ column , 'getName ' )) {
213+ return $ column ->getName ();
214+ }
215+ return is_string ($ column ) ? $ column : null ;
216+ }, $ columns );
217+ // Remove any nulls if any invalid columns found
218+ $ changeInfo ['columns ' ] = array_filter ($ changeInfo ['columns ' ]);
219+ }
220+ }
221+ }
222+ }
223+
188224 /**
189225 * Safely get table name from any change object
190226 *
@@ -236,6 +272,7 @@ private function safeGetTableName($change): ?string
236272 }
237273 } catch (\Exception $ e ) {
238274 // Silently fail and return null
275+ error_log ('Error get table name: ' . $ e ->getMessage ());
239276 }
240277
241278 return null ;
@@ -269,7 +306,8 @@ private function processElementHistory($change, array $changeInfo): array
269306 }
270307
271308 // For modify operations, add basic diff information
272- if (($ changeInfo ['operation ' ] === 'modify_column ' || $ changeInfo ['operation ' ] === 'modify_table ' ) && $ oldElement && $ newElement ) {
309+ if (($ changeInfo ['operation ' ] === 'modify_column ' || $ changeInfo ['operation ' ] === 'modify_table ' )
310+ && $ oldElement && $ newElement ) {
273311 // Check for comment differences (most common issue)
274312 if (method_exists ($ oldElement , 'getComment ' ) && method_exists ($ newElement , 'getComment ' )) {
275313 $ oldComment = $ oldElement ->getComment ();
@@ -284,6 +322,7 @@ private function processElementHistory($change, array $changeInfo): array
284322 }
285323 } catch (\Exception $ e ) {
286324 // Silently fail and return original changeInfo
325+ error_log ('Error processing element history: ' . $ e ->getMessage ());
287326 }
288327
289328 return $ changeInfo ;
0 commit comments