'auth'])); } $action = $_POST['action'] ?? $_GET['action'] ?? ''; $file = basename($_POST['file'] ?? $_GET['file'] ?? ''); $old = $_POST['old'] ?? $_GET['old'] ?? ''; $new = $_POST['new'] ?? $_GET['new'] ?? ''; // PATH LOCK: *.html only, no hidden, no GOLD/bak if (!preg_match('/^[a-zA-Z0-9_-]+\.html$/', $file)) { http_response_code(400); die(json_encode(['error'=>'invalid_filename', 'msg'=>'must be [a-zA-Z0-9_-]+.html'])); } $full = '/var/www/html/' . $file; if (!file_exists($full)) { http_response_code(404); die(json_encode(['error'=>'file_not_found', 'file'=>$full])); } $out = ['ok'=>false, 'action'=>$action, 'file'=>$file, 'ts'=>date('c')]; if ($action === 'sed_patch') { if ($old === '' || $new === '') die(json_encode(array_merge($out, ['error'=>'old_new_required']))); // Escape regex $old_esc = escapeshellarg($old); $new_esc = escapeshellarg($new); // GOLD $gold = '/opt/wevads/vault/' . $file . '.GOLD-' . date('Ymd-His') . '-safe-ops'; @shell_exec('cp ' . escapeshellarg($full) . ' ' . escapeshellarg($gold) . ' 2>&1'); // Unlock, patch, relock @shell_exec('sudo -n chattr -i ' . escapeshellarg($full) . ' 2>&1'); $before = (int) @shell_exec('grep -c ' . $old_esc . ' ' . escapeshellarg($full)); @shell_exec('sed -i "s|' . str_replace('|', '\\|', $old) . '|' . str_replace('|', '\\|', $new) . '|g" ' . escapeshellarg($full) . ' 2>&1'); $after = (int) @shell_exec('grep -c ' . $new_esc . ' ' . escapeshellarg($full)); @shell_exec('sudo -n chattr +i ' . escapeshellarg($full) . ' 2>&1'); @shell_exec('chown www-data:www-data ' . escapeshellarg($full) . ' 2>&1'); $out['ok'] = $after > 0; $out['before_count'] = $before; $out['after_count'] = $after; $out['gold'] = $gold; echo json_encode($out); exit; } if ($action === 'splice_drill') { // Inject drill-down block before $block_src = '/tmp/drill-block.html'; if (!file_exists($block_src)) die(json_encode(array_merge($out, ['error'=>'drill_block_missing']))); // Already has drill? $has = (int) @shell_exec('grep -c __opusUniversalDrill ' . escapeshellarg($full)); if ($has > 0) { $out['ok'] = true; $out['already'] = true; echo json_encode($out); exit; } $line = (int) @shell_exec('grep -n "" ' . escapeshellarg($full) . ' | head -1 | cut -d: -f1'); if ($line <= 0) die(json_encode(array_merge($out, ['error'=>'no_body_tag']))); $gold = '/opt/wevads/vault/' . $file . '.GOLD-' . date('Ymd-His') . '-safe-splice'; @shell_exec('cp ' . escapeshellarg($full) . ' ' . escapeshellarg($gold) . ' 2>&1'); @shell_exec('sudo -n chattr -i ' . escapeshellarg($full) . ' 2>&1'); $tmp = '/tmp/splice-' . uniqid() . '.html'; @shell_exec('head -n ' . ($line-1) . ' ' . escapeshellarg($full) . ' > ' . escapeshellarg($tmp)); @shell_exec('cat ' . escapeshellarg($block_src) . ' >> ' . escapeshellarg($tmp)); @shell_exec('tail -n +' . $line . ' ' . escapeshellarg($full) . ' >> ' . escapeshellarg($tmp)); @shell_exec('cp ' . escapeshellarg($tmp) . ' ' . escapeshellarg($full)); @shell_exec('chown www-data:www-data ' . escapeshellarg($full) . ' 2>&1'); @shell_exec('sudo -n chattr +i ' . escapeshellarg($full) . ' 2>&1'); @shell_exec('rm -f ' . escapeshellarg($tmp)); $after = (int) @shell_exec('grep -c __opusUniversalDrill ' . escapeshellarg($full)); $out['ok'] = $after > 0; $out['after_count'] = $after; $out['injected_line'] = $line; $out['gold'] = $gold; echo json_encode($out); exit; } if ($action === 'validate') { $out['has_drill'] = (int) @shell_exec('grep -c __opusUniversalDrill ' . escapeshellarg($full)); $out['size_bytes'] = filesize($full); $out['md5'] = md5_file($full); $lsattr = trim(@shell_exec('lsattr ' . escapeshellarg($full) . ' 2>&1')); $out['immutable'] = (strpos($lsattr, 'i') !== false); $hs = @file_get_contents('https://weval-consulting.com/' . $file); $out['http_ok'] = ($hs !== false && strlen($hs) > 100); $out['ok'] = true; echo json_encode($out); exit; } die(json_encode(array_merge($out, ['error'=>'unknown_action', 'available'=>['sed_patch','splice_drill','validate']])));