AI NPC Responses Show in Console But Missing from Game Interface

I’m developing a FiveM mod that uses QBCore to create smart NPC conversations. Players should walk up to NPCs, hit E to start chatting, and see both their messages and the NPC replies in a chat window.

The problem is weird - the AI generates responses perfectly and I can see them in the console logs, but they never show up in the actual game UI. Player messages display fine in the chat interface, but NPC responses are completely invisible.

My setup includes three main parts:

-- manifest.lua
fx_version 'cerulean'
game 'gta5'

author 'DevUser'
description 'Smart NPC Chat System'
version '1.0.0'

shared_script 'settings.lua'

client_scripts {
    'client/main.lua'
}

server_scripts {
    'server/handlers.lua'
}

files {
    'interface/chat.html',
    'interface/styles.css',
    'interface/app.js'
}

ui_page 'interface/chat.html'
-- settings.lua
Settings = {}
Settings.APIToken = "your-token-here"
Settings.AIEndpoint = "https://api-inference.huggingface.co/models/microsoft/DialoGPT-medium"
-- server/handlers.lua
local jsonLib = require('json')

RegisterNetEvent('SmartNPC:GetAIReply')
AddEventHandler('SmartNPC:GetAIReply', function(userInput)
    print("Server got message: " .. userInput)
    local token = Settings.APIToken
    local url = Settings.AIEndpoint

    PerformHttpRequest(url, function(statusCode, responseBody, responseHeaders)
        if statusCode == 200 then
            print("AI API returned: " .. tostring(responseBody))
            local data = jsonLib.decode(responseBody)
            local aiReply = data and data[1] and data[1].generated_text or "I don't understand that."
            print("Sending AI reply: " .. aiReply)
            TriggerClientEvent('SmartNPC:HandleAIReply', source, aiReply)
        else
            print("API error: " .. tostring(statusCode))
            TriggerClientEvent('SmartNPC:HandleAIReply', source, "Something went wrong, sorry.")
        end
    end, 'POST', jsonLib.encode({
        inputs = userInput
    }), {
        ["Authorization"] = "Bearer " .. token,
        ["Content-Type"] = "application/json"
    })
end)

I’ve tried debugging everything but can’t figure out why the UI won’t display NPC responses even though they’re being generated correctly. Anyone know what might be causing this?

Check your NUI message routing - had this exact bug last month. Your server’s firing the event but the UI might not be processing SendNUIMessage right.

Add some debug logging in your interface/app.js to see if messages are reaching the frontend:

window.addEventListener('message', function(event) {
    console.log('NUI received:', event.data);
    // your existing handler code
});

No logs? Problem’s in your client-side SendNUIMessage call. See the logs but messages aren’t showing? Check your CSS - chat containers sometimes have overflow:hidden or z-index issues that hide new messages.

Also make sure your ui_page path is correct and the HTML file’s actually loading. FiveM gets picky about file paths in the manifest.

Spotted the issue - you’re missing the client-side handler that shows AI responses in your UI.

Your server fires SmartNPC:HandleAIReply correctly, but there’s no client event handler to catch it and display it in chat.

Add this to your client/main.lua:

RegisterNetEvent('SmartNPC:HandleAIReply')
AddEventHandler('SmartNPC:HandleAIReply', function(aiReply)
    print("Client received AI reply: " .. aiReply)
    -- Send to your UI
    SendNUIMessage({
        type = "addMessage",
        sender = "NPC",
        message = aiReply
    })
end)

Then in your interface/app.js, handle this message type:

window.addEventListener('message', function(event) {
    if (event.data.type === 'addMessage') {
        // Add message to your chat interface
        displayMessage(event.data.sender, event.data.message);
    }
});

I hit this same problem building something similar - server was doing everything right but forgot the client actually needs to display the results.

sounds like a scope issue with your client events. register the HandleAIReply event before any npc interactions start. ive seen this before - events fire too early and get lost. move your RegisterNetEvent calls to the top of client/main.lua or wrap them in Citizen.CreateThread so they initialize properly.

Looking at your manifest and code, you might have a timing issue - I hit this same problem before. The NUI isn’t always fully loaded when those first messages come through, even with proper client handlers.

Add a small delay before sending NUI messages, or better - use a ready check system. In chat.html, send a message when everything’s loaded:

window.addEventListener('DOMContentLoaded', function() {
    fetch('https://smartnpc/uiReady', { method: 'POST' });
});

Queue incoming AI responses on the client until you get that ready signal. My responses were vanishing because the UI wasn’t ready when the server fired back quickly.

Also check your QBCore chat integration - some versions need messages routed specific ways between chat system and custom UIs.