Skip to content

Commit

Permalink
Specify open dictionaries.
Browse files Browse the repository at this point in the history
  • Loading branch information
jyasskin committed Sep 30, 2016
1 parent dc0d362 commit 9392a5d
Show file tree
Hide file tree
Showing 2 changed files with 6,380 additions and 5,838 deletions.
111 changes: 111 additions & 0 deletions index.bs
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,9 @@ urlPrefix: https://tc39.github.io/ecma262/; spec: ECMA-262
text: Set; url: sec-set-o-p-v-throw
text: IsConstructor; url: sec-isconstructor
text: Construct; url: sec-construct
text: own property; url: sec-own-property
text: enumerable; url: sec-property-attributes
text: EnumerableOwnProperties; url: sec-enumerableownproperties
text: DefinePropertyOrThrow; url: sec-definepropertyorthrow
url: sec-code-realms
text: Realm
Expand All @@ -120,6 +123,7 @@ urlPrefix: https://tc39.github.io/ecma262/; spec: ECMA-262
text: ECMA-262 section 9.1.8; url: sec-ordinary-object-internal-methods-and-internal-slots-get-p-receiver
text: ECMA-262 section 19.2.2.3; url: sec-function-@@create
text: ECMA-262 section 19.2.3.8; url: sec-function.prototype-@@hasinstance
text: List; url: sec-list-and-record-specification-type
text: Array methods; url: sec-properties-of-the-array-prototype-object
text: typed arrays; url: sec-typedarray-objects
text: GetMethod; url: sec-getmethod
Expand Down Expand Up @@ -5171,6 +5175,7 @@ type.
"DOMException" Null
BufferRelatedType Null
"FrozenArray" "<" Type ">" Null
"dictionary" "<" Type "," Type ">" Null
</pre>

<div data-fill-with="grammar-ConstType"></div>
Expand Down Expand Up @@ -5737,6 +5742,36 @@ is the concatenation of the type name for |T| and
the string “Sequence”.


<h4 id="idl-open-dictionary" dictionary lt="dictionary">Open dictionary types — dictionary&lt;[|K|,] |V|&gt;</h4>

An <dfn export>open dictionary type</dfn> is a parameterized [=dictionary type=]
whose values are ordered associative arrays mapping instances of |K| to
instances of |V|. The (key, value) pairs are called <dfn for="dictionary">mappings</dfn>.
The order of an open dictionary's mappings is determined when the open
dictionary value is created.

|K| must be one of {{DOMString}}, {{USVString}}, or {{ByteString}}. In a type
name of the form <code>dictionary&lt;|V|></code>, which omits |K|, |K| defaults
to {{DOMString}}.

|V| must be a type allowed for [=dictionary members=].

Open dictionaries are always passed by value. In language bindings where an open
dictionary is represented by an object of some kind, passing an open dictionary
to a [=platform object=] will not result in a reference to the open dictionary
being kept by that object. Similarly, any open dictionary returned from a
platform object will be a copy and modifications made to it will not be visible
to the platform object.

There is no way to represent a constant open dictionary value in IDL.

Open dictionaries must not be used as the type of an [=attribute=] or
[=constant=].

The [=type name=] of an open dictionary type is the concatenation of the type
name for |K|, the type name for |V| and the string “OpenDictionary”.


<h4 oldids="dom-promise" id="idl-promise" interface lt="Promise|Promise&lt;T&gt;">Promise types — Promise&lt;|T|&gt;</h4>

A <dfn id="dfn-promise-type" export>promise type</dfn> is a parameterized type
Expand Down Expand Up @@ -7529,6 +7564,82 @@ iterable |iterable| and an iterator getter
</div>


<h4 id="es-open-dictionary">Open dictionaries — dictionary&lt;[|K|,] |V|&gt;</h4>

IDL {{dictionary}}&lt;|K|, |V|&gt; values are represented by
ECMAScript <emu-val>Object</emu-val> values.

