aboutsummaryrefslogtreecommitdiff
path: root/gamemode/core/database/sv_setup.lua
blob: a99cef4c7310b04e1d5e66a651e62cb001a38071 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
---Functions for working the the mysqlite module.
-- Helps load players into their correct instance
--@server sv_setup.lua
--@alias sql

--Adds the MySQLite global
nrequire("sv_mysqlite.lua")
local config = nrequire("config/sv_sql.lua")
local data = nrequire("config/sv_newplayer.lua")
local col = nrequire("config/colortheme.lua")
local q = nrequire("core/database/sv_queries.lua")
local sql = {}

--Setup the database if it's not already
local setup_db = [[
CREATE TABLE IF NOT EXISTS playerdata(SteamID bigint primary key, PlayerData TEXT, MetaData TEXT)]]

--Create a new player
local create_player_query = [[
INSERT INTO playerdata (`SteamID`,`PlayerData`,`MetaData`) VALUES(%.0f,'%s','%s')]]

--Get a player's data from the database
local fetch_player_query = [[
SELECT PlayerData, MetaData FROM playerdata WHERE SteamID=%.0f
]]

local save_player_query = [[
UPDATE playerdata SET MetaData='%s' PlayerData='%s' WHERE SteamID=%.0f
]]

local function q_fai(err,query)
	MsgC(col.console.red,string.format("Error executing %s, error:%s",query,err))
end



local function connect()
	--print("Connecting to the database...")
	MySQLite.initialize(config)
end
hook.Add("DatabaseInitialized","setup_table",function()
	assert(MySQLite.isMySQL(),"Database wasn't mysqloo, something is probably wrong!")
	local setup_success = function(res,li)
		--print("Set up connection to db")
	end
	--print("Setup query:",setup_db)
	MySQLite.query(setup_db,setup_success,q_fai)
end)

hook.Add("Initialize","initalizedbconnection",function()
	connect()
end)

---Gets a player's data from the database.
-- Finds a player's data, returns nil if not found. Players are found off their steamid
--@tparam player ply The player to look for's data
--@treturn table|nil {PlayerData, MetaData}
function sql.GetPlayerData(ply)
	local s64 = ply:SteamID64()
	local q_str = q.s_fmt(fetch_player_query,s64)
	local q_suc = function(res,li)
		if res == nil then
			sql.CreatePlayerTable(ply)
		else
			assert(#res == 1,"Not unique!")
			local meta = res[1].MetaData
			local plyd = res[1].PlayerData
			local mtbl = util.JSONToTable(meta)
			if mtbl.lastserver ~= game.GetIPAddress() then
				--ply:ConCommand("connect " .. mtbl.lastserver)
				-- net.Start("art_sendtoserver")
				-- net.WriteString(mtbl.lastserver)
				-- net.Send(ply)
				return nil
			end
			local _,_,x,y,z = string.find(mtbl.lastlocation,"([-%d%.]+) ([-%d%.]+) ([-%d%.]+)")
			local vec = {x,y,z}
			for k,v in pairs(vec) do vec[k] = tonumber(v) end
			ply:SetPos(Vector(unpack(vec)))
			q.deserialize_player(ply,plyd)
		end
	end
	--print("doing query",q_str)
	MySQLite.query(q_str,q_suc,q_fai)
end

---Manually loads data for the caller.
-- Forefully loads a player's data. ![Requires admin](./req_admin)
--@concommand artery_loadplayer
concommand.Add("artery_loadplayer",function(ply,cmd,args)
	if not ply:IsAdmin() then return end
	sql.GetPlayerData(ply)
end)

---Creates a new row for the player in the database.
-- Creates a new row for a player, works off the configuration in sv_newplayer.lua
--@see sv_newplayer.lua
--@tparam player ply The player to create the new row for
function sql.CreatePlayerTable(ply)
	--print("Createing player table....")
	local s64 = ply:SteamID64()
	--print("steamid was", s64)
	local plytbl = data.newdata()
	local plymet = data.newmeta()
	local plydata =util.TableToJSON(plytbl)
	local metdata = util.TableToJSON(plymet)
	local q_str = q.s_fmt(create_player_query,s64,plydata,metdata)
	local q_suc = function(res,li)
		--print("Inserted new player",ply)
		sql.GetPlayerData(ply)
	end
	--print("doing query", q_str)
	MySQLite.query(q_str,q_suc,q_fai)
end

---Sends a player to another server.
-- Usually when a player disconnects, their location & server are saved, this overrides that and sends them to another instance when they reconnect.
--@tparam player ply The player to send to a different instace
--@tparam string ls The server to send the player to
--@tparam vector3 ll The location to send the player to on that server
function sql.SendPlayerToInstance(ply,ls,ll)
	local s64 = ply:SteamID64()
	local plydata = q.serialize_player(ply)
	local plymeta = util.TableToJSON({
		lastserver = ls,
		lastlocation = ll
	})
	local q_str = q.s_fmt(save_player_query,plymeta,plydata,s64)
	local q_suc = function(res,li)
		--print("Successfully saved player data")
	end
	MySQLite.query(q_str,q_suc,q_fai)
end

---Do queries related to the player creation.
-- Create the caller's data, Reload the coller's data, or Send the caller to another instance ![Requires admin](./req_admin)
--@usage artery_DoQuery (create|get|send <server> <location>)
--@concommand artery_DoQuery
concommand.Add("artery_DoQuery",function(ply,cmd,args)
	if not ply:IsAdmin() then return end
	if args[1] == "create" then
		sql.CreatePlayerTable(ply)
	elseif args[1] == "get" then
		sql.GetPlayerData(ply)
	elseif args[1] == "send" then
		sql.SendPlayerToInstance(ply,args[2],args[3])
	else
		error("Command not understood:" .. args[1] .. "!")
	end
end)

--print("In sv_setup.lua, sql before returning is", sql)

return sql