Dumb DOM API questions

What’s the best way to free a handle in a chain of promises? I find myself having to “nest” my calls instead of chaining them because if I simply chain them I lose the reference of the handle used previously so I can’t free it once the chain is done.

Or a simple example of the problem:

window.safeMutableDataEntries.forEach(entriesHandle, (k, v) => {

    let key = String.fromCharCode.apply(null, k);
    let value = String.fromCharCode.apply(null, new Uint8Array(v.buf));

    console.log(key + ': ' + value);
  }).then(_ => {
    // You can't free entriesHandle here since it is not in scope
    return 'Iteration complete' + _;
  });
}

What I end up doing is create a variable outside of the promise, assign the handle to it and then free it using the outside variable like:

var handle_to_erase;
window.safeMutableDataEntries.forEach(entriesHandle, (k, v) => {
handle_to_erase = entriesHandle;
let key = String.fromCharCode.apply(null, k);
let value = String.fromCharCode.apply(null, new Uint8Array(v.buf));

    console.log(key + ': ' + value);
  }).then(_ => {
    window.safeMutableDataEntries.free(handle_to_erase);
    return 'Iteration complete' + _;
  });
}

So what’s the best way to handle handles? :slight_smile:

2 Likes

Another question:

When I remove an entry, it simply erases its value, the key of the entry is still present in the MD, is that a bug or am I missing a step?

1 Like

My solution was this:

function sendMessage() {
  window.safeMutableData.newMutation(auth)
    .then((mutationHandle) => {
      var date = new Date();
      var time = date.getTime();
      window.safeMutableDataMutation.insert(mutationHandle, time.toString(), textarea.value)
        .then(_ =>
          window.safeMutableData.applyEntriesMutation(mdHandle, mutationHandle))
        .then(_ => {
          Materialize.toast('Message has been sent to the network', 3000, 'rounded');
          window.safeMutableDataMutation.free(mutationHandle);
          getMutableDataHandle("getMessages");
        });
      textarea.value = "";

    });
}

example taken from Chaty. As far as I know nesting is the best way, but it should be possible to pass the handle as either a variable for chaining or a paramenter when doing a callback.

As far as I know you aren’t suppose to be able to remove the key from a Mutable Data Entry, Demoy’s Main.js video goes a bit into removing Mutable Data here and a few other functions of Mutable Data as well.

1 Like

Yeah I’m doing something similar, I just don’t like nesting just for the sake of freeing my handles. I’ll look at passing handle as variable for chaining. Do you have any example code?

Can you confirm @bochaco?

Thanks for your help @Joseph_Meagher, I’m slowly getting up to speed.

1 Like

Afraid not, but make sure to use local variables as global variables aren’t the best practice.

10 posts were split to a new topic: JavaScript tips for using the SAFE API

  • window.safeApp.free(appHandle)
    Does this also free other handles (ie mutable data, NFS, file etc) or do they have to be explicitly free’d?

  • safeNfs.open()
    …returns a new file handle. If it was given an existing file handle, does that get freed by this operation or does it remain valid?

1 Like

That’s correct, the entry’s value is cleared but the entry is not removed.

It does free them all, this is done by the safe_client_libs itself rather than the safe_app_nodejs layer though.

It remains valid, but it sounds to me we can enhance this by returning the same handle if one was provided instead of returning a new one (just created this for consideration MAID-2365).

3 Likes

If it’s not a temporary behaviour, I would suggest to change the name of the function to clear instead of remove to avoid confusion.

Btw, is this a technical limitation or a design choice?

2 Likes

I think this was to prevent people from being able to change content and claim it was never changed. Let’s say you have an entry with version N which other people take as valid, perhaps some contractual information, you could then remove it and create an new entry with the same key and same version N but new content, i.e. you remove the entry, then insert a new one with the same key, and update it until you reached the same version N but with a new value. So by clearing it, you can at least realise that the value for version N is not valid anymore.
This a whole topic in itself, my understanding is that there are also plans/proposals for having the network to keep the entire history of an entry or data.

4 Likes

Thanks Gabriel, that makes sense, but it has some unfortunate consequences.

For example, in using an MD for storing and regularly invalidating keys such as using an MD as a file index as in SAFE-NFS. Every time a filename is changed, an unused key is left which takes up space in the MD, and which has to be filtered whenever searching the index (such as to list a directory).

So I’m wondering if there are plans to mitigate this kind of issue?

Similarly, over time a container will become cluttered with discarded keys.

1 Like

This proposal transform the mutable data in a new kind of immutable data. That’s change one basic purpose of MD and loose privacy.
Hope could delete, at least, previous versions.

I see. But now we have a list of item that can only grow overtime. It’s not very practical as a list. For example, the MD for NFS will be filled with empty field pretty fast.
Sounds like the problem of data disappearing needs to be fixed elsewhere, if at all. Maybe apps that needs it should figure out a protocol using immutable data for this kind of problem. Idk.

Its just that the impact on the list of entries is too big IMHO.

I think the solution is two kinds of MD:

  • one which exhibits current behaviour, and is useful where keys rarely or are never needing to be removed
  • or where keys can be deleted

In the mean time it is possible to simulate the latter if you need it, at the cost of not being able to use the built-in NFS API ‘simulate as’ functionality.

You could do this by storing your index in a single MD key, but since the cost of updating this would likely be the same as the equivalent size immutable data, it might be more sensible to use ID for an index rather than MD. You would then have the option of also storing references to your ID as a history, giving rollback/archive functionality too.

I can see good reasons for building your own layer rather than using the built in features (such as emulate as NFS). For ‘serious’ applications, you could optimise the storage to minimise PUT costs by moving infrequently used data together, and frequently changed data together for example.

So we can do what we need with the existing MD & ID, which means we don’t have a good case for changing the API for this at least.

1 Like

That sound backward, use an immutable data when you need to remove items for a list and mutable data when you want a immutable list… It’s not an elegant intuitive solution and it makes the NFS api unusable in the long term as a file system, that should hint that something is off in the design.

If we need an immutable list of item, create a key value list within a ID where the value points to an MD that can be modified.

So I don’t see why it should be the default behavior of MD when it’s doable with an ID in the rare case that you’ll need it.

My 2c anyway, I understand I might be missing something.

Edit: wait, can’t we create a MD without the delete permission for undeletable list?

3 Likes

Just to be sure there is no misunderstanding: The use case for clearing entries instead of deleting them, is not for immutable data, but is for mutable data for which we want to know if it is has been modified. Hard delete implementation doesn’t allow this because an entry could be recreated with the same version as before but a different content.

I’m with you. Could we achieve the same result with a MD that has no owner and no delete permission? Or, not really sure if it’s possible but, a MD set in a way that the owner can update, insert but not delete?

3 Likes

You can also add: without update permissions permission. But yes, it should work. I think you have found the solution to allow both usage:

  • no possibility to delete an entry when there is a need to prove non alteration (but an entry can still be cleared with an update operation)

  • efficient hard delete otherwise.

4 Likes

Cool, glad I could help :slight_smile:

Edit: actually, @bochaco what do you think?

2 Likes

This would seem to work for MDs created for arbitrary purposes, but am I right in thinking it won’t help applications which want to use the standard containers (to store files for example)? Unless those are made to allow delete, which in not sure would be acceptable.