• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

Serialize and Unserialize functions

Gesior.pl

Mega Noob&LOL 2012
Senator
Joined
Sep 18, 2007
Messages
2,966
Solutions
99
Reaction score
3,383
Location
Poland
GitHub
gesior
Like in PHP:
You can change number,string,boolean,nil and table variable to string.
You can change string from 'serialize' to variable again.
Function code:
Lua:
-- LUA function: exportstrin(s) , author: unknown, http://lua-users.org/wiki/SaveTableToFile
function exportstring( s )
	s = string.format( "%q",s )
	s = string.gsub( s,"\\\n","\\n" )
	s = string.gsub( s,"\r","\\r" )
	s = string.gsub( s,string.char(26),"\"..string.char(26)..\"" )
	return s
end

-- LUA function: serialize(var) , author: Gesior [ [email protected] ], based on http://lua-users.org/wiki/SaveTableToFile
function serialize(variable)
	local varType = type(variable)
	if(varType == "table") then
		local file = { write = function( self,newstr ) self.str = self.str..newstr end, str = "" }
		local tables,lookup = { variable },{ [variable] = 1 }
		file:write( "return {" )
		for idx,t in ipairs( tables ) do
			file:write( "{" )
			local thandled = {}
			for i,v in ipairs( t ) do
				thandled[i] = true
				if type( v ) ~= "userdata" then
					if type( v ) == "table" then
						if not lookup[v] then
							table.insert( tables, v )
							lookup[v] = #tables
						end
						file:write( "{"..lookup[v].."}," )
					elseif type( v ) == "function" then
						file:write( "loadstring("..exportstring(string.dump( v ))..")," )
					else
						local value =  ( type( v ) == "string" and exportstring( v ) ) or tostring( v )
						file:write(  value.."," )
					end
				end
			end
			for i,v in pairs( t ) do
				if (not thandled[i]) and type( v ) ~= "userdata" then
					if type( i ) == "table" then
						if not lookup[i] then
							table.insert( tables,i )
							lookup[i] = #tables
						end
						file:write( "[{"..lookup[i].."}]=" )
					else
						local index = ( type( i ) == "string" and "["..exportstring( i ).."]" ) or string.format( "[%d]",i )
						file:write( index.."=" )
					end
					if type( v ) == "table" then
						if not lookup[v] then
							table.insert( tables,v )
							lookup[v] = #tables
						end
						file:write( "{"..lookup[v].."}," )
					elseif type( v ) == "function" then
						file:write( "loadstring("..exportstring(string.dump( v ))..")," )
					else
						local value =  ( type( v ) == "string" and exportstring( v ) ) or tostring( v )
						file:write( value.."," )
					end
				end
			end
			file:write( "}," )
		end
		file:write( "}" )
		return "t" .. file.str
	elseif(varType == "string") then
		return "s" .. variable
	elseif(varType == "number") then
		return "n" .. variable
	elseif(varType == "boolean") then
		if(variable) then
			return "b1"
		else
			return "b0"
		end
	end
	return ""
end

-- LUA function: unserialize(serializedString) , author: Gesior [ [email protected] ], based on http://lua-users.org/wiki/SaveTableToFile
function unserialize( dataString )
	local dataType = string.sub(dataString,1,1)
	local dataValue = string.sub(dataString,2)
	if(dataType == "t") then
		tables,err = loadstring( dataValue )
		if err then return _,err end
		tables = tables()
		for idx = 1,#tables do
			local tolinkv,tolinki = {},{}
			for i,v in pairs( tables[idx] ) do
				if type( v ) == "table" and tables[v[1]] then
					table.insert( tolinkv,{ i,tables[v[1]] } )
				end
				if type( i ) == "table" and tables[i[1]] then
					table.insert( tolinki,{ i,tables[i[1]] } )
				end
			end
			for _,v in ipairs( tolinkv ) do
				tables[idx][v[1]] = v[2]
			end
			for _,v in ipairs( tolinki ) do
				tables[idx][v[2]],tables[idx][v[1]] =  tables[idx][v[1]],nil
			end
		end
		return tables[1]
	elseif(dataType == "s") then
		return dataValue
	elseif(dataType == "n") then
		return tonumber(dataValue)
	elseif(dataType == "b") then
		if(dataValue == 1) then
			return true
		elseif(dataValue == 0) then
			return false
		end
	end
	return nil
end


Example:
Lua:
tmptbl = {}
tmptbl["a"] = {}
table.insert(tmptbl["a"], {["someNumber"] = 54545.6, ["bolvalueexample"] = true})
table.insert(tmptbl, {["other"] = 1231, ["textvalue"] = "sdsdd\"ds@#$%^&*"})
-- save table in storage
doSetStorage(15, serialize(tmptbl))
-- you can view serialized string in client
doPlayerSendTextMessage(cid, MESSAGE_STATUS_CONSOLE_BLUE, getStorage(15))
-- you can get table in any other script
local oldTmptbl = unserialize(getStorage(15))

Example table serialized string:
treturn {{{2},["a"]={3},},{["other"]=1231,["textvalue"]="sdsdd\"ds@#$%^&*",},{{4},},{["bolvalueexample"]=true,["someNumber"]=54545.6,},}

You can also store serialized variable in file or MySQL 'text' field.
----------------------------------
I know that 99% users got no idea what to do with these functions, but maybe someone will need it to auctions/offline items script (save item special attributes). I will use it to load addons and storages in new sms shop.
 
Source: tfs/data/lib/tables.lua

Lua:
function table.serialize(x, recur)
	local t = type(x)
	recur = recur or {}

	if(t == nil) then
		return "nil"
	elseif(t == "string") then
		return string.format("%q", x)
	elseif(t == "number") then
		return tostring(x)
	elseif(t == "boolean") then
		return t and "true" or "false"
	elseif(getmetatable(x)) then
		error("Can not serialize a table that has a metatable associated with it.")
	elseif(t == "table") then
		if(table.find(recur, x)) then
			error("Can not serialize recursive tables.")
		end
		table.insert(recur, x)

		local s = "{"
		for k, v in pairs(x) do
			s = s .. "[" .. table.serialize(k, recur) .. "]" .. " = " .. table.serialize(v, recur) .. ", "
		end

		return s:sub(0, s:len() - 2) .. "}"
	end

	error("Can not serialize value of type '" .. t .. "'.")
end

function table.unserialize(str)
	return loadstring("return " .. str)()
end
 
OPdKV.png


Why would you check if variable doesn't equal something then check if it equals something else instead of just check if it equals something else :p.
 
@UP
I've copied table dump code from link that is in comment.

@offtop
Syntax posted tfs 0.4 code! BAN! :)
 
@UP
I've copied table dump code from link that is in comment.

@offtop
Syntax posted tfs 0.4 code! BAN! :)

Actually it's been in 0.3 for awhile. I ripped that code straight from Tfs 0.3.6p1 (latest public release)
:)
 
Epic functions. Thx Gesior! :)
 
Last edited:
Back
Top