Fix manifest infinite loop from incomplete entries

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
root
2026-01-15 08:31:31 +00:00
parent 1683df867b
commit 61f8f058f2
3 changed files with 17 additions and 6 deletions

View File

@@ -83,7 +83,7 @@ class _Manifest_Builder_Helper
// This creates a map of className => filename (not full metadata to save space)
// NOTE: Class override detection (rsx/ vs app/RSpade/) happens earlier in _check_unique_base_class_names()
foreach (Manifest::$data['data']['files'] as $file => $filedata) {
if ($filedata['extension'] == $ext && !empty($filedata['class'])) {
if (isset($filedata['extension']) && $filedata['extension'] == $ext && !empty($filedata['class'])) {
$class_name = $filedata['class'];
// Duplicates should have been caught by _check_unique_base_class_names()

View File

@@ -310,21 +310,32 @@ class _Manifest_Quality_Helper
// Valid override: exactly one file in rsx/, rest in app/RSpade/
if (count($rsx_files) === 1 && count($framework_files) >= 1) {
$did_change = false;
// Rename framework files to .upstream and remove from manifest
foreach ($framework_files as $framework_file) {
$full_framework_path = base_path($framework_file);
$upstream_path = $full_framework_path . '.upstream';
if (file_exists($full_framework_path) && !file_exists($upstream_path)) {
// Normal case: rename to .upstream
rename($full_framework_path, $upstream_path);
console_debug('MANIFEST', "Class override: {$class_name} - moved {$framework_file} to .upstream");
$did_change = true;
} elseif (file_exists($full_framework_path) && file_exists($upstream_path)) {
// Self-healing: both .php and .php.upstream exist (e.g., after framework update)
// Remove the .php file since .upstream is the correct archived version
unlink($full_framework_path);
console_debug('MANIFEST', "Class override: {$class_name} - removed duplicate {$framework_file} (upstream already exists)");
$did_change = true;
}
// Remove from manifest data so it won't be indexed
unset(Manifest::$data['data']['files'][$framework_file]);
}
Manifest::$_needs_manifest_restart = true;
if ($did_change) {
Manifest::$_needs_manifest_restart = true;
}
continue;
}

View File

@@ -168,8 +168,8 @@ class _Manifest_Scanner_Helper
$current_size = filesize($absolute_path);
// Stage 1: Size check
if ($old['size'] != $current_size) {
// Stage 1: Size check (guard for incomplete manifest entries)
if (!isset($old['size']) || $old['size'] != $current_size) {
// Only show the message once per page load
if (!Manifest::$__shown_rescan_message) {
console_debug('MANIFEST', '* File ' . $file . ' has changed size, triggering manifest rescan *');
@@ -180,9 +180,9 @@ class _Manifest_Scanner_Helper
return true;
}
// Stage 2: mtime check
// Stage 2: mtime check (guard for incomplete manifest entries)
$current_mtime = filemtime($absolute_path);
if ($old['mtime'] != $current_mtime) {
if (!isset($old['mtime']) || $old['mtime'] != $current_mtime) {
// Only show the message once per page load
if (!Manifest::$__shown_rescan_message) {
console_debug('MANIFEST', '* File ' . $file . ' has changed mtime, triggering manifest rescan *');