fix: reacciones y audio en chat turnero
- chat_react: guardaba en tabla `messages` en lugar de `conversations` (tabla real del chat) - chat_react: columna era `whatsapp_message_id`; la correcta es `message_id` - chat.php: sendReactionEmoji actualiza la burbuja DOM inmediatamente sin esperar poll - chat_upload_media: mime_content_type() devuelve video/webm en Linux para audio grabado; ahora cualquier mime con "webm" se remapea a audio/ogg antes de determinar mediaType Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 4.6
parent
ab72750410
commit
f975844d9d
@@ -34,7 +34,7 @@ try {
|
|||||||
|
|
||||||
// Guardar reacción en el mensaje
|
// Guardar reacción en el mensaje
|
||||||
$db->query(
|
$db->query(
|
||||||
"UPDATE messages SET reaction_emoji = ?, reaction_to_message_id = ? WHERE whatsapp_message_id = ?",
|
"UPDATE conversations SET reaction_emoji = ?, reaction_to_message_id = ? WHERE message_id = ?",
|
||||||
[$emoji, $messageId, $messageId]
|
[$emoji, $messageId, $messageId]
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|||||||
@@ -22,9 +22,15 @@ if ($file['error'] !== UPLOAD_ERR_OK) tmErr('Error al subir archivo: código ' .
|
|||||||
$maxBytes = 64 * 1024 * 1024; // 64 MB
|
$maxBytes = 64 * 1024 * 1024; // 64 MB
|
||||||
if ($file['size'] > $maxBytes) tmErr('El archivo supera el límite de 64 MB');
|
if ($file['size'] > $maxBytes) tmErr('El archivo supera el límite de 64 MB');
|
||||||
|
|
||||||
$mime = mime_content_type($file['tmp_name']) ?: $file['type'];
|
$detectedMime = mime_content_type($file['tmp_name']) ?: $file['type'];
|
||||||
$caption = trim($_POST['caption'] ?? '');
|
$browserMime = $file['type'] ?: '';
|
||||||
$isVoice = !empty($_POST['is_voice']);
|
$caption = trim($_POST['caption'] ?? '');
|
||||||
|
$isVoice = !empty($_POST['is_voice']);
|
||||||
|
|
||||||
|
// mime_content_type() returns video/webm for browser-recorded audio (same WebM container).
|
||||||
|
// WhatsApp rejects webm; map to audio/ogg (same Opus codec, accepted format).
|
||||||
|
$mime = (str_contains($detectedMime, 'webm') || str_contains($browserMime, 'webm'))
|
||||||
|
? 'audio/ogg' : $detectedMime;
|
||||||
|
|
||||||
// Determinar tipo de media
|
// Determinar tipo de media
|
||||||
if (str_starts_with($mime, 'image/')) $mediaType = 'image';
|
if (str_starts_with($mime, 'image/')) $mediaType = 'image';
|
||||||
@@ -42,11 +48,8 @@ try {
|
|||||||
|
|
||||||
$wa = new WhatsAppService('turnero');
|
$wa = new WhatsAppService('turnero');
|
||||||
|
|
||||||
// WhatsApp no acepta audio/webm — reenviar como audio/ogg (mismo codec Opus)
|
|
||||||
$uploadMime = (str_starts_with($mime, 'audio/webm')) ? 'audio/ogg' : $mime;
|
|
||||||
|
|
||||||
// Subir a WhatsApp Media API
|
// Subir a WhatsApp Media API
|
||||||
$uploadResult = $wa->uploadMedia($file['tmp_name'], $uploadMime);
|
$uploadResult = $wa->uploadMedia($file['tmp_name'], $mime);
|
||||||
if (!$uploadResult || !isset($uploadResult['id'])) {
|
if (!$uploadResult || !isset($uploadResult['id'])) {
|
||||||
tmErr('No se pudo subir el archivo a WhatsApp', 502);
|
tmErr('No se pudo subir el archivo a WhatsApp', 502);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -931,13 +931,30 @@ function showReactionPicker(e, waId) {
|
|||||||
async function sendReactionEmoji(emoji) {
|
async function sendReactionEmoji(emoji) {
|
||||||
document.getElementById('reaction-picker').classList.remove('show');
|
document.getElementById('reaction-picker').classList.remove('show');
|
||||||
if (!_reactionTarget || !state.activeUserId) return;
|
if (!_reactionTarget || !state.activeUserId) return;
|
||||||
|
const waId = _reactionTarget;
|
||||||
try {
|
try {
|
||||||
await fetch(BASE + API_REACT, {
|
const res = await fetch(BASE + API_REACT, {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
headers: { 'Content-Type': 'application/json' },
|
headers: { 'Content-Type': 'application/json' },
|
||||||
body: JSON.stringify({ user_id: state.activeUserId, message_id: _reactionTarget, emoji })
|
body: JSON.stringify({ user_id: state.activeUserId, message_id: waId, emoji })
|
||||||
});
|
});
|
||||||
await pollMessages();
|
const json = await res.json();
|
||||||
|
if (json.success) {
|
||||||
|
// Actualizar burbuja en el DOM inmediatamente
|
||||||
|
const bubble = document.querySelector(`[data-wa-id="${waId}"]`);
|
||||||
|
if (bubble) {
|
||||||
|
let reEl = bubble.querySelector('.msg-reaction');
|
||||||
|
if (!reEl) {
|
||||||
|
reEl = document.createElement('div');
|
||||||
|
reEl.className = 'msg-reaction';
|
||||||
|
bubble.appendChild(reEl);
|
||||||
|
}
|
||||||
|
reEl.textContent = emoji;
|
||||||
|
}
|
||||||
|
// Actualizar estado en memoria para consistencia
|
||||||
|
const m = state.messages.find(x => x.message_id === waId);
|
||||||
|
if (m) m.reaction_emoji = emoji;
|
||||||
|
}
|
||||||
} catch(e) { console.error('reaction:', e); }
|
} catch(e) { console.error('reaction:', e); }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user