Fixed small edge cases for datastore

This commit is contained in:
Cooldude2606
2020-05-27 20:45:39 +01:00
parent 27cb7c6c55
commit 3b58365bf5
2 changed files with 38 additions and 16 deletions

View File

@@ -224,7 +224,6 @@ function DatastoreManager.combine(datastoreName, subDatastoreName)
return datastore:combine(subDatastoreName) return datastore:combine(subDatastoreName)
end end
local function ingest_error(err) print('Datastore ingest error, Unable to parse json:', err) end
--[[-- Ingest the result from a request, this is used through a rcon interface to sync data --[[-- Ingest the result from a request, this is used through a rcon interface to sync data
@tparam string action The action that should be done, can be: remove, message, propagate, or request @tparam string action The action that should be done, can be: remove, message, propagate, or request
@tparam string datastoreName The name of the datastore that should have the action done to it @tparam string datastoreName The name of the datastore that should have the action done to it
@@ -244,15 +243,14 @@ function DatastoreManager.ingest(action, datastoreName, key, valueJson)
datastore:raw_set(key) datastore:raw_set(key)
elseif action == 'message' then elseif action == 'message' then
local success, value = xpcall(game.json_to_table, ingest_error, valueJson) local success, value = pcall(game.json_to_table, valueJson)
if not success then return end if not success or value == nil then value = tonumber(valueJson) or valueJson end
if value == nil then value = valueJson end
datastore:raise_event('on_message', key, value) datastore:raise_event('on_message', key, value)
elseif action == 'propagate' or action == 'request' then elseif action == 'propagate' or action == 'request' then
local success, value = xpcall(game.json_to_table, ingest_error, valueJson) local success, value = pcall(game.json_to_table, valueJson)
if not success then return end if not success or value == nil then value = tonumber(valueJson) or valueJson end
if value == nil then value = valueJson end datastore:raw_set(key) -- clear any existing data
value = datastore:raise_event('on_load', key, value) value = datastore:raise_event('on_load', key, value)
datastore:set(key, value) datastore:set(key, value)
@@ -437,6 +435,20 @@ function Datastore:set_serializer(callback)
self.serializer = callback self.serializer = callback
end end
--[[-- Set a default value to be returned by get if no other default is given, using will mean get will never return nil, set using the default will set to nil to save space
@tparam any default The value that will be deep copied by get if the value is nil and no other default is given
@tparam boolean allowSet When true if the default is passed as the value for set it will be set rather than setting nil
@usage-- Set a default value to be returned by get
local ExampleData = Datastore.connect('ExampleData')
ExampleData:set_default('Foo')
]]
function Datastore:set_default(value, allowSet)
self.default = value
self.allow_set_to_default = allowSet
end
--[[-- Set metadata tags on this datastore which can be accessed by other scripts --[[-- Set metadata tags on this datastore which can be accessed by other scripts
@tparam table tags A table of tags that you want to set in the metadata for this datastore @tparam table tags A table of tags that you want to set in the metadata for this datastore
@@ -456,7 +468,7 @@ function Datastore:set_metadata(tags)
end end
end end
--[[-- Get a value from local storage, option to have a default value --[[-- Get a value from local storage, option to have a default value, do not edit the data returned as changes may not save, use update if you want to make changes
@tparam any key The key that you want to get the value of, must be a string unless a serializer is set @tparam any key The key that you want to get the value of, must be a string unless a serializer is set
@tparam[opt] any default The default value that will be returned if no value is found in the datastore @tparam[opt] any default The default value that will be returned if no value is found in the datastore
@@ -469,7 +481,7 @@ function Datastore:get(key, default)
key = self:serialize(key) key = self:serialize(key)
local value = self:raw_get(key) local value = self:raw_get(key)
if value ~= nil then return value end if value ~= nil then return value end
return copy(default) return copy(default or self.default)
end end
--[[-- Set a value in local storage, will trigger on_update then on_save, save_to_disk and auto_save is required for on_save --[[-- Set a value in local storage, will trigger on_update then on_save, save_to_disk and auto_save is required for on_save
@@ -483,7 +495,11 @@ ExampleData:set('TestKey', 'Foo')
]] ]]
function Datastore:set(key, value) function Datastore:set(key, value)
key = self:serialize(key) key = self:serialize(key)
if value == self.default and not self.allow_set_to_default then
self:raw_set(key)
else
self:raw_set(key, value) self:raw_set(key, value)
end
self:raise_event('on_update', key, value) self:raise_event('on_update', key, value)
if self.auto_save then self:save(key) end if self.auto_save then self:save(key) end
return value return value
@@ -528,7 +544,7 @@ function Datastore:update(key, callback)
end end
end end
--[[-- Remove a value locally and on the external source, works regardless of propagateChanges --[[-- Remove a value locally and on the external source, works regardless of propagateChanges, requires save_to_disk for external changes
@tparam any key The key that you want to remove locally and externally, must be a string unless a serializer is set @tparam any key The key that you want to remove locally and externally, must be a string unless a serializer is set
@usage-- Remove a key locally and externally @usage-- Remove a key locally and externally
@@ -539,7 +555,8 @@ ExampleData:remove('TestKey')
function Datastore:remove(key) function Datastore:remove(key)
key = self:serialize(key) key = self:serialize(key)
self:raw_set(key) self:raw_set(key)
self:write_action('remove', key) self:raise_event('on_update', key)
if self.save_to_disk then self:write_action('remove', key) end
if self.parent and self.parent.auto_save then return self.parent:save(key) end if self.parent and self.parent.auto_save then return self.parent:save(key) end
end end
@@ -734,7 +751,8 @@ value = self:raise_event('on_save', key, value)
]] ]]
function Datastore:raise_event(event_name, key, value, source) function Datastore:raise_event(event_name, key, value, source)
-- Raise the event for the children of this datastore -- Raise the event for the children of this datastore
if source ~= 'child' then if source ~= 'child' and next(self.children) then
if type(value) ~= 'table' then value = self:raw_get(key, true) end
for value_name, child in pairs(self.children) do for value_name, child in pairs(self.children) do
value[value_name] = child:raise_event(event_name, key, value[value_name], 'parent') value[value_name] = child:raise_event(event_name, key, value[value_name], 'parent')
end end
@@ -753,6 +771,9 @@ function Datastore:raise_event(event_name, key, value, source)
if source ~= 'parent' and self.parent then if source ~= 'parent' and self.parent then
self.parent:raise_event(event_name, key, self.parent:raw_get(key), 'child') self.parent:raise_event(event_name, key, self.parent:raw_get(key), 'child')
end end
-- If this is the save event and the table is empty then return nil
if event_name == 'on_save' and next(self.children) and not next(value) then return end
return value return value
end end

View File

@@ -54,6 +54,7 @@ PlayerData:set_serializer(Datastore.name_serializer) -- use player name
local DataSavingPreference = PlayerData:combine('DataSavingPreference') local DataSavingPreference = PlayerData:combine('DataSavingPreference')
local PreferenceEnum = { 'All', 'Statistics', 'Settings', 'Required' } local PreferenceEnum = { 'All', 'Statistics', 'Settings', 'Required' }
for k,v in ipairs(PreferenceEnum) do PreferenceEnum[v] = k end for k,v in ipairs(PreferenceEnum) do PreferenceEnum[v] = k end
DataSavingPreference:set_default('All')
--- Sets your data saving preference --- Sets your data saving preference
-- @command set-data-preference -- @command set-data-preference
@@ -68,12 +69,12 @@ end)
-- @command data-preference -- @command data-preference
Commands.new_command('data-preference', 'Shows you what your current data saving preference is') Commands.new_command('data-preference', 'Shows you what your current data saving preference is')
:register(function(player) :register(function(player)
return {'expcore-data.get-preference', DataSavingPreference:get(player, 'All')} return {'expcore-data.get-preference', DataSavingPreference:get(player)}
end) end)
--- Remove data that the player doesnt want to have stored --- Remove data that the player doesnt want to have stored
PlayerData:on_save(function(player_name, player_data) PlayerData:on_save(function(player_name, player_data)
local dataPreference = DataSavingPreference:get(player_name, 'All') local dataPreference = DataSavingPreference:get(player_name)
dataPreference = PreferenceEnum[dataPreference] dataPreference = PreferenceEnum[dataPreference]
if dataPreference == PreferenceEnum.All then return player_data end if dataPreference == PreferenceEnum.All then return player_data end
@@ -86,7 +87,7 @@ end)
--- Display your data preference when your data loads --- Display your data preference when your data loads
DataSavingPreference:on_load(function(player_name, dataPreference) DataSavingPreference:on_load(function(player_name, dataPreference)
game.players[player_name].print{'expcore-data.get-preference', dataPreference or 'All'} game.players[player_name].print{'expcore-data.get-preference', dataPreference or DataSavingPreference.default}
end) end)
--- Load player data when they join --- Load player data when they join