HttpService MySQL - Data is nil

Hello. I made a MySQL Database to store my in-game bans since I want to update the ban list in real-time. I made the REST API and the Database. The problem is that the data is always nil.

Here is the Script:

local HttpService = game:GetService("HttpService")

game.Players.PlayerAdded:Connect(function(player)
	local URL = "[REMOVED]/user/"..player.Name
	-- I made this Chatted function only to see if the data changes.
	player.Chatted:Connect(function()
		local ReceivedData = HttpService:GetAsync(URL)
		local Data = HttpService:JSONDecode(ReceivedData)
		
		if Data.username == player.Name then
			print("Yes. The reason is: "..Data.reason)
		else
			print("False!!!")
		end
	end)
end)

If the user is banned I will receive this JSON Code:
[{"username":"JakyeRU","reason":"Reason for ban."}] else [].

1 Like

We have no way of magically reading the code for your backend, nor seeing your DB schema, so… you’re kinda on your own with the info you’ve provided.
Try printing ReceivedData - maybe it’s not returning valid JSON (a mysql error perhaps)? Otherwise, we’re gunna need your backend. Feel free to PM it to me if you don’t want to post it publicly, I’d be glad to help.

The back-end code and the Database works perfectly. That’s the JSON that I receive:
[{"username":"JakyeRU","reason":"Reason for ban."}]

That’s the back-end code if you need it.

const express = require('express');
const app = express();
const morgan = require('morgan');
const mysql = require('mysql');

app.use(express.static('public'));
app.get('/', function(request, response) {
  response.sendFile(__dirname + '/views/index.html');
});

const listener = app.listen(process.env.PORT, function() {
  console.log('Listening on port ' + listener.address().port);
});

app.use(morgan('combined'))

app.get("/user/:username", (request, response) => {
    const connection = mysql.createConnection({
        host: 'something',
        user: 'something',
        password: 'something',
        database: 'something'
    })

    const queryString = "SELECT * FROM users WHERE username = ?"
    connection.query(queryString, [request.params.username], (error, rows, fields) =>{
        if (error) {
            console.log("Failed to query for user! " + error)
            response.send(error)
            response.sendStatus(500)
            response.end()
            return
        }

        response.json(rows)
    })
})


I know, I have no protection.

Can you post the output of printing ReceivedData, and the response if you attempt to make a request to the API from your web browser?



image

The way your JSON is currently formatted is the equivalent to doing this in Lua:

local Data = {
    {
        ["username"] = "JakyeRU",
        ["reason"] = "Reason for ban."
    }
}

In order to actually access the username, you’d need to do

Data[1].username

or

Data[1]["username"]

This is because the mysql module for node you’re using supports multiple rows being returned (as it should). You can fix this by adding LIMIT 1 to the end of your query, and then only responding with the first row result:

const express = require('express');
const app = express();
const morgan = require('morgan');
const mysql = require('mysql');

const connection = mysql.createConnection({ // It is best practice to connect to the db BEFORE you start serving requests - connecting every single time a request is made is VERY resource intensive and not reccomended 
	host: 'something',
	user: 'something',
	password: 'something',
	database: 'something'
})

app.use(express.static('public'));
app.get('/', function(request, response) {
  response.sendFile(__dirname + '/views/index.html');
});

const listener = app.listen(process.env.PORT, function() {
  console.log('Listening on port ' + listener.address().port);
});

app.use(morgan('combined'))

app.get("/user/:username", (request, response) => {
    const queryString = "SELECT * FROM users WHERE username = ? LIMIT 1"
    connection.query(queryString, [request.params.username], (error, rows, fields) =>{
        if (error || !rows[0]) {
            console.log("Failed to query for user! " + error)
            response.send(error)
            response.end(500) // PRO TIP: you can simply .end(STATUS) instead of doing .sendStatus too
            return
        }

        response.json(rows[0])
    })
})
3 Likes