DeleteKey problems

Discussion and help for Easy Save 3
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

DeleteKey problems

Post by zephiron »

Hi,

i'm trying to delete some keys from a save file, but no matter what I do, the keys remain in the file on disk. I'm using caching, so maybe there is some problem with my approach. Can someone help? Here is the code I use:

Code: Select all

string file = "mysave.dat";

ES3Settings settings = new ES3Settings(file, ES3.Location.Cache, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

// load to cache
ES3.CacheFile(settings);

// delete the keys in cache
foreach (string key in ES3.GetKeys(settings))
{
       if (key.StartsWith(prefix))
       {
             ES3.DeleteKey(key, settings);
             Debug.LogFormat("Deleting key: {0}", key);
       }
}

// write to file
ES3.StoreCachedFile(settings);
The debug log contains several "Deleting key... " lines, but the file on disk remains the same.
User avatar
Joel
Moodkie Staff
Posts: 4849
Joined: Wed Nov 07, 2012 10:32 pm

Re: DeleteKey problems

Post by Joel »

Hi there,

If you use ES3.DeleteKey when caching is enabled, it will delete the file from the cache. You need to set the save location to File if you want to delete the data from persistent storage.

All the best,
Joel
Joel @ Moodkie Interactive
Purchase Easy Save | Contact | Guides | Docs | Getting started
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

Re: DeleteKey problems

Post by zephiron »

Well that's what I assumed the code will do: loads the file into cache, deletes a bunch of keys from the cache and then saves the cache back to the file. I wanted to avoid overwriting the file on every key delete.

So maybe I'm completely misunderstanding how it works? Anyway, changing the ES3Settings object to contain "ES3.Location.File" instead "ES3.Location.Cache" had no effect :(
User avatar
Joel
Moodkie Staff
Posts: 4849
Joined: Wed Nov 07, 2012 10:32 pm

Re: DeleteKey problems

Post by Joel »

Hi there,

Please could you create a new project with a basic scene which replicates your issue and private message it to me?

All the best,
Joel
Joel @ Moodkie Interactive
Purchase Easy Save | Contact | Guides | Docs | Getting started
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

Re: DeleteKey problems

Post by zephiron »

Not sure how to send a scene but what I made is very simple, just a short script on an empty gameobject in a new default scene.

The script puts 3 buttons on the screen:
- one to Save two integer keys ('first' = 1, 'second' = 2) into a cached file
- one to Load the two integer keys (if missing, first will have value of 100, second of 200)
- one to delete the 'first' key

The script:

Code: Select all

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TestES3 : MonoBehaviour
{
    private readonly string file = "testes3.dat";

    private void OnGUI()
    {
        if (GUI.Button(new Rect(64, 64, 256, 64), "Save"))
        {
            ES3Settings settings = new ES3Settings(file, ES3.Location.Cache, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

            int first = 1;
            int second = 2;

            ES3.Save("first", first, settings);
            ES3.Save("second", second, settings);

            ES3.StoreCachedFile(settings);

            Debug.LogFormat("Saved - First: {0}, Second: {1} to {2}", first, second, file);
        }

        if (GUI.Button(new Rect(64, 160, 256, 64), "Load"))
        {
            ES3Settings settings = new ES3Settings(file, ES3.Location.Cache, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

            ES3.CacheFile(settings);

            int first = ES3.Load("first", 100, settings);
            int second = ES3.Load("second", 200, settings);

            Debug.LogFormat("Loaded - First: {0}, Second: {1} from {2}", first, second, file);
        }

        if (GUI.Button(new Rect(64, 256, 256, 64), "Delete 'first'"))
        {
            ES3Settings settings = new ES3Settings(file, ES3.Location.Cache, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

            ES3.CacheFile(settings);

            ES3.DeleteKey("first", settings);

            ES3.StoreCachedFile(settings);

            Debug.LogFormat("Deleted 'first' from: {0}", file);
        }
    }
}
So saving and loadnig works just fine. I can store the values and load them back correctly even after restarting the scene. I can delete the file and try loading it which gives me the new default values (100, 200). I can also manually edit the file and delete 'first' key and on load it correctly loads 'first' as 100 (meaning not found in file) and 'second' as 2 (found in file).

BUT pressing the delete button does not do anything to the file on disk... it stays the same no matter what.
User avatar
Joel
Moodkie Staff
Posts: 4849
Joined: Wed Nov 07, 2012 10:32 pm

Re: DeleteKey problems

Post by Joel »

Hi there,

Your script still appears to be using ES3Settings objects with ES3.Location.Cache as the storage location.

All the best,
Joel
Joel @ Moodkie Interactive
Purchase Easy Save | Contact | Guides | Docs | Getting started
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

Re: DeleteKey problems

Post by zephiron »

Yeah I know, but as stated above, changing to ES3.Location.File makes no difference.

If I use this:

Code: Select all

if (GUI.Button(new Rect(64, 256, 256, 64), "Delete 'first'"))
        {
            ES3Settings settings = new ES3Settings(file, ES3.Location.File, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

            ES3.CacheFile(settings);

            ES3.DeleteKey("first", settings);

            ES3.StoreCachedFile(settings);
            Debug.LogFormat("Deleted 'first' from: {0}", file);
        }
It still behaves the same.
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

Re: DeleteKey problems

Post by zephiron »

I have a feeling there must be a simple way how to make this work, but so far nothing i tried has done the trick.

Could you perhaps be so kind and post a small example that works? With caching, as i will be deleting thousands of keys at a time.

Thanks!
zephiron
Posts: 8
Joined: Mon Feb 01, 2021 8:48 pm

Re: DeleteKey problems

Post by zephiron »

Update:

So this works, but as far as I can tell it does not use caching so deleting thousands of keys would result in thousands of writes right?

Code: Select all

if (GUI.Button(new Rect(64, 256, 256, 64), "Delete 'first'"))
        {
            ES3Settings settings = new ES3Settings(file, ES3.Location.File, ES3.Directory.PersistentDataPath, ES3.CompressionType.None, ES3.ReferenceMode.ByRef);

            ES3.DeleteKey("first", settings);

            Debug.LogFormat("Deleted 'first' from: {0}", file);
        }
User avatar
Joel
Moodkie Staff
Posts: 4849
Joined: Wed Nov 07, 2012 10:32 pm

Re: DeleteKey problems

Post by Joel »

In your example you're deleting the key from the file in storage, but then you're calling StoreCachedFile, which will overwrite the file in storage with the file in cache.

Here's an example where you don't need to use ES3.Location.File at all.

Code: Select all

using UnityEngine;

public class DeleteCachedKey : MonoBehaviour
{
    void Start()
    {
        var settingsCache = new ES3Settings(ES3.Location.Cache);

        // Save three keys to the cache.
        ES3.Save("Key", 1, settingsCache);
        ES3.Save("KeyToBeDeleted", 2, settingsCache);
        ES3.Save("Key2", 3, settingsCache);

        // Store the file to persistent storage.
        ES3.StoreCachedFile();

        // Check that the key exists in permanent storage.
        Debug.Log("Key exists: " + ES3.KeyExists("KeyToBeDeleted", new ES3Settings(ES3.Location.File)));

        // Delete the key from the cached file.
        ES3.DeleteKey("KeyToBeDeleted", settingsCache);

        // Store the cached file to storage, thus deleting the key.
        ES3.StoreCachedFile();

        // Check that the key doesn't exist in the file in storage.
        Debug.Log("Key exists: " + ES3.KeyExists("KeyToBeDeleted", new ES3Settings(ES3.Location.File)));
    }
}
All the best,
Joel
Joel @ Moodkie Interactive
Purchase Easy Save | Contact | Guides | Docs | Getting started
Post Reply