<div algorithm="convert object to open dictionary" id="es-to-open-dictionary">
An ECMAScript value |O| is [=converted to an IDL value|converted=] to an IDL <code>{{dictionary}}<|K|, |V|></code> value as follows:

1. If [=Type=](|O|) is not <emu-val>Object</emu-val>,
<a lt="es throw">throw a <emu-val>TypeError</emu-val></a>.
1. Let |result| be a new empty instance of <code>{{dictionary}}<|K|, |V|></code>.
1. Let |entries| be [=EnumerableOwnProperties=](|O|, "key+value").
1. [=ReturnIfAbrupt=](|entries|).
1. Repeat, for each element [|key|, |value|] of |entries| in [=List=] order:
1. Let |typedKey| be |key| [=converted to an IDL value=] of type |K|.
1. Let |typedValue| be |value| [=converted to an IDL value=] of type |V|.
1. Assert: |typedKey| is not yet a key in |result|.
1. Append to |result| a mapping from |typedKey| to |typedValue|.
1. Return |result|.
</div>

<div algorithm="convert open dictionary to object" id="open-dictionary-to-es">
An IDL <code>{{dictionary}}<…></code> value |D| is [=converted to an
ECMAScript value|converted=] to an ECMAScript value as follows:

1. Let |result| be a new <emu-val>Object</emu-val> instance
created as if by the expression <code>{}</code>.
1. Repeat, for each [=dictionary/mapping=] (|key|, |value|) in |D|:
1. Let |esKey| be |key| [=converted to an ECMAScript value=].
1. Let |esValue| be |value| [=converted to an ECMAScript value=].
1. Let |created| be [=!=] [=CreateDataProperty=](|result|, |esKey|, |esValue|).
1. Assert: |created| is <code>true</code>.
1. Return |result|.
</div>

<div class="example" id="example-es-open-dictionary">
Passing the ECMAScript value <code>{b: 3, a: 4}</code> to a
<code>{{dictionary}}&lt;DOMString, long></code> argument would result in the
IDL value:
<table class="data">
<thead><th>Key</th><th>Value</th></thead>
<tr><td><code>"b"</code></td><td><code>3</code></td></tr>
<tr><td><code>"a"</code></td><td><code>4</code></td></tr>
</table>

Open dictionaries only consider [=own property|own=] [=enumerable=] properties, so given an IDL operation
<code>dictionary&lt;long> identity(dictionary&lt;long> arg)</code> which
returns its argument, the following code passes its assertions:

<pre highlight="js">
let proto = {a: 3, b: 4};
let obj = {__proto__: proto, d: 5, c: 6}
Object.defineProperty(obj, "e", {value: 7, enumerable: false});
let result = identity(obj);
assert(result.a === undefined);
assert(result.b === undefined);
assert(result.e === undefined);
let entries = Object.entries(result);
assert(entries[0][0] === "d");
assert(entries[0][1] === "5");
assert(entries[1][0] === "c");
assert(entries[1][1] === "6");
</pre>

Dictionary keys and values can be constrained, although keys can only be
constrained among the three string types. The following conversions all
throw {{TypeError}}s:
<table class="data">
<thead><th>Value</th><th>Passed to type</th></thead>
<tr><td><code>{"😞": 1}</code></td><td><code>{{dictionary}}&lt;ByteString, long></code></td></tr>
<tr><td><code>{"\uD83D": 1}</code></td><td><code>{{dictionary}}&lt;USVString, long></code></td></tr>
<tr><td><code>{a: {hello: "world"}}</code></td><td><code>{{dictionary}}&lt;DOMString, long></code></td></tr>
</table>
</div>


<h4 id="es-promise">Promise types — Promise&lt;|T|&gt;</h4>

IDL [=promise type=] values are
Expand Down

0 comments on commit 9392a5d

Please sign in to comment.