View Full Version : player:SaveToDB() too slow?

10-07-2014, 02:04 AM
local function horadric (event, player, item, target)
if (item:GetEntry()==25647) then
local guid = player:GetGUIDLow()
local KilledDB = CharDBQuery("SELECT item_template,item FROM character_inventory WHERE guid = ("..guid..") AND slot = 0 AND bag = 24873 GROUP BY item_template ORDER BY item_template DESC") --CharDB Query
if (KilledDB~=nil) then
local itemtemplate = KilledDB:GetString(0)
local itemid = KilledDB:GetUInt32(1)
local raritydb = WorldDBQuery("SELECT Quality FROM item_template WHERE entry = "..itemtemplate.." GROUP BY Quality ORDER BY Quality DESC")
local rarity = raritydb:GetString(0)
local rolldb = WorldDBQuery("SELECT item FROM horadric_cube WHERE rarity = "..rarity.." ORDER BY RAND() LIMIT 1")
local roll = rolldb:GetUInt32(0)
local lastitemindb = 817999
local itemlink = GetItemLink(itemtemplate)
if (tonumber(itemtemplate)<=lastitemindb) and (tonumber(itemtemplate)~=6948) and (tonumber(itemtemplate)~=25994) then
player:RemoveItem(itemtemplate, 1)
player:AddItem(roll, 1)
player:SendBroadcastMessage(""..player:GetName().."'s item: "..itemlink.." is soulbound and will not be dropped!") --If itemID >818000, then the item won't drop and player gets this message
until not KilledDB:NextRow()
player:SendBroadcastMessage("NotHawthorne sucks at scripting. Try that one again.")

RegisterItemEvent(25647, 2, horadric)

The issue with this script is that player:SaveToDB() doesn't finish by the time the script checks the players inventory. Is there any way around this?

10-07-2014, 02:25 AM
You know it saves the players in the database automatically 10 minutes by default. I think it is 10 minutes. Anyway, my point is that it is pretty pointless to save the player to the database when it will do it regardless. What you're doing is just causing potential problems when you have a ton of people using that item and it constantly saving over and over again. I'd suggest removing the "player:SaveToDB()" and let it save like it should without forcing it to save. Honestly, I don't get what's new that points towards you forcing it to save. Is it the item that the player can receive or? Regardless, I stick with my last statement.

10-07-2014, 12:09 PM
You should never do queries this way, overhead is massive with larger player bases and bigger queries. Make a cache system lua side, write relevant information to the said cache, then run an sql schedule with a timed event to update the database instead with newcached information

10-07-2014, 05:12 PM
No, there is no way forcing the SaveToDB to be faster, other than changing it in core.
However there are workarounds for the problem..
As Foe said, you should write the cache to lua if you need one. Or then use the existing functions to go around the problem.
You dont store data in C++ to DB either .. or shouldnt. Same rules apply there as well and you would be facing the same problem basically.

I tried inspecting your code and the SQL query doesnt make sense to me.
You are querying the DB for the player's items that are inside a specific bag and you have hardcoded the bag's guid, so this will only work for one player.
What column is item_template? Is it custom? It doesnt exist.

As a plan for the script it seems that you should change the SQL queries (all of them) to be done with other functions.
horadric_cube should be a lua table loaded on startup for example.
It seems that you do not take into consideration bags being full. Do note that the item removed can be in inventory or bags or bank etc.

Could you try explain the logic behind the script overall?