Add test-chat.html for testing customer chat initiation

Simple web page for testing the chat flow as a customer.
Enter BusinessID and start a chat that appears on the HUD.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
John Mizerek 2026-02-08 15:25:34 -08:00
parent 8108924dcd
commit 4cfcb728cc

306
test-chat.html Normal file
View file

@ -0,0 +1,306 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Test Chat - Customer</title>
<style>
* { margin: 0; padding: 0; box-sizing: border-box; }
body {
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
background: #1a1a1a;
color: #fff;
min-height: 100vh;
padding: 20px;
}
h1 { margin-bottom: 20px; }
.form-group { margin-bottom: 16px; }
label { display: block; margin-bottom: 4px; color: #888; font-size: 14px; }
input, select, textarea {
width: 100%;
padding: 12px;
border: 1px solid #333;
border-radius: 8px;
background: #222;
color: #fff;
font-size: 16px;
}
button {
padding: 12px 24px;
border: none;
border-radius: 8px;
font-size: 16px;
font-weight: 600;
cursor: pointer;
margin-right: 8px;
margin-bottom: 8px;
}
.btn-primary { background: #2196f3; color: #fff; }
.btn-secondary { background: #333; color: #fff; }
.btn-success { background: #22c55e; color: #fff; }
.result {
margin-top: 20px;
padding: 16px;
border-radius: 8px;
background: #222;
white-space: pre-wrap;
font-family: monospace;
font-size: 14px;
}
.chat-container {
display: none;
margin-top: 20px;
border: 1px solid #333;
border-radius: 12px;
overflow: hidden;
}
.chat-container.visible { display: block; }
.chat-messages {
height: 300px;
overflow-y: auto;
padding: 16px;
background: #111;
}
.chat-message {
max-width: 80%;
padding: 10px 14px;
border-radius: 12px;
margin-bottom: 8px;
font-size: 14px;
}
.chat-message.customer {
background: #2196f3;
margin-left: auto;
}
.chat-message.staff {
background: #333;
}
.chat-input-area {
display: flex;
gap: 8px;
padding: 12px;
background: #1a1a1a;
}
.chat-input-area input { flex: 1; }
.chat-input-area button { flex-shrink: 0; }
.info { color: #888; font-size: 14px; margin-bottom: 20px; }
</style>
</head>
<body>
<h1>Test Chat (Customer View)</h1>
<p class="info">Use this page to test initiating a chat as a customer. The chat will appear on the HUD.</p>
<div class="form-group">
<label>Business ID</label>
<input type="number" id="businessId" value="" placeholder="Enter business ID (e.g., 17 for Quick Bites)">
</div>
<div class="form-group">
<label>Service Point ID (optional - for dine-in)</label>
<input type="number" id="servicePointId" value="0" placeholder="0 for remote chat">
</div>
<div class="form-group">
<label>User ID (optional - for remote chat)</label>
<input type="number" id="userId" value="0" placeholder="Your user ID">
</div>
<div class="form-group">
<label>Initial Message (optional)</label>
<textarea id="initialMessage" rows="2" placeholder="Hello, I need help..."></textarea>
</div>
<button class="btn-primary" onclick="startChat()">Start Chat</button>
<button class="btn-secondary" onclick="checkActiveChat()">Check Active Chat</button>
<div class="result" id="result" style="display:none;"></div>
<div class="chat-container" id="chatContainer">
<div class="chat-messages" id="chatMessages"></div>
<div class="chat-input-area">
<input type="text" id="chatInput" placeholder="Type a message..." onkeypress="if(event.key==='Enter')sendMessage()">
<button class="btn-success" onclick="sendMessage()">Send</button>
<button class="btn-secondary" onclick="closeChat()">Close</button>
</div>
</div>
<script>
let currentTaskId = null;
let pollInterval = null;
let lastMessageId = 0;
// Load saved business ID
document.getElementById('businessId').value = localStorage.getItem('test_chat_business_id') || '';
async function startChat() {
const businessId = parseInt(document.getElementById('businessId').value) || 0;
const servicePointId = parseInt(document.getElementById('servicePointId').value) || 0;
const userId = parseInt(document.getElementById('userId').value) || 0;
const message = document.getElementById('initialMessage').value.trim();
if (!businessId) {
showResult('Error: BusinessID is required');
return;
}
// Save for next time
localStorage.setItem('test_chat_business_id', businessId);
try {
const response = await fetch('/api/tasks/createChat.cfm', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
BusinessID: businessId,
ServicePointID: servicePointId,
UserID: userId,
Message: message
})
});
const data = await response.json();
showResult(JSON.stringify(data, null, 2));
if (data.OK && data.TaskID) {
currentTaskId = data.TaskID;
openChatUI();
}
} catch (err) {
showResult('Error: ' + err.message);
}
}
async function checkActiveChat() {
const businessId = parseInt(document.getElementById('businessId').value) || 0;
const servicePointId = parseInt(document.getElementById('servicePointId').value) || 0;
if (!businessId) {
showResult('Error: BusinessID is required');
return;
}
try {
const response = await fetch('/api/chat/getActiveChat.cfm', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
BusinessID: businessId,
ServicePointID: servicePointId
})
});
const data = await response.json();
showResult(JSON.stringify(data, null, 2));
if (data.OK && data.HAS_ACTIVE_CHAT && data.TASK_ID) {
currentTaskId = data.TASK_ID;
openChatUI();
}
} catch (err) {
showResult('Error: ' + err.message);
}
}
function openChatUI() {
document.getElementById('chatContainer').classList.add('visible');
lastMessageId = 0;
loadMessages();
pollInterval = setInterval(loadMessages, 2000);
}
function closeChat() {
document.getElementById('chatContainer').classList.remove('visible');
if (pollInterval) {
clearInterval(pollInterval);
pollInterval = null;
}
currentTaskId = null;
}
async function loadMessages() {
if (!currentTaskId) return;
try {
const response = await fetch('/api/chat/getMessages.cfm', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
TaskID: currentTaskId,
AfterMessageID: lastMessageId
})
});
const data = await response.json();
if (data.OK) {
const messages = data.MESSAGES || [];
const container = document.getElementById('chatMessages');
if (lastMessageId === 0) {
container.innerHTML = '';
}
messages.forEach(msg => {
const div = document.createElement('div');
const isCustomer = msg.SenderType === 'customer';
div.className = 'chat-message ' + (isCustomer ? 'customer' : 'staff');
div.textContent = msg.MessageBody;
container.appendChild(div);
lastMessageId = Math.max(lastMessageId, msg.MessageID);
});
container.scrollTop = container.scrollHeight;
if (data.CHAT_CLOSED) {
showResult('Chat has been closed by staff');
closeChat();
}
}
} catch (err) {
console.error('Load messages error:', err);
}
}
async function sendMessage() {
const input = document.getElementById('chatInput');
const message = input.value.trim();
if (!message || !currentTaskId) return;
input.value = '';
try {
const response = await fetch('/api/chat/sendMessage.cfm', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
TaskID: currentTaskId,
Message: message,
SenderType: 'customer'
})
});
const data = await response.json();
if (data.OK) {
// Add locally for immediate feedback
const container = document.getElementById('chatMessages');
const div = document.createElement('div');
div.className = 'chat-message customer';
div.textContent = message;
container.appendChild(div);
container.scrollTop = container.scrollHeight;
}
} catch (err) {
console.error('Send message error:', err);
}
}
function showResult(text) {
const el = document.getElementById('result');
el.textContent = text;
el.style.display = 'block';
}
</script>
</body>
</html>