feat(documents): дедупликация documents_meta и исправление field_label
- Исправлен N8N_CODE_PROCESS_UPLOADED_FILES_FIXED.js: использовать uploads_field_labels[0] вместо [grp] - Создан SQL_CLAIMSAVE_FIXED_NEW_FLOW_DEDUP.sql с дедупликацией documents_meta - Создан SQL_CLEANUP_DOCUMENTS_META_DUPLICATES.sql для очистки существующих дубликатов - Создан полный уникальный индекс idx_document_texts_hash_unique на document_texts(file_hash) - Добавлен SESSION_LOG_2025-11-28_documents_dedup.md с описанием всех изменений Fixes: - field_label теперь корректно отображает 'Переписка' вместо 'group-2' - documents_meta не накапливает дубликаты при повторных сохранениях - ON CONFLICT (file_hash) теперь работает для document_texts
This commit is contained in:
137
fix_nextcloud_collation_all.php
Normal file
137
fix_nextcloud_collation_all.php
Normal file
@@ -0,0 +1,137 @@
|
||||
<?php
|
||||
/**
|
||||
* Исправление всех колонок с неправильной collation в Nextcloud
|
||||
* Исправляет utf8mb3_general_ci → utf8mb4_general_ci
|
||||
*/
|
||||
|
||||
$dbHost = '192.168.128.3';
|
||||
$dbUser = 'nextcloud';
|
||||
$dbPass = 'nextcloud_password';
|
||||
$dbName = 'nextcloud';
|
||||
|
||||
try {
|
||||
$pdo = new PDO(
|
||||
"mysql:host=$dbHost;dbname=$dbName;charset=utf8mb4",
|
||||
$dbUser,
|
||||
$dbPass,
|
||||
[PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION]
|
||||
);
|
||||
|
||||
echo "=== ИСПРАВЛЕНИЕ COLLATION В NEXTCLOUD ===\n\n";
|
||||
|
||||
// Находим все колонки с неправильной collation
|
||||
$query = "
|
||||
SELECT
|
||||
TABLE_NAME,
|
||||
COLUMN_NAME,
|
||||
DATA_TYPE,
|
||||
CHARACTER_SET_NAME,
|
||||
COLLATION_NAME
|
||||
FROM
|
||||
INFORMATION_SCHEMA.COLUMNS
|
||||
WHERE
|
||||
TABLE_SCHEMA = ?
|
||||
AND TABLE_NAME LIKE 'oc_%'
|
||||
AND COLLATION_NAME = 'utf8mb3_general_ci'
|
||||
ORDER BY TABLE_NAME, COLUMN_NAME
|
||||
";
|
||||
|
||||
$stmt = $pdo->prepare($query);
|
||||
$stmt->execute([$dbName]);
|
||||
$columns = $stmt->fetchAll(PDO::FETCH_ASSOC);
|
||||
|
||||
if (empty($columns)) {
|
||||
echo "✅ Все колонки уже имеют правильную collation!\n";
|
||||
exit(0);
|
||||
}
|
||||
|
||||
echo "Найдено колонок с неправильной collation: " . count($columns) . "\n\n";
|
||||
|
||||
$fixed = 0;
|
||||
$errors = 0;
|
||||
|
||||
foreach ($columns as $col) {
|
||||
$table = $col['TABLE_NAME'];
|
||||
$column = $col['COLUMN_NAME'];
|
||||
$dataType = $col['DATA_TYPE'];
|
||||
$charSet = $col['CHARACTER_SET_NAME'];
|
||||
|
||||
// Определяем новый тип данных
|
||||
$newCharSet = 'utf8mb4';
|
||||
$newCollation = 'utf8mb4_general_ci';
|
||||
|
||||
// Для TEXT типов нужно указать CHARACTER SET
|
||||
$alterQuery = "ALTER TABLE `$table` MODIFY COLUMN `$column` ";
|
||||
|
||||
if (in_array(strtoupper($dataType), ['VARCHAR', 'CHAR', 'TEXT', 'TINYTEXT', 'MEDIUMTEXT', 'LONGTEXT'])) {
|
||||
// Получаем текущие параметры колонки
|
||||
$colInfoQuery = "SHOW FULL COLUMNS FROM `$table` WHERE Field = ?";
|
||||
$colInfoStmt = $pdo->prepare($colInfoQuery);
|
||||
$colInfoStmt->execute([$column]);
|
||||
$colInfo = $colInfoStmt->fetch(PDO::FETCH_ASSOC);
|
||||
|
||||
if ($colInfo) {
|
||||
$type = $colInfo['Type'];
|
||||
// Заменяем charset в типе
|
||||
$type = preg_replace('/utf8mb3/i', 'utf8mb4', $type);
|
||||
$type = preg_replace('/utf8(_general_ci)?/i', 'utf8mb4', $type);
|
||||
|
||||
$null = $colInfo['Null'] === 'YES' ? 'NULL' : 'NOT NULL';
|
||||
$default = $colInfo['Default'] !== null ? "DEFAULT '{$colInfo['Default']}'" : '';
|
||||
$extra = $colInfo['Extra'] ?: '';
|
||||
|
||||
$alterQuery .= "$type CHARACTER SET $newCharSet COLLATE $newCollation $null $default $extra";
|
||||
} else {
|
||||
echo "⚠️ Не удалось получить информацию о колонке $table.$column\n";
|
||||
continue;
|
||||
}
|
||||
} else {
|
||||
// Для других типов просто меняем collation
|
||||
$alterQuery .= "`$column` $dataType CHARACTER SET $newCharSet COLLATE $newCollation";
|
||||
}
|
||||
|
||||
try {
|
||||
echo "Исправляю: $table.$column ... ";
|
||||
$pdo->exec($alterQuery);
|
||||
echo "✅\n";
|
||||
$fixed++;
|
||||
} catch (PDOException $e) {
|
||||
echo "❌ Ошибка: " . $e->getMessage() . "\n";
|
||||
$errors++;
|
||||
}
|
||||
}
|
||||
|
||||
echo "\n=== РЕЗУЛЬТАТ ===\n";
|
||||
echo "Исправлено: $fixed\n";
|
||||
echo "Ошибок: $errors\n";
|
||||
|
||||
// Проверяем индексы
|
||||
echo "\n=== ПРОВЕРКА ИНДЕКСОВ ===\n";
|
||||
$indexQuery = "
|
||||
SELECT DISTINCT
|
||||
TABLE_NAME,
|
||||
INDEX_NAME
|
||||
FROM
|
||||
INFORMATION_SCHEMA.STATISTICS
|
||||
WHERE
|
||||
TABLE_SCHEMA = ?
|
||||
AND TABLE_NAME LIKE 'oc_%'
|
||||
AND COLLATION = 'utf8mb3_general_ci'
|
||||
";
|
||||
|
||||
$indexStmt = $pdo->prepare($indexQuery);
|
||||
$indexStmt->execute([$dbName]);
|
||||
$indexes = $indexStmt->fetchAll(PDO::FETCH_ASSOC);
|
||||
|
||||
if (!empty($indexes)) {
|
||||
echo "⚠️ Найдено индексов с неправильной collation: " . count($indexes) . "\n";
|
||||
echo "Индексы нужно пересоздать вручную или через Nextcloud\n";
|
||||
} else {
|
||||
echo "✅ Все индексы имеют правильную collation\n";
|
||||
}
|
||||
|
||||
} catch (PDOException $e) {
|
||||
echo "❌ Ошибка подключения к БД: " . $e->getMessage() . "\n";
|
||||
exit(1);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user