12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724
  1. <!doctype html>
  2. <head><meta charset="utf-8">
  3. <title>Metadata Proposal - ECMAScript</title>
  4. <link rel="stylesheet" href="ecmarkup.css">
  5. <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/8.4/styles/github.min.css">
  6. <script src="ecmarkup.js"></script>
  7. <script>
  8. if (location.hostname === 'rbuckton.github.io' && location.protocol !== 'https:') {
  9. location.protocol = 'https:';
  10. }
  11. </script>
  12. <script type="application/json" id="menu-search-biblio">[{"type":"clause","id":"introduction","aoid":null,"title":"Metadata Proposal - ECMAScript","titleHTML":"Metadata Proposal - ECMAScript","number":"","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Metadata Proposal - ECMAScript"},{"type":"clause","id":"syntax","aoid":null,"title":"Syntax","titleHTML":"Syntax","number":"1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Syntax"},{"type":"op","aoid":"GetOrCreateMetadataMap","refId":"getorcreatemetadatamap","location":"","key":"GetOrCreateMetadataMap"},{"type":"clause","id":"getorcreatemetadatamap","aoid":"GetOrCreateMetadataMap","title":"GetOrCreateMetadataMap ( O, P, Create )","titleHTML":"GetOrCreateMetadataMap ( O, P, Create )","number":"2.1.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"GetOrCreateMetadataMap ( O, P, Create )"},{"type":"clause","id":"operations-on-objects","aoid":null,"title":"Operations on Objects","titleHTML":"Operations on Objects","number":"2.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Operations on Objects"},{"type":"clause","id":"abstract-operations","aoid":null,"title":"Abstract Operations","titleHTML":"Abstract Operations","number":"2","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Abstract Operations"},{"type":"op","aoid":"OrdinaryHasMetadata","refId":"ordinaryhasmetadata","location":"","key":"OrdinaryHasMetadata"},{"type":"clause","id":"ordinaryhasmetadata","aoid":"OrdinaryHasMetadata","title":"OrdinaryHasMetadata ( MetadataKey, O, P )","titleHTML":"OrdinaryHasMetadata ( MetadataKey, O, P )","number":"3.1.1.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryHasMetadata ( MetadataKey, O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-hasmetadata","aoid":null,"title":"[[HasMetadata]] ( MetadataKey, P )","titleHTML":"[[HasMetadata]] ( MetadataKey, P )","number":"3.1.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[HasMetadata]] ( MetadataKey, P )"},{"type":"op","aoid":"OrdinaryHasOwnMetadata","refId":"ordinaryhasownmetadata","location":"","key":"OrdinaryHasOwnMetadata"},{"type":"clause","id":"ordinaryhasownmetadata","aoid":"OrdinaryHasOwnMetadata","title":"OrdinaryHasOwnMetadata ( MetadataKey, O, P )","titleHTML":"OrdinaryHasOwnMetadata ( MetadataKey, O, P )","number":"3.1.2.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryHasOwnMetadata ( MetadataKey, O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-hasownmetadata","aoid":null,"title":"[[HasOwnMetadata]] ( MetadataKey, P )","titleHTML":"[[HasOwnMetadata]] ( MetadataKey, P )","number":"3.1.2","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[HasOwnMetadata]] ( MetadataKey, P )"},{"type":"op","aoid":"OrdinaryGetMetadata","refId":"ordinarygetmetadata","location":"","key":"OrdinaryGetMetadata"},{"type":"clause","id":"ordinarygetmetadata","aoid":"OrdinaryGetMetadata","title":"OrdinaryGetMetadata ( MetadataKey, O, P )","titleHTML":"OrdinaryGetMetadata ( MetadataKey, O, P )","number":"3.1.3.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryGetMetadata ( MetadataKey, O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-getmetadata","aoid":null,"title":"[[GetMetadata]] ( MetadataKey, P )","titleHTML":"[[GetMetadata]] ( MetadataKey, P )","number":"3.1.3","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[GetMetadata]] ( MetadataKey, P )"},{"type":"op","aoid":"OrdinaryGetOwnMetadata","refId":"ordinarygetownmetadata","location":"","key":"OrdinaryGetOwnMetadata"},{"type":"clause","id":"ordinarygetownmetadata","aoid":"OrdinaryGetOwnMetadata","title":"OrdinaryGetOwnMetadata ( MetadataKey, O, P )","titleHTML":"OrdinaryGetOwnMetadata ( MetadataKey, O, P )","number":"3.1.4.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryGetOwnMetadata ( MetadataKey, O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-getownmetadata","aoid":null,"title":"[[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )","titleHTML":"[[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )","number":"3.1.4","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )"},{"type":"op","aoid":"OrdinaryDefineOwnMetadata","refId":"ordinarydefineownmetadata","location":"","key":"OrdinaryDefineOwnMetadata"},{"type":"clause","id":"ordinarydefineownmetadata","aoid":"OrdinaryDefineOwnMetadata","title":"OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )","titleHTML":"OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )","number":"3.1.5.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-defineownmetadata","aoid":null,"title":"[[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )","titleHTML":"[[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )","number":"3.1.5","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )"},{"type":"op","aoid":"OrdinaryMetadataKeys","refId":"ordinarymetadatakeys","location":"","key":"OrdinaryMetadataKeys"},{"type":"clause","id":"ordinarymetadatakeys","aoid":"OrdinaryMetadataKeys","title":"OrdinaryMetadataKeys ( O, P )","titleHTML":"OrdinaryMetadataKeys ( O, P )","number":"3.1.6.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryMetadataKeys ( O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-metadatakeys","aoid":null,"title":"[[MetadataKeys]] ( P )","titleHTML":"[[MetadataKeys]] ( P )","number":"3.1.6","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[MetadataKeys]] ( P )"},{"type":"op","aoid":"OrdinaryOwnMetadataKeys","refId":"ordinaryownmetadatakeys","location":"","key":"OrdinaryOwnMetadataKeys"},{"type":"clause","id":"ordinaryownmetadatakeys","aoid":"OrdinaryOwnMetadataKeys","title":"OrdinaryOwnMetadataKeys ( O, P )","titleHTML":"OrdinaryOwnMetadataKeys ( O, P )","number":"3.1.7.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"OrdinaryOwnMetadataKeys ( O, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-ownmetadatakeys","aoid":null,"title":"[[OwnMetadataKeys]] ( P )","titleHTML":"[[OwnMetadataKeys]] ( P )","number":"3.1.7","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[OwnMetadataKeys]] ( P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots-deletemetadata","aoid":null,"title":"[[DeleteMetadata]]( MetadataKey, P )","titleHTML":"[[DeleteMetadata]]( MetadataKey, P )","number":"3.1.8","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"[[DeleteMetadata]]( MetadataKey, P )"},{"type":"clause","id":"ordinary-object-internal-methods-and-internal-slots","aoid":null,"title":"Ordinary Object Internal Methods and Internal Slots","titleHTML":"Ordinary Object Internal Methods and Internal Slots","number":"3.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Ordinary Object Internal Methods and Internal Slots"},{"type":"clause","id":"ordinary-and-exotic-objects-behaviors","aoid":null,"title":"Ordinary and Exotic Objects Behaviors","titleHTML":"Ordinary and Exotic Objects Behaviors","number":"3","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Ordinary and Exotic Objects Behaviors"},{"type":"clause","id":"reflect-metadatadecoratorfunctions","aoid":null,"title":"Metadata Decorator Functions","titleHTML":"Metadata Decorator Functions","number":"4.1.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Metadata Decorator Functions"},{"type":"clause","id":"reflect.metadata","aoid":null,"title":"Reflect.metadata ( metadataKey, metadataValue )","titleHTML":"Reflect.metadata ( metadataKey, metadataValue )","number":"4.1.2","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.metadata ( metadataKey, metadataValue )"},{"type":"clause","id":"reflect.definemetadata","aoid":null,"title":"Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )","titleHTML":"Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )","number":"4.1.3","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )"},{"type":"clause","id":"reflect.hasmetadata","aoid":null,"title":"Reflect.hasMetadata ( metadataKey, target [, propertyKey] )","titleHTML":"Reflect.hasMetadata ( metadataKey, target [, propertyKey] )","number":"4.1.4","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.hasMetadata ( metadataKey, target [, propertyKey] )"},{"type":"clause","id":"reflect.hasownmetadata","aoid":null,"title":"Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )","titleHTML":"Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )","number":"4.1.5","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )"},{"type":"clause","id":"reflect.getmetadata","aoid":null,"title":"Reflect.getMetadata ( metadataKey, target [, propertyKey] )","titleHTML":"Reflect.getMetadata ( metadataKey, target [, propertyKey] )","number":"4.1.6","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.getMetadata ( metadataKey, target [, propertyKey] )"},{"type":"clause","id":"reflect.getownmetadata","aoid":null,"title":"Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )","titleHTML":"Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )","number":"4.1.7","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )"},{"type":"clause","id":"reflect.getmetadatakeys","aoid":null,"title":"Reflect.getMetadataKeys ( target [, propertyKey] )","titleHTML":"Reflect.getMetadataKeys ( target [, propertyKey] )","number":"4.1.8","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.getMetadataKeys ( target [, propertyKey] )"},{"type":"clause","id":"reflect.getownmetadatakeys","aoid":null,"title":"Reflect.getOwnMetadataKeys ( target [, propertyKey] )","titleHTML":"Reflect.getOwnMetadataKeys ( target [, propertyKey] )","number":"4.1.9","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.getOwnMetadataKeys ( target [, propertyKey] )"},{"type":"clause","id":"reflect.deletemetadata","aoid":null,"title":"Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )","titleHTML":"Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )","number":"4.1.10","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )"},{"type":"clause","id":"reflect","aoid":null,"title":"The Reflect Object","titleHTML":"The Reflect Object","number":"4.1","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"The Reflect Object"},{"type":"clause","id":"reflection","aoid":null,"title":"Reflection","titleHTML":"Reflection","number":"4","namespace":"https://rbuckton.github.io/reflect-metadata","location":"","key":"Reflection"}]</script><script>"use strict";
  13. function Search(menu) {
  14. this.menu = menu;
  15. this.$search = document.getElementById('menu-search');
  16. this.$searchBox = document.getElementById('menu-search-box');
  17. this.$searchResults = document.getElementById('menu-search-results');
  18. this.loadBiblio();
  19. document.addEventListener('keydown', this.documentKeydown.bind(this));
  20. this.$searchBox.addEventListener('keydown', debounce(this.searchBoxKeydown.bind(this), { stopPropagation: true }));
  21. this.$searchBox.addEventListener('keyup', debounce(this.searchBoxKeyup.bind(this), { stopPropagation: true }));
  22. }
  23. Search.prototype.loadBiblio = function () {
  24. var $biblio = document.getElementById('menu-search-biblio');
  25. if (!$biblio) {
  26. this.biblio = {};
  27. } else {
  28. this.biblio = JSON.parse($biblio.textContent);
  29. this.biblio.clauses = this.biblio.filter(function (e) { return e.type === 'clause' });
  30. this.biblio.clausesById = this.biblio.clauses.reduce(function (map, entry) {
  31. map[entry.id] = entry;
  32. return map;
  33. }, {});
  34. }
  35. }
  36. Search.prototype.documentKeydown = function (e) {
  37. if (e.keyCode === 191) {
  38. e.preventDefault();
  39. e.stopPropagation();
  40. this.triggerSearch();
  41. }
  42. }
  43. Search.prototype.searchBoxKeydown = function (e) {
  44. e.stopPropagation();
  45. e.preventDefault();
  46. if (e.keyCode === 191 && e.target.value.length === 0) {
  47. e.preventDefault();
  48. } else if (e.keyCode === 13) {
  49. e.preventDefault();
  50. this.selectResult();
  51. }
  52. }
  53. Search.prototype.searchBoxKeyup = function (e) {
  54. if (e.keyCode === 13 || e.keyCode === 9) {
  55. return;
  56. }
  57. this.search(e.target.value);
  58. }
  59. Search.prototype.triggerSearch = function (e) {
  60. if (this.menu.isVisible()) {
  61. this._closeAfterSearch = false;
  62. } else {
  63. this._closeAfterSearch = true;
  64. this.menu.show();
  65. }
  66. this.$searchBox.focus();
  67. this.$searchBox.select();
  68. }
  69. // bit 12 - Set if the result starts with searchString
  70. // bits 8-11: 8 - number of chunks multiplied by 2 if cases match, otherwise 1.
  71. // bits 1-7: 127 - length of the entry
  72. // General scheme: prefer case sensitive matches with fewer chunks, and otherwise
  73. // prefer shorter matches.
  74. function relevance(result, searchString) {
  75. var relevance = 0;
  76. relevance = Math.max(0, 8 - result.match.chunks) << 7;
  77. if (result.match.caseMatch) {
  78. relevance *= 2;
  79. }
  80. if (result.match.prefix) {
  81. relevance += 2048
  82. }
  83. relevance += Math.max(0, 255 - result.entry.key.length);
  84. return relevance;
  85. }
  86. Search.prototype.search = function (searchString) {
  87. var s = Date.now();
  88. if (searchString === '') {
  89. this.displayResults([]);
  90. this.hideSearch();
  91. return;
  92. } else {
  93. this.showSearch();
  94. }
  95. if (searchString.length === 1) {
  96. this.displayResults([]);
  97. return;
  98. }
  99. var results;
  100. if (/^[\d\.]*$/.test(searchString)) {
  101. results = this.biblio.clauses.filter(function (clause) {
  102. return clause.number.substring(0, searchString.length) === searchString;
  103. }).map(function (clause) {
  104. return { entry: clause };
  105. });
  106. } else {
  107. results = [];
  108. for (var i = 0; i < this.biblio.length; i++) {
  109. var entry = this.biblio[i];
  110. var match = fuzzysearch(searchString, entry.key);
  111. if (match) {
  112. results.push({ entry: entry, match: match });
  113. }
  114. }
  115. results.forEach(function (result) {
  116. result.relevance = relevance(result, searchString);
  117. });
  118. results = results.sort(function (a, b) { return b.relevance - a.relevance });
  119. }
  120. if (results.length > 50) {
  121. results = results.slice(0, 50);
  122. }
  123. this.displayResults(results);
  124. }
  125. Search.prototype.hideSearch = function () {
  126. this.$search.classList.remove('active');
  127. }
  128. Search.prototype.showSearch = function () {
  129. this.$search.classList.add('active');
  130. }
  131. Search.prototype.selectResult = function () {
  132. var $first = this.$searchResults.querySelector('li:first-child a');
  133. if ($first) {
  134. document.location = $first.getAttribute('href');
  135. }
  136. this.$searchBox.value = '';
  137. this.$searchBox.blur();
  138. this.displayResults([]);
  139. this.hideSearch();
  140. if (this._closeAfterSearch) {
  141. this.menu.hide();
  142. }
  143. }
  144. Search.prototype.displayResults = function (results) {
  145. if (results.length > 0) {
  146. this.$searchResults.classList.remove('no-results');
  147. var html = '<ul>';
  148. results.forEach(function (result) {
  149. var entry = result.entry;
  150. var id = entry.id;
  151. var cssClass = '';
  152. var text = '';
  153. if (entry.type === 'clause') {
  154. var number = entry.number ? entry.number + ' ' : '';
  155. text = number + entry.key;
  156. cssClass = 'clause';
  157. id = entry.id;
  158. } else if (entry.type === 'production') {
  159. text = entry.key;
  160. cssClass = 'prod';
  161. id = entry.id;
  162. } else if (entry.type === 'op') {
  163. text = entry.key;
  164. cssClass = 'op';
  165. id = entry.refId;
  166. } else if (entry.type === 'term') {
  167. text = entry.key;
  168. cssClass = 'term';
  169. id = entry.id || entry.refId;
  170. }
  171. if (text) {
  172. html += '<li class=menu-search-result-' + cssClass + '><a href="#' + id + '">' + text + '</a></li>'
  173. }
  174. });
  175. html += '</ul>'
  176. this.$searchResults.innerHTML = html;
  177. } else {
  178. this.$searchResults.innerHTML = '';
  179. this.$searchResults.classList.add('no-results');
  180. }
  181. }
  182. function Menu() {
  183. this.$toggle = document.getElementById('menu-toggle');
  184. this.$menu = document.getElementById('menu');
  185. this.$toc = document.querySelector('menu-toc > ol');
  186. this.$pins = document.querySelector('#menu-pins');
  187. this.$pinList = document.getElementById('menu-pins-list');
  188. this.$toc = document.querySelector('#menu-toc > ol');
  189. this.$specContainer = document.getElementById('spec-container');
  190. this.search = new Search(this);
  191. this._pinnedIds = {};
  192. this.loadPinEntries();
  193. // toggle menu
  194. this.$toggle.addEventListener('click', this.toggle.bind(this));
  195. // keydown events for pinned clauses
  196. document.addEventListener('keydown', this.documentKeydown.bind(this));
  197. // toc expansion
  198. var tocItems = this.$menu.querySelectorAll('#menu-toc li');
  199. for (var i = 0; i < tocItems.length; i++) {
  200. var $item = tocItems[i];
  201. $item.addEventListener('click', function($item, event) {
  202. $item.classList.toggle('active');
  203. event.stopPropagation();
  204. }.bind(null, $item));
  205. }
  206. // close toc on toc item selection
  207. var tocLinks = this.$menu.querySelectorAll('#menu-toc li > a');
  208. for (var i = 0; i < tocLinks.length; i++) {
  209. var $link = tocLinks[i];
  210. $link.addEventListener('click', function(event) {
  211. this.toggle();
  212. event.stopPropagation();
  213. }.bind(this));
  214. }
  215. // update active clause on scroll
  216. window.addEventListener('scroll', debounce(this.updateActiveClause.bind(this)));
  217. this.updateActiveClause();
  218. // prevent menu scrolling from scrolling the body
  219. this.$toc.addEventListener('wheel', function (e) {
  220. var target = e.currentTarget;
  221. var offTop = e.deltaY < 0 && target.scrollTop === 0;
  222. if (offTop) {
  223. e.preventDefault();
  224. }
  225. var offBottom = e.deltaY > 0
  226. && target.offsetHeight + target.scrollTop >= target.scrollHeight;
  227. if (offBottom) {
  228. event.preventDefault();
  229. }
  230. })
  231. // handle pinning clauses via the pin link
  232. document.addEventListener('click', function (e) {
  233. if (e.target.classList.contains('utils-pin')) {
  234. var id = e.target.parentNode.parentNode.parentNode.parentNode.id;
  235. this.togglePinEntry(id);
  236. }
  237. }.bind(this))
  238. }
  239. Menu.prototype.documentKeydown = function (e) {
  240. e.stopPropagation();
  241. if (e.keyCode === 80) {
  242. this.togglePinEntry();
  243. } else if (e.keyCode > 48 && e.keyCode < 58) {
  244. this.selectPin(e.keyCode - 49);
  245. }
  246. }
  247. Menu.prototype.updateActiveClause = function () {
  248. this.setActiveClause(findActiveClause(this.$specContainer))
  249. }
  250. Menu.prototype.setActiveClause = function (clause) {
  251. this.$activeClause = clause;
  252. this.revealInToc(this.$activeClause);
  253. }
  254. Menu.prototype.revealInToc = function (path) {
  255. var current = this.$toc.querySelectorAll('li.revealed');
  256. for (var i = 0; i < current.length; i++) {
  257. current[i].classList.remove('revealed');
  258. current[i].classList.remove('revealed-leaf');
  259. }
  260. var current = this.$toc;
  261. var index = 0;
  262. while (index < path.length) {
  263. var children = current.children;
  264. for (var i = 0; i < children.length; i++) {
  265. if ('#' + path[index].id === children[i].children[1].getAttribute('href') ) {
  266. children[i].classList.add('revealed');
  267. if (index === path.length - 1) {
  268. children[i].classList.add('revealed-leaf');
  269. var rect = children[i].getBoundingClientRect();
  270. this.$toc.getBoundingClientRect().top
  271. var tocRect = this.$toc.getBoundingClientRect();
  272. if (rect.top + 10 > tocRect.bottom) {
  273. this.$toc.scrollTop = this.$toc.scrollTop + (rect.top - tocRect.bottom) + (rect.bottom - rect.top);
  274. } else if (rect.top < tocRect.top) {
  275. this.$toc.scrollTop = this.$toc.scrollTop - (tocRect.top - rect.top);
  276. }
  277. }
  278. current = children[i].querySelector('ol');
  279. index++;
  280. break;
  281. }
  282. }
  283. }
  284. }
  285. function findActiveClause(root, path) {
  286. var clauses = new ClauseWalker(root);
  287. var $clause;
  288. var found = false;
  289. var path = path || [];
  290. while ($clause = clauses.nextNode()) {
  291. var rect = $clause.getBoundingClientRect();
  292. var $header = $clause.children[0];
  293. var marginTop = parseInt(getComputedStyle($header)["margin-top"]);
  294. if ((rect.top - marginTop) <= 0 && rect.bottom > 0) {
  295. found = true;
  296. return findActiveClause($clause, path.concat($clause)) || path;
  297. }
  298. }
  299. return path;
  300. }
  301. function ClauseWalker(root) {
  302. var previous;
  303. var treeWalker = document.createTreeWalker(
  304. root,
  305. NodeFilter.SHOW_ELEMENT,
  306. {
  307. acceptNode: function (node) {
  308. if (previous === node.parentNode) {
  309. return NodeFilter.FILTER_REJECT;
  310. } else {
  311. previous = node;
  312. }
  313. if (node.nodeName === 'EMU-CLAUSE' || node.nodeName === 'EMU-INTRO' || node.nodeName === 'EMU-ANNEX') {
  314. return NodeFilter.FILTER_ACCEPT;
  315. } else {
  316. return NodeFilter.FILTER_SKIP;
  317. }
  318. }
  319. },
  320. false
  321. );
  322. return treeWalker;
  323. }
  324. Menu.prototype.toggle = function () {
  325. this.$menu.classList.toggle('active');
  326. }
  327. Menu.prototype.show = function () {
  328. this.$menu.classList.add('active');
  329. }
  330. Menu.prototype.hide = function () {
  331. this.$menu.classList.remove('active');
  332. }
  333. Menu.prototype.isVisible = function() {
  334. return this.$menu.classList.contains('active');
  335. }
  336. Menu.prototype.showPins = function () {
  337. this.$pins.classList.add('active');
  338. }
  339. Menu.prototype.hidePins = function () {
  340. this.$pins.classList.remove('active');
  341. }
  342. Menu.prototype.addPinEntry = function (id) {
  343. var entry = this.search.biblio.clausesById[id];
  344. var prefix;
  345. if (entry.number) {
  346. prefix = entry.number + ' ';
  347. } else {
  348. prefix = '';
  349. }
  350. this.$pinList.innerHTML += '<li><a href="#' + entry.id + '">' + prefix + entry.titleHTML + '</a></li>';
  351. if (Object.keys(this._pinnedIds).length === 0) {
  352. this.showPins();
  353. }
  354. this._pinnedIds[id] = true;
  355. this.persistPinEntries();
  356. }
  357. Menu.prototype.removePinEntry = function (id) {
  358. var item = this.$pinList.querySelector('a[href="#' + id + '"]').parentNode;
  359. this.$pinList.removeChild(item);
  360. delete this._pinnedIds[id];
  361. if (Object.keys(this._pinnedIds).length === 0) {
  362. this.hidePins();
  363. }
  364. this.persistPinEntries();
  365. }
  366. Menu.prototype.persistPinEntries = function () {
  367. try {
  368. if (!window.localStorage) return;
  369. } catch (e) {
  370. return;
  371. }
  372. localStorage.pinEntries = JSON.stringify(Object.keys(this._pinnedIds));
  373. }
  374. Menu.prototype.loadPinEntries = function () {
  375. try {
  376. if (!window.localStorage) return;
  377. } catch (e) {
  378. return;
  379. }
  380. var pinsString = window.localStorage.pinEntries;
  381. if (!pinsString) return;
  382. var pins = JSON.parse(pinsString);
  383. for(var i = 0; i < pins.length; i++) {
  384. this.addPinEntry(pins[i]);
  385. }
  386. }
  387. Menu.prototype.togglePinEntry = function (id) {
  388. if (!id) {
  389. id = this.$activeClause[this.$activeClause.length - 1].id;
  390. }
  391. if (this._pinnedIds[id]) {
  392. this.removePinEntry(id);
  393. } else {
  394. this.addPinEntry(id);
  395. }
  396. }
  397. Menu.prototype.selectPin = function (num) {
  398. document.location = this.$pinList.children[num].children[0].href;
  399. }
  400. function init() {
  401. var menu = new Menu();
  402. }
  403. document.addEventListener('DOMContentLoaded', init);
  404. function debounce(fn, opts) {
  405. opts = opts || {};
  406. var timeout;
  407. return function(e) {
  408. if (opts.stopPropagation) {
  409. e.stopPropagation();
  410. }
  411. var args = arguments;
  412. if (timeout) {
  413. clearTimeout(timeout);
  414. }
  415. timeout = setTimeout(function() {
  416. timeout = null;
  417. fn.apply(this, args);
  418. }.bind(this), 150);
  419. }
  420. }
  421. var CLAUSE_NODES = ['EMU-CLAUSE', 'EMU-INTRO', 'EMU-ANNEX'];
  422. function findLocalReferences ($elem) {
  423. var name = $elem.innerHTML;
  424. var references = [];
  425. var parentClause = $elem.parentNode;
  426. while (parentClause && CLAUSE_NODES.indexOf(parentClause.nodeName) === -1) {
  427. parentClause = parentClause.parentNode;
  428. }
  429. if(!parentClause) return;
  430. var vars = parentClause.querySelectorAll('var');
  431. for (var i = 0; i < vars.length; i++) {
  432. var $var = vars[i];
  433. if ($var.innerHTML === name) {
  434. references.push($var);
  435. }
  436. }
  437. return references;
  438. }
  439. function toggleFindLocalReferences($elem) {
  440. var references = findLocalReferences($elem);
  441. if ($elem.classList.contains('referenced')) {
  442. references.forEach(function ($reference) {
  443. $reference.classList.remove('referenced');
  444. });
  445. } else {
  446. references.forEach(function ($reference) {
  447. $reference.classList.add('referenced');
  448. });
  449. }
  450. }
  451. function installFindLocalReferences () {
  452. document.addEventListener('click', function (e) {
  453. if (e.target.nodeName === 'VAR') {
  454. toggleFindLocalReferences(e.target);
  455. }
  456. });
  457. }
  458. document.addEventListener('DOMContentLoaded', installFindLocalReferences);
  459. // The following license applies to the fuzzysearch function
  460. // The MIT License (MIT)
  461. // Copyright © 2015 Nicolas Bevacqua
  462. // Copyright © 2016 Brian Terlson
  463. // Permission is hereby granted, free of charge, to any person obtaining a copy of
  464. // this software and associated documentation files (the "Software"), to deal in
  465. // the Software without restriction, including without limitation the rights to
  466. // use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
  467. // the Software, and to permit persons to whom the Software is furnished to do so,
  468. // subject to the following conditions:
  469. // The above copyright notice and this permission notice shall be included in all
  470. // copies or substantial portions of the Software.
  471. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  472. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
  473. // FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
  474. // COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
  475. // IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  476. // CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  477. function fuzzysearch (searchString, haystack, caseInsensitive) {
  478. var tlen = haystack.length;
  479. var qlen = searchString.length;
  480. var chunks = 1;
  481. var finding = false;
  482. var prefix = true;
  483. if (qlen > tlen) {
  484. return false;
  485. }
  486. if (qlen === tlen) {
  487. if (searchString === haystack) {
  488. return { caseMatch: true, chunks: 1, prefix: true };
  489. } else if (searchString.toLowerCase() === haystack.toLowerCase()) {
  490. return { caseMatch: false, chunks: 1, prefix: true };
  491. } else {
  492. return false;
  493. }
  494. }
  495. outer: for (var i = 0, j = 0; i < qlen; i++) {
  496. var nch = searchString[i];
  497. while (j < tlen) {
  498. var targetChar = haystack[j++];
  499. if (targetChar === nch) {
  500. finding = true;
  501. continue outer;
  502. }
  503. if (finding) {
  504. chunks++;
  505. finding = false;
  506. }
  507. }
  508. if (caseInsensitive) { return false }
  509. return fuzzysearch(searchString.toLowerCase(), haystack.toLowerCase(), true);
  510. }
  511. return { caseMatch: !caseInsensitive, chunks: chunks, prefix: j <= qlen };
  512. }
  513. var CLAUSE_NODES = ['EMU-CLAUSE', 'EMU-INTRO', 'EMU-ANNEX'];
  514. function findLocalReferences ($elem) {
  515. var name = $elem.innerHTML;
  516. var references = [];
  517. var parentClause = $elem.parentNode;
  518. while (parentClause && CLAUSE_NODES.indexOf(parentClause.nodeName) === -1) {
  519. parentClause = parentClause.parentNode;
  520. }
  521. if(!parentClause) return;
  522. var vars = parentClause.querySelectorAll('var');
  523. for (var i = 0; i < vars.length; i++) {
  524. var $var = vars[i];
  525. if ($var.innerHTML === name) {
  526. references.push($var);
  527. }
  528. }
  529. return references;
  530. }
  531. function toggleFindLocalReferences($elem) {
  532. var references = findLocalReferences($elem);
  533. if ($elem.classList.contains('referenced')) {
  534. references.forEach(function ($reference) {
  535. $reference.classList.remove('referenced');
  536. });
  537. } else {
  538. references.forEach(function ($reference) {
  539. $reference.classList.add('referenced');
  540. });
  541. }
  542. }
  543. function installFindLocalReferences () {
  544. document.addEventListener('click', function (e) {
  545. if (e.target.nodeName === 'VAR') {
  546. toggleFindLocalReferences(e.target);
  547. }
  548. });
  549. }
  550. document.addEventListener('DOMContentLoaded', installFindLocalReferences);
  551. </script><style>body {
  552. display: flex;
  553. font-size: 18px;
  554. line-height: 1.5;
  555. font-family: Cambria, Palatino Linotype, Palatino, Liberation Serif, serif;
  556. padding: 0;
  557. margin: 0;
  558. color: #111;
  559. }
  560. #spec-container {
  561. padding-left: 20px;
  562. flex-grow: 1;
  563. flex-basis: 66%;
  564. box-sizing: border-box;
  565. overflow: hidden;
  566. }
  567. body.oldtoc {
  568. margin: 0 auto;
  569. }
  570. a {
  571. text-decoration: none;
  572. color: #206ca7;
  573. }
  574. a:visited {
  575. color: #206ca7;
  576. }
  577. a:hover {
  578. text-decoration: underline;
  579. color: #239dee;
  580. }
  581. code {
  582. font-weight: bold;
  583. font-family: Consolas, Monaco, monospace;
  584. white-space: pre;
  585. }
  586. pre code {
  587. font-weight: inherit;
  588. }
  589. pre code.hljs {
  590. background-color: #fff;
  591. margin: 0;
  592. padding: 0;
  593. }
  594. ol.toc {
  595. list-style: none;
  596. padding-left: 0;
  597. }
  598. ol.toc ol.toc {
  599. padding-left: 2ex;
  600. list-style: none;
  601. }
  602. var {
  603. color: #2aa198;
  604. transition: background-color 0.25s ease;
  605. cursor: pointer;
  606. }
  607. var.referenced {
  608. background-color: #ffff33;
  609. }
  610. emu-const {
  611. font-family: sans-serif;
  612. }
  613. emu-val {
  614. font-weight: bold;
  615. }
  616. emu-alg ol, emu-alg ol ol ol ol {
  617. list-style-type: decimal;
  618. }
  619. emu-alg ol ol, emu-alg ol ol ol ol ol {
  620. list-style-type: lower-alpha;
  621. }
  622. emu-alg ol ol ol, ol ol ol ol ol ol {
  623. list-style-type: lower-roman;
  624. }
  625. emu-eqn {
  626. display: block;
  627. margin-left: 4em;
  628. }
  629. emu-eqn.inline {
  630. display: inline;
  631. margin: 0;
  632. }
  633. emu-eqn div:first-child {
  634. margin-left: -2em;
  635. }
  636. emu-note {
  637. margin: 1em 0;
  638. color: #666;
  639. border-left: 5px solid #ccc;
  640. display: flex;
  641. flex-direction: row;
  642. }
  643. emu-note > span.note {
  644. flex-basis: 100px;
  645. min-width: 100px;
  646. flex-grow: 0;
  647. flex-shrink: 1;
  648. text-transform: uppercase;
  649. padding-left: 5px;
  650. }
  651. emu-note[type=editor] {
  652. border-left-color: #faa;
  653. }
  654. emu-note > div.note-contents {
  655. flex-grow: 1;
  656. flex-shrink: 1;
  657. }
  658. emu-note > div.note-contents > p:first-child {
  659. margin-top: 0;
  660. }
  661. emu-note > div.note-contents > p:last-child {
  662. margin-bottom: 0;
  663. }
  664. emu-example {
  665. display: block;
  666. margin: 1em 3em;
  667. }
  668. emu-example figure figcaption {
  669. margin-top: 0.5em;
  670. text-align: left;
  671. }
  672. emu-production {
  673. display: block;
  674. margin-top: 1em;
  675. margin-bottom: 1em;
  676. margin-left: 5ex;
  677. }
  678. emu-grammar.inline, emu-production.inline,
  679. emu-grammar.inline emu-production emu-rhs, emu-production.inline emu-rhs {
  680. display: inline;
  681. }
  682. emu-grammar[collapsed] emu-production, emu-production[collapsed] {
  683. margin: 0;
  684. }
  685. emu-grammar[collapsed] emu-production emu-rhs, emu-production[collapsed] emu-rhs {
  686. display: inline;
  687. padding-left: 1ex;
  688. }
  689. emu-constraints {
  690. font-size: .75em;
  691. margin-right: 1ex;
  692. }
  693. emu-gann {
  694. margin-right: 1ex;
  695. }
  696. emu-gann emu-t:last-child,
  697. emu-gann emu-nt:last-child {
  698. margin-right: 0;
  699. }
  700. emu-geq {
  701. margin-left: 1ex;
  702. font-weight: bold;
  703. }
  704. emu-oneof {
  705. font-weight: bold;
  706. margin-left: 1ex;
  707. }
  708. emu-nt {
  709. display: inline-block;
  710. font-style: italic;
  711. white-space: nowrap;
  712. text-indent: 0;
  713. }
  714. emu-nt a, emu-nt a:visited {
  715. color: #333;
  716. }
  717. emu-rhs emu-nt {
  718. margin-right: 1ex;
  719. }
  720. emu-t {
  721. display: inline-block;
  722. font-family: monospace;
  723. font-weight: bold;
  724. white-space: nowrap;
  725. text-indent: 0;
  726. }
  727. emu-production emu-t {
  728. margin-right: 1ex;
  729. }
  730. emu-rhs {
  731. display: block;
  732. padding-left: 75px;
  733. text-indent: -25px;
  734. }
  735. emu-mods {
  736. font-size: .85em;
  737. vertical-align: sub;
  738. font-style: normal;
  739. font-weight: normal;
  740. }
  741. emu-production[collapsed] emu-mods {
  742. display: none;
  743. }
  744. emu-params, emu-opt {
  745. margin-right: 1ex;
  746. font-family: monospace;
  747. }
  748. emu-params, emu-constraints {
  749. color: #2aa198;
  750. }
  751. emu-opt {
  752. color: #b58900;
  753. }
  754. emu-gprose {
  755. font-size: 0.9em;
  756. font-family: Helvetica, Arial, sans-serif;
  757. }
  758. h1.shortname {
  759. color: #f60;
  760. font-size: 1.5em;
  761. margin: 0;
  762. }
  763. h1.version {
  764. color: #f60;
  765. font-size: 1.5em;
  766. margin: 0;
  767. }
  768. h1.title {
  769. margin-top: 0;
  770. color: #f60;
  771. }
  772. h1.first {
  773. margin-top: 0;
  774. }
  775. h1, h2, h3, h4, h5, h6 {
  776. position: relative;
  777. }
  778. h1 .secnum {
  779. text-decoration: none;
  780. margin-right: 10px;
  781. }
  782. h1 span.title {
  783. order: 2;
  784. }
  785. h1 { font-size: 2.67em; margin-top: 2em; margin-bottom: 1em; line-height: 1em;}
  786. h2 { font-size: 2em; }
  787. h3 { font-size: 1.56em; }
  788. h4 { font-size: 1.25em; }
  789. h5 { font-size: 1.11em; }
  790. h6 { font-size: 1em; }
  791. h1:hover span.utils {
  792. display: block;
  793. }
  794. span.utils {
  795. font-size: 18px;
  796. line-height: 18px;
  797. display: none;
  798. position: absolute;
  799. top: 100%;
  800. left: 0;
  801. right: 0;
  802. font-weight: normal;
  803. }
  804. span.utils:before {
  805. content: "⤷";
  806. display: inline-block;
  807. padding: 0 5px;
  808. }
  809. span.utils > * {
  810. display: inline-block;
  811. margin-right: 20px;
  812. }
  813. h1 span.utils span.anchor a,
  814. h2 span.utils span.anchor a,
  815. h3 span.utils span.anchor a,
  816. h4 span.utils span.anchor a,
  817. h5 span.utils span.anchor a,
  818. h6 span.utils span.anchor a {
  819. text-decoration: none;
  820. font-variant: small-caps;
  821. }
  822. h1 span.utils span.anchor a:hover,
  823. h2 span.utils span.anchor a:hover,
  824. h3 span.utils span.anchor a:hover,
  825. h4 span.utils span.anchor a:hover,
  826. h5 span.utils span.anchor a:hover,
  827. h6 span.utils span.anchor a:hover {
  828. color: #333;
  829. }
  830. emu-intro h1, emu-clause h1, emu-annex h1 { font-size: 2em; }
  831. emu-intro h2, emu-clause h2, emu-annex h2 { font-size: 1.56em; }
  832. emu-intro h3, emu-clause h3, emu-annex h3 { font-size: 1.25em; }
  833. emu-intro h4, emu-clause h4, emu-annex h4 { font-size: 1.11em; }
  834. emu-intro h5, emu-clause h5, emu-annex h5 { font-size: 1em; }
  835. emu-intro h6, emu-clause h6, emu-annex h6 { font-size: 0.9em; }
  836. emu-intro emu-intro h1, emu-clause emu-clause h1, emu-annex emu-annex h1 { font-size: 1.56em; }
  837. emu-intro emu-intro h2, emu-clause emu-clause h2, emu-annex emu-annex h2 { font-size: 1.25em; }
  838. emu-intro emu-intro h3, emu-clause emu-clause h3, emu-annex emu-annex h3 { font-size: 1.11em; }
  839. emu-intro emu-intro h4, emu-clause emu-clause h4, emu-annex emu-annex h4 { font-size: 1em; }
  840. emu-intro emu-intro h5, emu-clause emu-clause h5, emu-annex emu-annex h5 { font-size: 0.9em; }
  841. emu-intro emu-intro emu-intro h1, emu-clause emu-clause emu-clause h1, emu-annex emu-annex emu-annex h1 { font-size: 1.25em; }
  842. emu-intro emu-intro emu-intro h2, emu-clause emu-clause emu-clause h2, emu-annex emu-annex emu-annex h2 { font-size: 1.11em; }
  843. emu-intro emu-intro emu-intro h3, emu-clause emu-clause emu-clause h3, emu-annex emu-annex emu-annex h3 { font-size: 1em; }
  844. emu-intro emu-intro emu-intro h4, emu-clause emu-clause emu-clause h4, emu-annex emu-annex emu-annex h4 { font-size: 0.9em; }
  845. emu-intro emu-intro emu-intro emu-intro h1, emu-clause emu-clause emu-clause emu-clause h1, emu-annex emu-annex emu-annex emu-annex h1 { font-size: 1.11em; }
  846. emu-intro emu-intro emu-intro emu-intro h2, emu-clause emu-clause emu-clause emu-clause h2, emu-annex emu-annex emu-annex emu-annex h2 { font-size: 1em; }
  847. emu-intro emu-intro emu-intro emu-intro h3, emu-clause emu-clause emu-clause emu-clause h3, emu-annex emu-annex emu-annex emu-annex h3 { font-size: 0.9em; }
  848. emu-intro emu-intro emu-intro emu-intro emu-intro h1, emu-clause emu-clause emu-clause emu-clause emu-clause h1, emu-annex emu-annex emu-annex emu-annex emu-annex h1 { font-size: 1em; }
  849. emu-intro emu-intro emu-intro emu-intro emu-intro h2, emu-clause emu-clause emu-clause emu-clause emu-clause h2, emu-annex emu-annex emu-annex emu-annex emu-annex h2 { font-size: 0.9em; }
  850. emu-intro emu-intro emu-intro emu-intro emu-intro emu-intro h1, emu-clause emu-clause emu-clause emu-clause emu-clause emu-clause h1, emu-annex emu-annex emu-annex emu-annex emu-annex emu-annex h1 { font-size: 0.9em }
  851. emu-clause {
  852. display: block;
  853. }
  854. /* Figures and tables */
  855. figure { display: block; margin: 1em 0 3em 0; }
  856. figure object { display: block; margin: 0 auto; }
  857. figure table.real-table { margin: 0 auto; }
  858. figure figcaption {
  859. display: block;
  860. color: #555555;
  861. font-weight: bold;
  862. text-align: center;
  863. }
  864. emu-table table {
  865. margin: 0 auto;
  866. }
  867. emu-table table, table.real-table {
  868. border-collapse: collapse;
  869. }
  870. emu-table td, emu-table th, table.real-table td, table.real-table th {
  871. border: 1px solid black;
  872. padding: 0.4em;
  873. vertical-align: baseline;
  874. }
  875. emu-table th, emu-table thead td, table.real-table th {
  876. background-color: #eeeeee;
  877. }
  878. /* Note: the left content edges of table.lightweight-table >tbody >tr >td
  879. and div.display line up. */
  880. table.lightweight-table {
  881. border-collapse: collapse;
  882. margin: 0 0 0 1.5em;
  883. }
  884. table.lightweight-table td, table.lightweight-table th {
  885. border: none;
  886. padding: 0 0.5em;
  887. vertical-align: baseline;
  888. }
  889. /* diff styles */
  890. ins {
  891. background-color: #e0f8e0;
  892. text-decoration: none;
  893. border-bottom: 1px solid #396;
  894. }
  895. del {
  896. background-color: #fee;
  897. }
  898. ins.block, del.block,
  899. emu-production > ins, emu-production > del,
  900. emu-grammar > ins, emu-grammar > del {
  901. display: block;
  902. }
  903. /* Menu Styles */
  904. #menu-toggle {
  905. font-size: 2em;
  906. position: fixed;
  907. top: 0;
  908. left: 0;
  909. width: 1.5em;
  910. height: 1.5em;
  911. z-index: 3;
  912. visibility: hidden;
  913. color: #1567a2;
  914. background-color: #fff;
  915. line-height: 1.5em;
  916. text-align: center;
  917. -webkit-touch-callout: none;
  918. -webkit-user-select: none;
  919. -khtml-user-select: none;
  920. -moz-user-select: none;
  921. -ms-user-select: none;
  922. user-select: none;;
  923. cursor: pointer;
  924. }
  925. #menu {
  926. display: flex;
  927. flex-direction: column;
  928. width: 33%; height: 100vh;
  929. max-width: 500px;
  930. box-sizing: border-box;
  931. background-color: #ddd;
  932. overflow: hidden;
  933. transition: opacity 0.1s linear;
  934. padding: 0 5px;
  935. position: fixed;
  936. left: 0; top: 0;
  937. z-index: 2;
  938. }
  939. #menu-spacer {
  940. flex-basis: 33%;
  941. max-width: 500px;
  942. flex-grow: 0;
  943. flex-shrink: 0;
  944. }
  945. #menu a {
  946. color: #1567a2;
  947. }
  948. #menu.active {
  949. display: flex;
  950. opacity: 1;
  951. z-index: 2;
  952. }
  953. #menu-pins {
  954. flex-grow: 1;
  955. display: none;
  956. }
  957. #menu-pins.active {
  958. display: block;
  959. }
  960. #menu-pins-list {
  961. margin: 0;
  962. padding: 0;
  963. counter-reset: pins-counter;
  964. }
  965. #menu-pins-list > li:before {
  966. content: counter(pins-counter);
  967. counter-increment: pins-counter;
  968. display: inline-block;
  969. width: 25px;
  970. text-align: center;
  971. border: 1px solid #bbb;
  972. padding: 2px;
  973. margin: 4px;
  974. box-sizing: border-box;
  975. line-height: 1em;
  976. background-color: #ccc;
  977. border-radius: 4px;
  978. }
  979. #menu-toc > ol {
  980. padding: 0;
  981. flex-grow: 1;
  982. }
  983. #menu-toc > ol li {
  984. padding: 0;
  985. }
  986. #menu-toc > ol , #menu-toc > ol ol {
  987. list-style-type: none;
  988. margin: 0;
  989. padding: 0;
  990. }
  991. #menu-toc > ol ol {
  992. padding-left: 0.75em;
  993. }
  994. #menu-toc li {
  995. text-overflow: ellipsis;
  996. overflow: hidden;
  997. white-space: nowrap;
  998. }
  999. #menu-toc .item-toggle {
  1000. display: inline-block;
  1001. transform: rotate(-45deg) translate(-5px, -5px);
  1002. transition: transform 0.1s ease;
  1003. text-align: center;
  1004. width: 20px;
  1005. color: #aab;
  1006. -webkit-touch-callout: none;
  1007. -webkit-user-select: none;
  1008. -khtml-user-select: none;
  1009. -moz-user-select: none;
  1010. -ms-user-select: none;
  1011. user-select: none;;
  1012. cursor: pointer;
  1013. }
  1014. #menu-toc .item-toggle-none {
  1015. display: inline-block;
  1016. width: 20px;
  1017. }
  1018. #menu-toc li.active > .item-toggle {
  1019. transform: rotate(45deg) translate(-5px, -5px);
  1020. }
  1021. #menu-toc li > ol {
  1022. display: none;
  1023. }
  1024. #menu-toc li.active > ol {
  1025. display: block;
  1026. }
  1027. #menu-toc li.revealed > a {
  1028. background-color: #bbb;
  1029. font-weight: bold;
  1030. /*
  1031. background-color: #222;
  1032. color: #c6d8e4;
  1033. */
  1034. }
  1035. #menu-toc li.revealed-leaf> a {
  1036. color: #206ca7;
  1037. /*
  1038. background-color: #222;
  1039. color: #c6d8e4;
  1040. */
  1041. }
  1042. #menu-toc li.revealed > .item-toggle {
  1043. transform: rotate(45deg) translate(-5px, -5px);
  1044. }
  1045. #menu-toc li.revealed > ol {
  1046. display: block;
  1047. }
  1048. #menu-toc li > a {
  1049. padding: 2px 5px;
  1050. }
  1051. #menu > * {
  1052. margin-bottom: 5px;
  1053. }
  1054. .menu-pane-header {
  1055. padding: 0 5px;
  1056. text-transform: uppercase;
  1057. background-color: #aaa;
  1058. color: #335;
  1059. font-weight: bold;
  1060. letter-spacing: 2px;
  1061. flex-grow: 0;
  1062. flex-shrink: 0;
  1063. font-size: 0.8em;
  1064. }
  1065. #menu-toc {
  1066. display: flex;
  1067. flex-direction: column;
  1068. width: 100%;
  1069. overflow: hidden;
  1070. flex-grow: 1;
  1071. }
  1072. #menu-toc ol.toc {
  1073. overflow-x: hidden;
  1074. overflow-y: auto;
  1075. }
  1076. #menu-search {
  1077. position: relative;
  1078. flex-grow: 0;
  1079. flex-shrink: 0;
  1080. width: 100%;
  1081. display: flex;
  1082. flex-direction: column;
  1083. max-height: 300px;
  1084. }
  1085. #menu-trace-list {
  1086. display: none;
  1087. }
  1088. #menu-search-box {
  1089. box-sizing: border-box;
  1090. display: block;
  1091. width: 100%;
  1092. margin: 5px 0 0 0;
  1093. font-size: 1em;
  1094. padding: 2px;
  1095. background-color: #bbb;
  1096. border: 1px solid #999;
  1097. }
  1098. #menu-search-results {
  1099. overflow-x: hidden;
  1100. overflow-y: auto;
  1101. }
  1102. li.menu-search-result-clause:before {
  1103. content: 'clause';
  1104. width: 40px;
  1105. display: inline-block;
  1106. text-align: right;
  1107. padding-right: 1ex;
  1108. color: #666;
  1109. font-size: 75%;
  1110. }
  1111. li.menu-search-result-op:before {
  1112. content: 'op';
  1113. width: 40px;
  1114. display: inline-block;
  1115. text-align: right;
  1116. padding-right: 1ex;
  1117. color: #666;
  1118. font-size: 75%;
  1119. }
  1120. li.menu-search-result-prod:before {
  1121. content: 'prod';
  1122. width: 40px;
  1123. display: inline-block;
  1124. text-align: right;
  1125. padding-right: 1ex;
  1126. color: #666;
  1127. font-size: 75%
  1128. }
  1129. li.menu-search-result-term:before {
  1130. content: 'term';
  1131. width: 40px;
  1132. display: inline-block;
  1133. text-align: right;
  1134. padding-right: 1ex;
  1135. color: #666;
  1136. font-size: 75%
  1137. }
  1138. #menu-search-results ul {
  1139. padding: 0 5px;
  1140. margin: 0;
  1141. }
  1142. #menu-search-results li {
  1143. white-space: nowrap;
  1144. text-overflow: ellipsis;
  1145. }
  1146. #menu-trace-list {
  1147. counter-reset: item;
  1148. margin: 0 0 0 20px;
  1149. padding: 0;
  1150. }
  1151. #menu-trace-list li {
  1152. display: block;
  1153. white-space: nowrap;
  1154. }
  1155. #menu-trace-list li .secnum:after {
  1156. content: " ";
  1157. }
  1158. #menu-trace-list li:before {
  1159. content: counter(item) " ";
  1160. background-color: #222;
  1161. counter-increment: item;
  1162. color: #999;
  1163. width: 20px;
  1164. height: 20px;
  1165. line-height: 20px;
  1166. display: inline-block;
  1167. text-align: center;
  1168. margin: 2px 4px 2px 0;
  1169. }
  1170. @media (max-width: 1000px) {
  1171. body {
  1172. margin: 0;
  1173. display: block;
  1174. }
  1175. #menu {
  1176. display: none;
  1177. padding-top: 3em;
  1178. width: 450px;
  1179. }
  1180. #menu.active {
  1181. position: fixed;
  1182. height: 100%;
  1183. left: 0;
  1184. top: 0;
  1185. right: 300px;
  1186. }
  1187. #menu-toggle {
  1188. visibility: visible;
  1189. }
  1190. #spec-container {
  1191. padding: 0 5px;
  1192. }
  1193. }
  1194. @media only screen and (max-width: 800px) {
  1195. #menu {
  1196. width: 100%;
  1197. }
  1198. h1 .secnum:empty {
  1199. margin: 0; padding: 0;
  1200. }
  1201. }
  1202. </style></head><body><div id="menu-toggle">☰</div><div id="menu-spacer"></div><div id="menu"><div id="menu-search"><input type="text" id="menu-search-box" placeholder="Search..."><div id="menu-search-results" class="inactive"></div></div><div id="menu-pins"><div class="menu-pane-header">Pinned Clauses</div><ul id="menu-pins-list"></ul></div><div class="menu-pane-header">Table of Contents</div><div id="menu-toc"><ol class="toc"><li><span class="item-toggle-none"></span><a href="#introduction" title="Metadata Proposal - ECMAScript">Metadata Proposal - ECMAScript</a></li><li><span class="item-toggle-none"></span><a href="#syntax" title="Syntax"><span class="secnum">1</span> Syntax</a></li><li><span class="item-toggle">◢</span><a href="#abstract-operations" title="Abstract Operations"><span class="secnum">2</span> Abstract Operations</a><ol class="toc"><li><span class="item-toggle">◢</span><a href="#operations-on-objects" title="Operations on Objects"><span class="secnum">2.1</span> Operations on Objects</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#getorcreatemetadatamap" title="GetOrCreateMetadataMap ( O, P, Create )"><span class="secnum">2.1.1</span> GetOrCreateMetadataMap ( O, P, Create )</a></li></ol></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-and-exotic-objects-behaviors" title="Ordinary and Exotic Objects Behaviors"><span class="secnum">3</span> Ordinary and Exotic Objects Behaviors</a><ol class="toc"><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots" title="Ordinary Object Internal Methods and Internal Slots"><span class="secnum">3.1</span> Ordinary Object Internal Methods and Internal Slots</a><ol class="toc"><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-hasmetadata" title="[[HasMetadata]] ( MetadataKey, P )"><span class="secnum">3.1.1</span> [[HasMetadata]] ( MetadataKey, P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinaryhasmetadata" title="OrdinaryHasMetadata ( MetadataKey, O, P )"><span class="secnum">3.1.1.1</span> OrdinaryHasMetadata ( MetadataKey, O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-hasownmetadata" title="[[HasOwnMetadata]] ( MetadataKey, P )"><span class="secnum">3.1.2</span> [[HasOwnMetadata]] ( MetadataKey, P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinaryhasownmetadata" title="OrdinaryHasOwnMetadata ( MetadataKey, O, P )"><span class="secnum">3.1.2.1</span> OrdinaryHasOwnMetadata ( MetadataKey, O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-getmetadata" title="[[GetMetadata]] ( MetadataKey, P )"><span class="secnum">3.1.3</span> [[GetMetadata]] ( MetadataKey, P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinarygetmetadata" title="OrdinaryGetMetadata ( MetadataKey, O, P )"><span class="secnum">3.1.3.1</span> OrdinaryGetMetadata ( MetadataKey, O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-getownmetadata" title="[[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )"><span class="secnum">3.1.4</span> [[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinarygetownmetadata" title="OrdinaryGetOwnMetadata ( MetadataKey, O, P )"><span class="secnum">3.1.4.1</span> OrdinaryGetOwnMetadata ( MetadataKey, O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-defineownmetadata" title="[[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )"><span class="secnum">3.1.5</span> [[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinarydefineownmetadata" title="OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )"><span class="secnum">3.1.5.1</span> OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-metadatakeys" title="[[MetadataKeys]] ( P )"><span class="secnum">3.1.6</span> [[MetadataKeys]] ( P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinarymetadatakeys" title="OrdinaryMetadataKeys ( O, P )"><span class="secnum">3.1.6.1</span> OrdinaryMetadataKeys ( O, P )</a></li></ol></li><li><span class="item-toggle">◢</span><a href="#ordinary-object-internal-methods-and-internal-slots-ownmetadatakeys" title="[[OwnMetadataKeys]] ( P )"><span class="secnum">3.1.7</span> [[OwnMetadataKeys]] ( P )</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#ordinaryownmetadatakeys" title="OrdinaryOwnMetadataKeys ( O, P )"><span class="secnum">3.1.7.1</span> OrdinaryOwnMetadataKeys ( O, P )</a></li></ol></li><li><span class="item-toggle-none"></span><a href="#ordinary-object-internal-methods-and-internal-slots-deletemetadata" title="[[DeleteMetadata]]( MetadataKey, P )"><span class="secnum">3.1.8</span> [[DeleteMetadata]]( MetadataKey, P )</a></li></ol></li></ol></li><li><span class="item-toggle">◢</span><a href="#reflection" title="Reflection"><span class="secnum">4</span> Reflection</a><ol class="toc"><li><span class="item-toggle">◢</span><a href="#reflect" title="The Reflect Object"><span class="secnum">4.1</span> The Reflect Object</a><ol class="toc"><li><span class="item-toggle-none"></span><a href="#reflect-metadatadecoratorfunctions" title="Metadata Decorator Functions"><span class="secnum">4.1.1</span> Metadata Decorator Functions</a></li><li><span class="item-toggle-none"></span><a href="#reflect.metadata" title="Reflect.metadata ( metadataKey, metadataValue )"><span class="secnum">4.1.2</span> Reflect.metadata ( metadataKey, metadataValue )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.definemetadata" title="Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )"><span class="secnum">4.1.3</span> Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.hasmetadata" title="Reflect.hasMetadata ( metadataKey, target [, propertyKey] )"><span class="secnum">4.1.4</span> Reflect.hasMetadata ( metadataKey, target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.hasownmetadata" title="Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )"><span class="secnum">4.1.5</span> Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.getmetadata" title="Reflect.getMetadata ( metadataKey, target [, propertyKey] )"><span class="secnum">4.1.6</span> Reflect.getMetadata ( metadataKey, target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.getownmetadata" title="Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )"><span class="secnum">4.1.7</span> Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.getmetadatakeys" title="Reflect.getMetadataKeys ( target [, propertyKey] )"><span class="secnum">4.1.8</span> Reflect.getMetadataKeys ( target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.getownmetadatakeys" title="Reflect.getOwnMetadataKeys ( target [, propertyKey] )"><span class="secnum">4.1.9</span> Reflect.getOwnMetadataKeys ( target [, propertyKey] )</a></li><li><span class="item-toggle-none"></span><a href="#reflect.deletemetadata" title="Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )"><span class="secnum">4.1.10</span> Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )</a></li></ol></li></ol></li></ol></div></div><div id="spec-container">
  1203. <emu-intro id="introduction">
  1204. <h1 class="first">Metadata Proposal - ECMAScript<span class="utils"><span class="anchor"><a href="#introduction">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1205. <emu-note><span class="note">Note</span><div class="note-contents">A shim for this API can be found here: <a href="https://github.com/rbuckton/ReflectDecorators">https://github.com/rbuckton/ReflectDecorators</a></div></emu-note>
  1206. <p>Proposal to add Metadata to ECMAScript.</p>
  1207. </emu-intro>
  1208. <emu-clause id="syntax">
  1209. <h1><span class="secnum">1</span>Syntax<span class="utils"><span class="anchor"><a href="#syntax">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1210. <emu-note><span class="note">Note</span><div class="note-contents">This section is non-normative.</div></emu-note>
  1211. <pre><code class="javascript hljs"><span class="hljs-comment">// define metadata on an object or property</span>
  1212. <span class="hljs-built_in">Reflect</span>.defineMetadata(metadataKey, metadataValue, target);
  1213. <span class="hljs-built_in">Reflect</span>.defineMetadata(metadataKey, metadataValue, target, propertyKey);
  1214. <span class="hljs-comment">// check for presence of a metadata key on the prototype chain of an object or property</span>
  1215. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.hasMetadata(metadataKey, target);
  1216. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.hasMetadata(metadataKey, target, propertyKey);
  1217. <span class="hljs-comment">// check for presence of an own metadata key of an object or property</span>
  1218. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.hasOwnMetadata(metadataKey, target);
  1219. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.hasOwnMetadata(metadataKey, target, propertyKey);
  1220. <span class="hljs-comment">// get metadata value of a metadata key on the prototype chain of an object or property</span>
  1221. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getMetadata(metadataKey, target);
  1222. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getMetadata(metadataKey, target, propertyKey);
  1223. <span class="hljs-comment">// get metadata value of an own metadata key of an object or property</span>
  1224. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getOwnMetadata(metadataKey, target);
  1225. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getOwnMetadata(metadataKey, target, propertyKey);
  1226. <span class="hljs-comment">// get all metadata keys on the prototype chain of an object or property</span>
  1227. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getMetadataKeys(target);
  1228. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getMetadataKeys(target, propertyKey);
  1229. <span class="hljs-comment">// get all own metadata keys of an object or property</span>
  1230. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getOwnMetadataKeys(target);
  1231. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.getOwnMetadataKeys(target, propertyKey);
  1232. <span class="hljs-comment">// delete metadata from an object or property</span>
  1233. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.deleteMetadata(metadataKey, target);
  1234. <span class="hljs-keyword">let</span> result = <span class="hljs-built_in">Reflect</span>.deleteMetadata(metadataKey, target, propertyKey);
  1235. <span class="hljs-comment">// apply metadata via a decorator to a constructor</span>
  1236. @<span class="hljs-built_in">Reflect</span>.metadata(metadataKey, metadataValue)
  1237. <span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">C</span> </span>{
  1238. <span class="hljs-comment">// apply metadata via a decorator to a method (property)</span>
  1239. @<span class="hljs-built_in">Reflect</span>.metadata(metadataKey, metadataValue)
  1240. method() {
  1241. }
  1242. }
  1243. <span class="hljs-comment">// Design-time type annotations</span>
  1244. <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">Type</span>(<span class="hljs-params">type</span>) </span>{ <span class="hljs-keyword">return</span> <span class="hljs-built_in">Reflect</span>.metadata(<span class="hljs-string">"design:type"</span>, type); }
  1245. <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">ParamTypes</span>(<span class="hljs-params">...types</span>) </span>{ <span class="hljs-keyword">return</span> <span class="hljs-built_in">Reflect</span>.metadata(<span class="hljs-string">"design:paramtypes"</span>, types); }
  1246. <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">ReturnType</span>(<span class="hljs-params">type</span>) </span>{ <span class="hljs-keyword">return</span> <span class="hljs-built_in">Reflect</span>.metadata(<span class="hljs-string">"design:returntype"</span>, type); }
  1247. <span class="hljs-comment">// Decorator application</span>
  1248. @ParamTypes(<span class="hljs-built_in">String</span>, <span class="hljs-built_in">Number</span>)
  1249. <span class="hljs-class"><span class="hljs-keyword">class</span> <span class="hljs-title">C</span> </span>{
  1250. <span class="hljs-keyword">constructor</span>(text, i) {
  1251. }
  1252. @Type(<span class="hljs-built_in">String</span>)
  1253. get name() { <span class="hljs-keyword">return</span> <span class="hljs-string">"text"</span>; }
  1254. @Type(<span class="hljs-built_in">Function</span>)
  1255. @ParamTypes(<span class="hljs-built_in">Number</span>, <span class="hljs-built_in">Number</span>)
  1256. @ReturnType(<span class="hljs-built_in">Number</span>)
  1257. add(x, y) {
  1258. <span class="hljs-keyword">return</span> x + y;
  1259. }
  1260. }
  1261. <span class="hljs-comment">// Metadata introspection</span>
  1262. <span class="hljs-keyword">let</span> obj = <span class="hljs-keyword">new</span> C(<span class="hljs-string">"a"</span>, <span class="hljs-number">1</span>);
  1263. <span class="hljs-keyword">let</span> paramTypes = <span class="hljs-built_in">Reflect</span>.getMetadata(<span class="hljs-string">"design:paramtypes"</span>, inst, <span class="hljs-string">"add"</span>); <span class="hljs-comment">// [Number, Number]</span></code></pre>
  1264. </emu-clause>
  1265. <emu-clause id="abstract-operations">
  1266. <h1><span class="secnum">2</span>Abstract Operations<span class="utils"><span class="anchor"><a href="#abstract-operations">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1267. <emu-clause id="operations-on-objects">
  1268. <h1><span class="secnum">2.1</span>Operations on Objects<span class="utils"><span class="anchor"><a href="#operations-on-objects">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1269. <emu-clause id="getorcreatemetadatamap" aoid="GetOrCreateMetadataMap">
  1270. <h1><span class="secnum">2.1.1</span>GetOrCreateMetadataMap ( O, P, Create )<span class="utils"><span class="anchor"><a href="#getorcreatemetadatamap">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1271. <p>When the abstract operation GetOrCreateMetadataMap is called with Object <var>O</var>, property key <var>P</var>, and Boolean <var>Create</var> the following steps are taken:</p>
  1272. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>targetMetadata</var> be the value of <var>O</var>'s [[Metadata]] internal slot.</li><li>If <var>targetMetadata</var> is <emu-val>undefined</emu-val>, then<ol><li>If <var>Create</var> is <emu-val>false</emu-val>, return <emu-val>undefined</emu-val>.</li><li>Set <var>targetMetadata</var> to be a newly created <emu-val>Map</emu-val> object.</li><li>Set the [[Metadata]] internal slot of <var>O</var> to <var>targetMetadata</var>.</li></ol></li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>targetMetadata</var>, <code>"get"</code>, <var>P</var>).</li><li>If <var>metadataMap</var> is <emu-val>undefined</emu-val>, then<ol><li>If <var>Create</var> is <emu-val>false</emu-val>, return <emu-val>undefined</emu-val>.</li><li>Set <var>metadataMap</var> to be a newly created <emu-val>Map</emu-val> object.</li><li>Perform ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>targetMetadata</var>, <code>"set"</code>, <var>P</var>, <var>metadataMap</var>).</li></ol></li><li>Return <var>metadataMap</var>.
  1273. </li></ol></emu-alg>
  1274. </emu-clause>
  1275. </emu-clause>
  1276. </emu-clause>
  1277. <emu-clause id="ordinary-and-exotic-objects-behaviors">
  1278. <h1><span class="secnum">3</span>Ordinary and Exotic Objects Behaviors<span class="utils"><span class="anchor"><a href="#ordinary-and-exotic-objects-behaviors">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1279. <emu-clause id="ordinary-object-internal-methods-and-internal-slots">
  1280. <h1><span class="secnum">3.1</span>Ordinary Object Internal Methods and Internal Slots<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1281. <p>All ordinary objects have an internal slot called [[Metadata]]. The value of this internal slot is either <emu-val>null</emu-val> or a <emu-val>Map</emu-val> object and is used for storing metadata for an object.</p>
  1282. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-hasmetadata">
  1283. <h1><span class="secnum">3.1.1</span>[[HasMetadata]] ( MetadataKey, P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-hasmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1284. <p>When the [[HasMetadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var> and property key <var>P</var>, the following steps are taken:</p>
  1285. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryHasMetadata"><a href="#ordinaryhasmetadata">OrdinaryHasMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).
  1286. </li></ol></emu-alg>
  1287. <emu-clause id="ordinaryhasmetadata" aoid="OrdinaryHasMetadata">
  1288. <h1><span class="secnum">3.1.1.1</span>OrdinaryHasMetadata ( MetadataKey, O, P )<span class="utils"><span class="anchor"><a href="#ordinaryhasmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1289. <p>When the abstract operation OrdinaryHasMetadata is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, Object <var>O</var>, and property key <var>P</var>, the following steps are taken:</p>
  1290. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>hasOwn</var> be ?&nbsp;<emu-xref aoid="OrdinaryHasOwnMetadata"><a href="#ordinaryhasownmetadata">OrdinaryHasOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).</li><li>If <var>hasOwn</var> is <emu-val>true</emu-val>, return <emu-val>true</emu-val>.</li><li>Let <var>parent</var> be ? <var>O</var>.[[GetPrototypeOf]]().</li><li>If <var>parent</var> is not <emu-val>null</emu-val>, Return ? <var>parent</var>.[[HasMetadata]](<var>MetadataKey</var>, <var>P</var>).</li><li>Return <emu-val>false</emu-val>.
  1291. </li></ol></emu-alg>
  1292. </emu-clause>
  1293. </emu-clause>
  1294. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-hasownmetadata">
  1295. <h1><span class="secnum">3.1.2</span>[[HasOwnMetadata]] ( MetadataKey, P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-hasownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1296. <p>When the [[HasOwnMetadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var> and property key <var>P</var>, the following steps are taken:</p>
  1297. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryHasOwnMetadata"><a href="#ordinaryhasownmetadata">OrdinaryHasOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).
  1298. </li></ol></emu-alg>
  1299. <emu-clause id="ordinaryhasownmetadata" aoid="OrdinaryHasOwnMetadata">
  1300. <h1><span class="secnum">3.1.2.1</span>OrdinaryHasOwnMetadata ( MetadataKey, O, P )<span class="utils"><span class="anchor"><a href="#ordinaryhasownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1301. <p>When the abstract operation OrdinaryHasOwnMetadata is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, Object <var>O</var>, and property key <var>P</var>, the following steps are taken:</p>
  1302. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="GetOrCreateMetadataMap"><a href="#getorcreatemetadatamap">GetOrCreateMetadataMap</a></emu-xref>(<var>O</var>, <var>P</var>, <emu-val>false</emu-val>).</li><li>If <var>metadataMap</var> is <emu-val>undefined</emu-val>, return <emu-val>false</emu-val>.</li><li>Return ?&nbsp;<emu-xref aoid="ToBoolean"><a href="https://tc39.github.io/ecma262/#sec-toboolean">ToBoolean</a></emu-xref>(? <emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>metadataMap</var>, <code>"has"</code>, <var>MetadataKey</var>)).
  1303. </li></ol></emu-alg>
  1304. </emu-clause>
  1305. </emu-clause>
  1306. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-getmetadata">
  1307. <h1><span class="secnum">3.1.3</span>[[GetMetadata]] ( MetadataKey, P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-getmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1308. <p>When the [[GetMatadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var> and property key <var>P</var>, the following steps are taken:</p>
  1309. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryGetMetadata"><a href="#ordinarygetmetadata">OrdinaryGetMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).
  1310. </li></ol></emu-alg>
  1311. <emu-clause id="ordinarygetmetadata" aoid="OrdinaryGetMetadata">
  1312. <h1><span class="secnum">3.1.3.1</span>OrdinaryGetMetadata ( MetadataKey, O, P )<span class="utils"><span class="anchor"><a href="#ordinarygetmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1313. <p>When the abstract operation OrdinaryGetMetadata is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, Object <var>O</var>, and property key <var>P</var>, the following steps are taken:</p>
  1314. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>hasOwn</var> be ?&nbsp;<emu-xref aoid="OrdinaryHasOwnMetadata"><a href="#ordinaryhasownmetadata">OrdinaryHasOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).</li><li>If <var>hasOwn</var> is <emu-val>true</emu-val>, return ?&nbsp;<emu-xref aoid="OrdinaryGetOwnMetadata"><a href="#ordinarygetownmetadata">OrdinaryGetOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).</li><li>Let <var>parent</var> be ? <var>O</var>.[[GetPrototypeOf]]().</li><li>If <var>parent</var> is not <emu-val>null</emu-val>, return ? <var>parent</var>.[[GetMetadata]](<var>MetadataKey</var>, <var>P</var>).</li><li>Return <emu-val>undefined</emu-val>.
  1315. </li></ol></emu-alg>
  1316. </emu-clause>
  1317. </emu-clause>
  1318. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-getownmetadata">
  1319. <h1><span class="secnum">3.1.4</span>[[GetOwnMetadata]] ( MetadataKey, P, ParamIndex )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-getownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1320. <p>When the [[GetOwnMetadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var> and property key <var>P</var>, the following steps are taken:</p>
  1321. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryGetOwnMetadata"><a href="#ordinarygetownmetadata">OrdinaryGetOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>O</var>, <var>P</var>).
  1322. </li></ol></emu-alg>
  1323. <emu-clause id="ordinarygetownmetadata" aoid="OrdinaryGetOwnMetadata">
  1324. <h1><span class="secnum">3.1.4.1</span>OrdinaryGetOwnMetadata ( MetadataKey, O, P )<span class="utils"><span class="anchor"><a href="#ordinarygetownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1325. <p>When the abstract operation OrdinaryGetOwnMetadata is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, Object <var>O</var>, and property key <var>P</var>, the following steps are taken:</p>
  1326. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="GetOrCreateMetadataMap"><a href="#getorcreatemetadatamap">GetOrCreateMetadataMap</a></emu-xref>(<var>O</var>, <var>P</var>, <emu-val>false</emu-val>).</li><li>If <var>metadataMap</var> is <emu-val>undefined</emu-val>, return <emu-val>undefined</emu-val>.</li><li>Return ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>metadataMap</var>, <code>"get"</code>, <var>MetadataKey</var>).
  1327. </li></ol></emu-alg>
  1328. </emu-clause>
  1329. </emu-clause>
  1330. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-defineownmetadata">
  1331. <h1><span class="secnum">3.1.5</span>[[DefineOwnMetadata]] ( MetadataKey, MetadataValue, P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-defineownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1332. <p>When the [[DefineOwnMetadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataValue</var>, and property key <var>P</var>, the following steps are taken:</p>
  1333. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryDefineOwnMetadata"><a href="#ordinarydefineownmetadata">OrdinaryDefineOwnMetadata</a></emu-xref>(<var>MetadataKey</var>, <var>MetadataValue</var>, <var>O</var>, <var>P</var>)
  1334. </li></ol></emu-alg>
  1335. <emu-clause id="ordinarydefineownmetadata" aoid="OrdinaryDefineOwnMetadata">
  1336. <h1><span class="secnum">3.1.5.1</span>OrdinaryDefineOwnMetadata ( MetadataKey, MetadataValue, O, P )<span class="utils"><span class="anchor"><a href="#ordinarydefineownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1337. <p>When the abstract operation <emu-xref aoid="OrdinaryDefineOwnProperty"><a href="https://tc39.github.io/ecma262/#sec-ordinarydefineownproperty">OrdinaryDefineOwnProperty</a></emu-xref> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var>, <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataValue</var>, Object <var>O</var>, and property key <var>P</var>, the following steps are taken:</p>
  1338. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="GetOrCreateMetadataMap"><a href="#getorcreatemetadatamap">GetOrCreateMetadataMap</a></emu-xref>(<var>O</var>, <var>P</var>, <emu-val>true</emu-val>).</li><li>Return ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>metadataMap</var>, <code>"set"</code>, <var>MetadataKey</var>, <var>MetadataValue</var>).
  1339. </li></ol></emu-alg>
  1340. </emu-clause>
  1341. </emu-clause>
  1342. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-metadatakeys">
  1343. <h1><span class="secnum">3.1.6</span>[[MetadataKeys]] ( P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-metadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1344. <p>When the [[MetadataKeys]] internal method of <var>O</var> is called with property key <var>P</var> the following steps are taken:</p>
  1345. <emu-alg><ol><li>Return ?&nbsp;<emu-xref aoid="OrdinaryMetadataKeys"><a href="#ordinarymetadatakeys">OrdinaryMetadataKeys</a></emu-xref>(<var>O</var>, <var>P</var>).
  1346. </li></ol></emu-alg>
  1347. <emu-clause id="ordinarymetadatakeys" aoid="OrdinaryMetadataKeys">
  1348. <h1><span class="secnum">3.1.6.1</span>OrdinaryMetadataKeys ( O, P )<span class="utils"><span class="anchor"><a href="#ordinarymetadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1349. <p>When the abstract operation OrdinaryMetadataKeys is called with Object <var>O</var> and property key <var>P</var> the following steps are taken:</p>
  1350. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>ownKeys</var> be ?&nbsp;<emu-xref aoid="OrdinaryOwnMetadataKeys"><a href="#ordinaryownmetadatakeys">OrdinaryOwnMetadataKeys</a></emu-xref>(<var>O</var>, <var>P</var>).</li><li>Let <var>parent</var> be ? <var>O</var>.[[GetPrototypeOf]]().</li><li>If <var>parent</var> is <emu-val>null</emu-val>, then return <var>ownKeys</var>.</li><li>Let <var>parentKeys</var> be ? <var>O</var>.[[OrdinaryMetadataKeys]](<var>P</var>).</li><li>Let <var>ownKeysLen</var> = ?&nbsp;<emu-xref aoid="Get"><a href="https://tc39.github.io/ecma262/#sec-get-o-p">Get</a></emu-xref>(<var>ownKeys</var>, "length").</li><li>If <var>ownKeysLen</var> is <emu-val>0</emu-val>, return <var>parentKeys</var>.</li><li>Let <var>parentKeysLen</var> = ?&nbsp;<emu-xref aoid="Get"><a href="https://tc39.github.io/ecma262/#sec-get-o-p">Get</a></emu-xref>(<var>parentKeys</var>, "length").</li><li>If <var>parentKeysLen</var> is <emu-val>0</emu-val>, return <var>ownKeys</var>.</li><li>Let <var>set</var> be a newly created <emu-val>Set</emu-val> object.</li><li>Let <var>keys</var> be ?&nbsp;<emu-xref aoid="ArrayCreate"><a href="https://tc39.github.io/ecma262/#sec-arraycreate">ArrayCreate</a></emu-xref>(0).</li><li>Let <var>k</var> be <emu-val>0</emu-val>.</li><li>For each element <var>key</var> of <var>ownKeys</var><ol><li>Let <var>hasKey</var> be ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>set</var>, <code>"has"</code>, <var>key</var>).</li><li>If <var>hasKey</var> is <emu-val>false</emu-val>, then<ol><li>Let <var>Pk</var> be !&nbsp;<emu-xref aoid="ToString"><a href="https://tc39.github.io/ecma262/#sec-tostring">ToString</a></emu-xref>(<var>k</var>).</li><li>Perform ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>set</var>, "add", <var>key</var>).</li><li>Let <var>defineStatus</var> be <emu-xref aoid="CreateDataProperty"><a href="https://tc39.github.io/ecma262/#sec-createdataproperty">CreateDataProperty</a></emu-xref>(<var>keys</var>, <var>Pk</var>, <var>key</var>).</li><li>Assert: <var>defineStatus</var> is <emu-val>true</emu-val>.</li><li>Increase <var>k</var> by <emu-val>1</emu-val>.</li></ol></li></ol></li><li>For each element <var>key</var> of <var>parentKeys</var><ol><li>Let <var>hasKey</var> be ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>set</var>, <code>"has"</code>, <var>key</var>).</li><li>If <var>hasKey</var> is <emu-val>false</emu-val>, then<ol><li>Let <var>Pk</var> be !&nbsp;<emu-xref aoid="ToString"><a href="https://tc39.github.io/ecma262/#sec-tostring">ToString</a></emu-xref>(<var>k</var>).</li><li>Perform ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>set</var>, <code>"add"</code>, <var>key</var>).</li><li>Let <var>defineStatus</var> be <emu-xref aoid="CreateDataProperty"><a href="https://tc39.github.io/ecma262/#sec-createdataproperty">CreateDataProperty</a></emu-xref>(<var>keys</var>, <var>Pk</var>, <var>key</var>).</li><li>Assert: <var>defineStatus</var> is <emu-val>true</emu-val>.</li><li>Increase <var>k</var> by <emu-val>1</emu-val>.</li></ol></li></ol></li><li>Perform ?&nbsp;<emu-xref aoid="Set"><a href="https://tc39.github.io/ecma262/#sec-set-o-p-v-throw">Set</a></emu-xref>(<var>keys</var>, <code>"length"</code>, <var>k</var>).</li><li>return <var>keys</var>.
  1351. </li></ol></emu-alg>
  1352. </emu-clause>
  1353. </emu-clause>
  1354. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-ownmetadatakeys">
  1355. <h1><span class="secnum">3.1.7</span>[[OwnMetadataKeys]] ( P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-ownmetadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1356. <p>When the [[OwnMetadataKeys]] internal method of <var>O</var> is called with property key <var>P</var> the following steps are taken:</p>
  1357. <emu-alg><ol><li>Return <emu-xref aoid="OrdinaryOwnMetadataKeys"><a href="#ordinaryownmetadatakeys">OrdinaryOwnMetadataKeys</a></emu-xref>(<var>O</var>, <var>P</var>).
  1358. </li></ol></emu-alg>
  1359. <emu-clause id="ordinaryownmetadatakeys" aoid="OrdinaryOwnMetadataKeys">
  1360. <h1><span class="secnum">3.1.7.1</span>OrdinaryOwnMetadataKeys ( O, P )<span class="utils"><span class="anchor"><a href="#ordinaryownmetadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1361. <p>When the abstract operation OrdinaryOwnMetadataKeys is called with Object <var>O</var> and property key <var>P</var> the following steps are taken:</p>
  1362. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>keys</var> be ?&nbsp;<emu-xref aoid="ArrayCreate"><a href="https://tc39.github.io/ecma262/#sec-arraycreate">ArrayCreate</a></emu-xref>(0).</li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="GetOrCreateMetadataMap"><a href="#getorcreatemetadatamap">GetOrCreateMetadataMap</a></emu-xref>(<var>O</var>, <var>P</var>, <emu-val>false</emu-val>).</li><li>If <var>metadataMap</var> is <emu-val>undefined</emu-val>, return <var>keys</var>.</li><li>Let <var>keysObj</var> be ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>metadataMap</var>, <code>"keys"</code>).</li><li>Let <var>iterator</var> be ?&nbsp;<emu-xref aoid="GetIterator"><a href="https://tc39.github.io/ecma262/#sec-getiterator">GetIterator</a></emu-xref>(<var>keysObj</var>).</li><li>Let <var>k</var> be <emu-val>0</emu-val>.</li><li>Repeat<ol><li>Let <var>Pk</var> be !&nbsp;<emu-xref aoid="ToString"><a href="https://tc39.github.io/ecma262/#sec-tostring">ToString</a></emu-xref>(<var>k</var>).</li><li>Let <var>next</var> be ?&nbsp;<emu-xref aoid="IteratorStep"><a href="https://tc39.github.io/ecma262/#sec-iteratorstep">IteratorStep</a></emu-xref>(<var>iterator</var>).</li><li>If <var>next</var> is <emu-val>false</emu-val>, then<ol><li>Let <var>setStatus</var> be ?&nbsp;<emu-xref aoid="Set"><a href="https://tc39.github.io/ecma262/#sec-set-o-p-v-throw">Set</a></emu-xref>(<var>keys</var>, <code>"length"</code>, <var>k</var>, <var>true</var>).</li><li>Assert: <var>setStatus</var> is <emu-val>true</emu-val>.</li><li>Return <var>keys</var>.</li></ol></li><li>Let <var>nextValue</var> be ?&nbsp;<emu-xref aoid="IteratorValue"><a href="https://tc39.github.io/ecma262/#sec-iteratorvalue">IteratorValue</a></emu-xref>(<var>next</var>).</li><li>Let <var>defineStatus</var> be <emu-xref aoid="CreateDataPropertyOrThrow"><a href="https://tc39.github.io/ecma262/#sec-createdatapropertyorthrow">CreateDataPropertyOrThrow</a></emu-xref>(<var>keys</var>, <var>Pk</var>, <var>nextValue</var>).</li><li>If <var>defineStatus</var> is an <emu-xref href="#sec-completion-record-specification-type"><a href="https://tc39.github.io/ecma262/#sec-completion-record-specification-type">abrupt completion</a></emu-xref>, return ?&nbsp;<emu-xref aoid="IteratorClose"><a href="https://tc39.github.io/ecma262/#sec-iteratorclose">IteratorClose</a></emu-xref>(<var>iterator</var>, <var>defineStatus</var>).</li><li>Increase <var>k</var> by <emu-val>1</emu-val>.
  1363. </li></ol></li></ol></emu-alg>
  1364. </emu-clause>
  1365. </emu-clause>
  1366. <emu-clause id="ordinary-object-internal-methods-and-internal-slots-deletemetadata">
  1367. <h1><span class="secnum">3.1.8</span>[[DeleteMetadata]]( MetadataKey, P )<span class="utils"><span class="anchor"><a href="#ordinary-object-internal-methods-and-internal-slots-deletemetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1368. <p>When the [[DeleteMetadata]] internal method of <var>O</var> is called with <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref> <var>MetadataKey</var> and property key <var>P</var> the following steps are taken:</p>
  1369. <emu-alg><ol><li>Assert: <var>P</var> is <emu-val>undefined</emu-val> or <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>P</var>) is <emu-val>true</emu-val>.</li><li>Let <var>metadataMap</var> be ?&nbsp;<emu-xref aoid="GetOrCreateMetadataMap"><a href="#getorcreatemetadatamap">GetOrCreateMetadataMap</a></emu-xref>(<var>O</var>, <var>P</var>, <emu-val>false</emu-val>).</li><li>If <var>metadataMap</var> is <emu-val>undefined</emu-val>, return <emu-val>false</emu-val>.</li><li>Return ?&nbsp;<emu-xref aoid="Invoke"><a href="https://tc39.github.io/ecma262/#sec-invoke">Invoke</a></emu-xref>(<var>metadataMap</var>, <code>"delete"</code>, <var>MetadataKey</var>).
  1370. </li></ol></emu-alg>
  1371. </emu-clause>
  1372. </emu-clause>
  1373. </emu-clause>
  1374. <emu-clause id="reflection">
  1375. <h1><span class="secnum">4</span>Reflection<span class="utils"><span class="anchor"><a href="#reflection">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1376. <emu-clause id="reflect">
  1377. <h1><span class="secnum">4.1</span>The Reflect Object<span class="utils"><span class="anchor"><a href="#reflect">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1378. <p>This section contains amendments to the Reflect object.</p>
  1379. <emu-clause id="reflect-metadatadecoratorfunctions">
  1380. <h1><span class="secnum">4.1.1</span>Metadata Decorator Functions<span class="utils"><span class="anchor"><a href="#reflect-metadatadecoratorfunctions">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1381. <p>A metadata decorator function is an anonymous built-in function that has [[MetadataKey]] and [[MetadataValue]] internal slots.</p>
  1382. <p>When a metadata decorator function <var>F</var> is called with arguments <var>target</var> and <var>key</var>, the following steps are taken:</p>
  1383. <emu-alg><ol><li>Assert: <var>F</var> has a [[MetadataKey]] internal slot whose value is an <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref>, or <emu-val>undefined</emu-val>.</li><li>Assert: <var>F</var> has a [[MetadataValue]] internal slot whose value is an <emu-xref href="#sec-ecmascript-language-types"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-language-types">ECMAScript language value</a></emu-xref>, or <emu-val>undefined</emu-val>.</li><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>If <var>key</var> is not <emu-val>undefined</emu-val> and <emu-xref aoid="IsPropertyKey"><a href="https://tc39.github.io/ecma262/#sec-ispropertykey">IsPropertyKey</a></emu-xref>(<var>key</var>) is <emu-val>false</emu-val>, throw a <emu-val>TypeError</emu-val> exception.</li><li>Let <var>metadataKey</var> be the value of <var>F</var>'s [[MetadataKey]] internal slot.</li><li>Let <var>metadataValue</var> be the value of <var>F</var>'s [[MetadataValue]] internal slot.</li><li>Perform ? <var>target</var>.[[DefineMetadata]](<var>metadataKey</var>, <var>metadataValue</var>, <var>target</var>, <var>key</var>).</li><li>Return <emu-val>undefined</emu-val>.
  1384. </li></ol></emu-alg>
  1385. </emu-clause>
  1386. <emu-clause id="reflect.metadata">
  1387. <h1><span class="secnum">4.1.2</span>Reflect.metadata ( metadataKey, metadataValue )<span class="utils"><span class="anchor"><a href="#reflect.metadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1388. <p>When the <code>metadata</code> function is called with arguments <var>metadataKey</var> and <var>metadataValue</var>, the following steps are taken:</p>
  1389. <emu-alg><ol><li>Let <var>decorator</var> be a new built-in function object as defined in Metadata Decorator Functions.</li><li>Set the [[MetadataKey]] internal slot of <var>decorator</var> to <var>metadataKey</var>.</li><li>Set the [[MetadataValue]] internal slot of <var>decorator</var> to <var>metadataValue</var>.</li><li>Return <var>decorator</var>.
  1390. </li></ol></emu-alg>
  1391. </emu-clause>
  1392. <emu-clause id="reflect.definemetadata">
  1393. <h1><span class="secnum">4.1.3</span>Reflect.defineMetadata ( metadataKey, metadataValue, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.definemetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1394. <p>When the <code>defineMetadata</code> function is called with arguments <var>metadataKey</var>, <var>metadataValue</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1395. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[DefineMetadata]](<var>metadataKey</var>, <var>metadataValue</var>, <var>propertyKey</var>).
  1396. </li></ol></emu-alg>
  1397. </emu-clause>
  1398. <emu-clause id="reflect.hasmetadata">
  1399. <h1><span class="secnum">4.1.4</span>Reflect.hasMetadata ( metadataKey, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.hasmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1400. <p>When the <code>hasMetadata</code> function is called with arguments <var>metadataKey</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1401. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[HasMetadata]](<var>metadataKey</var>, <var>propertyKey</var>).
  1402. </li></ol></emu-alg>
  1403. </emu-clause>
  1404. <emu-clause id="reflect.hasownmetadata">
  1405. <h1><span class="secnum">4.1.5</span>Reflect.hasOwnMetadata ( metadataKey, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.hasownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1406. <p>When the <code>hasOwnMetadata</code> function is called with arguments <var>metadataKey</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1407. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[HasOwn]](<var>metadataKey</var>, <var>propertyKey</var>).
  1408. </li></ol></emu-alg>
  1409. </emu-clause>
  1410. <emu-clause id="reflect.getmetadata">
  1411. <h1><span class="secnum">4.1.6</span>Reflect.getMetadata ( metadataKey, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.getmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1412. <p>When the <code>getMetadata</code> function is called with arguments <var>metadataKey</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1413. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[GetMetadata]](<var>metadataKey</var>, <var>propertyKey</var>).
  1414. </li></ol></emu-alg>
  1415. </emu-clause>
  1416. <emu-clause id="reflect.getownmetadata">
  1417. <h1><span class="secnum">4.1.7</span>Reflect.getOwnMetadata ( metadataKey, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.getownmetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1418. <p>When the <code>getOwnMetadata</code> function is called with arguments <var>metadataKey</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1419. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[GetOwnMetadata]](<var>metadataKey</var>, <var>propertyKey</var>).
  1420. </li></ol></emu-alg>
  1421. </emu-clause>
  1422. <emu-clause id="reflect.getmetadatakeys">
  1423. <h1><span class="secnum">4.1.8</span>Reflect.getMetadataKeys ( target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.getmetadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1424. <p>When the <code>getMetadataKeys</code> function is called with arguments <var>target</var> and <var>propertyKey</var>, the following steps are taken:</p>
  1425. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[GetMetadataKeys]](<var>propertyKey</var>).
  1426. </li></ol></emu-alg>
  1427. </emu-clause>
  1428. <emu-clause id="reflect.getownmetadatakeys">
  1429. <h1><span class="secnum">4.1.9</span>Reflect.getOwnMetadataKeys ( target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.getownmetadatakeys">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1430. <p>When the <code>getOwnMetadataKeys</code> function is called with arguments <var>target</var> and <var>propertyKey</var>, the following steps are taken:</p>
  1431. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[GetOwnMetadataKeys]](<var>propertyKey</var>).
  1432. </li></ol></emu-alg>
  1433. </emu-clause>
  1434. <emu-clause id="reflect.deletemetadata">
  1435. <h1><span class="secnum">4.1.10</span>Reflect.deleteMetadata ( metadataKey, target [, propertyKey] )<span class="utils"><span class="anchor"><a href="#reflect.deletemetadata">link</a></span><span class="anchor"><a href="#" class="utils-pin">pin</a></span></span></h1>
  1436. <p>When the <code>deleteMetadata</code> function is called with arguments <var>metadataKey</var>, <var>target</var>, and <var>propertyKey</var>, the following steps are taken:</p>
  1437. <emu-alg><ol><li>If <emu-xref aoid="Type"><a href="https://tc39.github.io/ecma262/#sec-ecmascript-data-types-and-values">Type</a></emu-xref>(<var>target</var>) is not Object, throw a <emu-val>TypeError</emu-val> exception.</li><li>Return ? <var>target</var>.[[DeleteMetadata]](<var>metadataKey</var>, <var>propertyKey</var>).
  1438. </li></ol></emu-alg>
  1439. </emu-clause>
  1440. </emu-clause>
  1441. </emu-clause></div></body>