Re: Spec for CryptoKey.algorithm and CryptoKey.usages doesn't really make sense

On Mon, Jul 14, 2014 at 1:03 PM, Domenic Denicola <
domenic@domenicdenicola.com> wrote:

> From: Boris Zbarsky <bzbarsky@MIT.EDU>
>
> >> Can you point to any explanation as to the "why"? I don't say so glibly,
> >> it's just that multiple people from different organizations have clearly
> >> different views on the "right" way to do things, and whether or not
> >> something is really "desired".
> >
> > I'm going to pass this off to Domenic, because he's written this sort of
> > thing up before and can probably just link you to it.  But the gist of
> > it is that that's the behavior JS programmers expect from their objects,
> > basically.
>
> So first, I apologize Ryan for leaving out this crucial detail when we
> went over this last. I know you've gone through a lot of back-and-forth to
> make these particular properties behave well, and you're right that we did
> seem satisfied with where things ended up. Boris brings up a point though
> that we didn't properly consider.
>
> Also, given that I am stepping into this thread late, let me know if I get
> something horribly wrong.
>
> I still think having these properties return objects (not class instances)
> is great, as it massively simplifies the spec. But Boris is right that as
> currently specced, it seems that each call to the getter creates a new
> object by copying from the internal slot. This breaks expected JS
> semantics, e.g. `key.algorithm !== key.algorithm` since each getter
> invocation returns a new object. In general the guidance for getters is
> that they should behave as much like data-properties as possible, e.g. the
> returned value should not change unless something happens that could change
> it.
>
> Now, let's say that we changed things around so that the internal slot
> stored a JS object, and the getter just returned it directly. Then the
> problem is that outside consumers could modify those objects. Is this bad?
> Yes, because the spec depends on the integrity of the internal slots. OK,
> so now we have a few options:
>
> 1. Lock down the objects. This only works if they are truly immutable (not
> just readonly), but from a brief glance at the spec, that appears to be the
> case? In that case, you can store a frozen object in the internal slot,
> which is tamper-proof against consumers, and just return that same frozen
> object every time, while also consulting it internally. If consumers try to
> modify it, they will get an error (in strict mode).
> 2. Use Boris's strategy, of separating the "model layer" [[algorithm]]
> from the user-exposed "API layer" [[algorithm_exposed]]. Then
> [[algorithm_exposed]] can be mutated by external consumers for whatever
> reason, but that will not break anything, since it is just a manifestation
> of the external values. (This strategy seems a bit overcomplicated because
> WebIDL only supports getters, leading to [[algorithm]] +
> [[algorithm_exposed]] + algorithm getter. In normal JS usage you would
> probably just do [[algorithm]] + an exposed algorithm data property.)
> 3. Bulletproof your spec algorithms against mutations to the object, e.g.
> check for invalid values and throw/reject with appropriate errors. This is
> how the ES spec does things, generally, but I am going to assume it is
> probably a big pain to do here, and not really worth considering. Let me
> know if I'm wrong!
>
> 1 seems nice to me; it provides a clear signal to users that modifying
> these properties is not useful, and has a straightforward conceptual
> model---you are actually tracking these values in JS objects, instead of
> having to convert between layers and type systems.
>
> Others on the TAG have defended 2, saying that frozen JS objects are not
> used very often, and also emphasizing the importance of separating the
> model layer and the API layer.
>
> I think either would be OK. What do you think?
>
> Again, sorry that we're spending so much time on making these properties
> into objects, especially after all the grief I already gave you on them. I
> appreciate you being willing to chart new territory in this regard, since I
> really think we have run up against a place where the path of least
> resistance in WebIDL (a bunch of algorithm classes) is a very bad path.
> Hopefully what we do here can help set a precedent for similar situations
> in the future---I know your usage of internal slots has already inspired a
> couple other specs, with great increases in clarity IMO.


Our replies crossed in flight, but I think Option 2 still has issues (with
respect to cloning), for the reason that you note internal slot storing JS
object is tricky.

So that leaves 1 and 3. 1 certainly has issues, even if it's clean. 3 seems
to introduce a ton of boiler plate, and loses a lot of clarity for the
spec, because now you can no longer rely on your pre-conditions still being
valid.

Received on Monday, 14 July 2014 20:07:53 UTC