[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"verticals":3,"article-using-explicit-resource-management":32,"code:ts:true:lri407":230,"code:ts:true:17rwrvt":231,"code:ts:true:xi1goy":232,"code:ts:true:12wc2ou":233,"code:ts:true:rxel7q":234,"code:json:true:1lf98k4":235},[4,20],{"id":5,"slug":6,"name":7,"tagline":8,"description":9,"accentFrom":10,"accentTo":11,"icon":12,"defaultLocale":13,"locales":14,"features":16,"position":19},"019fe637-3d33-714b-b57f-23e163ffca0c","dev","Web Development","Build. Learn. Ship.","Practical courses, engineering-grade articles and open-source tools for people who ship.","violet-500","cyan-400","◇","en",[13,15],"fa",{"courses":17,"paths":17,"articles":17,"exams":18,"flashcards":18,"packages":17,"community":17,"certificates":17,"teams":17,"commerce":17},true,false,0,{"id":21,"slug":22,"name":23,"tagline":24,"description":25,"accentFrom":26,"accentTo":10,"icon":27,"defaultLocale":13,"locales":28,"features":30,"position":31},"019fe637-3dc2-754c-8657-0f175bfee7c6","lang","Languages","Learn a language the way you learn a codebase.","Structured paths, listening drills and spaced repetition that actually sticks.","amber-400","⌘",[13,15,29],"es",{"courses":17,"paths":17,"articles":18,"exams":18,"flashcards":18,"packages":18,"community":17,"certificates":18,"teams":18,"commerce":17},2,{"id":33,"slug":34,"title":35,"subtitle":36,"excerpt":37,"coverUrl":38,"locale":13,"readingMinutes":39,"publishedAt":40,"viewCount":41,"likeCount":19,"commentCount":19,"author":42,"vertical":47,"topic":48,"tags":51,"_count":63,"playground":65,"body":67,"bodyMd":212,"seo":213,"translationGroupId":217,"thread":218,"assessments":220,"translations":226,"quiz":228},"019fe660-75da-727d-a751-32f8723b0b38","using-explicit-resource-management","You still write `finally { resource.close() }`. The `using` keyword does it automatically.",null,"The Explicit Resource Management proposal adds a `using` declaration that calls cleanup the moment a scope exits — normal return, early return, or throw. No more try\u002Ffinally boilerplate for timers, event listeners, connections, or any other resource you need to release.","\u002Fmedia\u002Fcovers\u002Fusing-explicit-resource-management.png",4,"2026-07-24T08:33:28.459Z",34,{"id":43,"name":44,"username":45,"avatarUrl":36,"headline":46},"019fe637-3c25-7088-9034-39c9f15dc3c8","Parsa Jiravand","parsa","Frontend engineer · building bestpractic",{"slug":6,"name":7,"accentFrom":10,"accentTo":11},{"slug":49,"name":50},"typescript","TypeScript",[52,54,57,60],{"slug":49,"name":53,"color":36},"Typescript",{"slug":55,"name":56,"color":36},"javascript","Javascript",{"slug":58,"name":59,"color":36},"webdev","Webdev",{"slug":61,"name":62,"color":36},"frontend","Frontend",{"assessments":64},1,{"slug":34,"title":66},"using \u002F explicit resource management — interactive playground",{"blocks":68,"version":64},[69,73,79,82,85,90,93,97,100,103,106,109,112,115,119,122,126,129,132,135,139,142,146,149,153,156,159,162,167,170,173,176,179,182,185,188,191,194,197,200,203],{"id":70,"html":71,"type":72},"b1","\u003Cp>You&#39;ve written this pattern — or something close to it — many times:\u003C\u002Fp>","paragraph",{"id":74,"code":75,"type":76,"language":77,"highlight":78},"b2","const timer = setTimeout(flush, 5000);\ntry {\n  await doWork();\n} finally {\n  clearTimeout(timer);\n}","code","ts",[],{"id":80,"html":81,"type":72},"b3","\u003Cp>The cleanup is real and necessary. But it&#39;s twelve lines away from the allocation, and every time the function grows — another early return, another throw path — you have to remember to extend the \u003Ccode>finally\u003C\u002Fcode> block. Miss one and you&#39;ve leaked a timer.\u003C\u002Fp>",{"id":83,"html":84,"type":72},"b4","\u003Cp>TypeScript 5.2 (and TC39&#39;s Explicit Resource Management proposal) added a \u003Ccode>using\u003C\u002Fcode> declaration that ties cleanup directly to the variable binding. The scope exits → the resource disposes. No \u003Ccode>finally\u003C\u002Fcode> required.\u003C\u002Fp>",{"id":86,"html":87,"text":88,"type":89,"level":31},"b5","What \u003Ccode>using\u003C\u002Fcode> does","What using does","heading",{"id":91,"html":92,"type":72},"b6","\u003Cp>\u003Ccode>using\u003C\u002Fcode> works like \u003Ccode>const\u003C\u002Fcode> with one difference: when the block it was declared in exits — normally, via early return, or via an exception — it calls \u003Ccode>[Symbol.dispose]()\u003C\u002Fcode> on the value automatically.\u003C\u002Fp>",{"id":94,"code":95,"type":76,"language":77,"highlight":96},"b7","class ManagedTimer {\n  #id: ReturnType\u003Ctypeof setTimeout>;\n\n  constructor(fn: () => void, ms: number) {\n    this.#id = setTimeout(fn, ms);\n  }\n\n  [Symbol.dispose]() {\n    clearTimeout(this.#id);\n  }\n}\n\nasync function doWork() {\n  using _timer = new ManagedTimer(flush, 5000);\n  await processItems();\n  \u002F\u002F clearTimeout is called here, regardless of whether\n  \u002F\u002F processItems() returned normally or threw\n}",[],{"id":98,"html":99,"type":72},"b8","\u003Cp>The cleanup is now written at the allocation site. Anyone reading the function sees the timer and its lifetime in the same line. No \u003Ccode>finally\u003C\u002Fcode> block to track, no hidden path that forgets to clean up.\u003C\u002Fp>",{"id":101,"html":102,"type":72},"b9","\u003C!-- playground:start -->",{"id":104,"html":105,"text":105,"type":89,"level":31},"b10","🎮 Try it yourself",{"id":107,"html":108,"type":72},"b11","\u003Cp>\u003Cstrong>\u003Ca href=\"https:\u002F\u002Fdaily-post-dev.netlify.app\u002Fposts\u002F2026-07-24-using-explicit-resource-management\u002Fplayground\u002F\">▶️ Open the interactive playground →\u003C\u002Fa>\u003C\u002Fstrong>\u003C\u002Fp>",{"id":110,"html":111,"type":72},"b12","\u003Cp>\u003Cem>Runs right in your browser — poke at it and watch the concept react live.\u003C\u002Fem>\u003C\u002Fp>",{"id":113,"html":114,"type":72},"b13","\u003C!-- playground:end -->",{"id":116,"html":117,"text":118,"type":89,"level":31},"b14","Async teardown with \u003Ccode>await using\u003C\u002Fcode>","Async teardown with await using",{"id":120,"html":121,"type":72},"b15","\u003Cp>If cleanup is asynchronous — closing a database connection, flushing a write buffer, calling an HTTP endpoint — you need \u003Ccode>await using\u003C\u002Fcode> instead:\u003C\u002Fp>",{"id":123,"code":124,"type":76,"language":77,"highlight":125},"b16","class DbConnection {\n  async [Symbol.asyncDispose]() {\n    await this.pool.end();\n  }\n}\n\nasync function runQuery(sql: string) {\n  await using conn = await openConnection();\n  return conn.execute(sql);\n  \u002F\u002F conn.pool.end() is awaited automatically when this returns\n}",[],{"id":127,"html":128,"type":72},"b17","\u003Cp>\u003Ccode>await using\u003C\u002Fcode> calls \u003Ccode>[Symbol.asyncDispose]()\u003C\u002Fcode> and awaits it before the surrounding \u003Ccode>async\u003C\u002Fcode> function resolves. The caller never sees a half-torn-down resource.\u003C\u002Fp>",{"id":130,"html":131,"text":131,"type":89,"level":31},"b18","Making your own disposables",{"id":133,"html":134,"type":72},"b19","\u003Cp>Any object with \u003Ccode>[Symbol.dispose]()\u003C\u002Fcode> (or \u003Ccode>[Symbol.asyncDispose]()\u003C\u002Fcode>) is a disposable. That includes objects you write yourself, but also wrappers you can add to things you don&#39;t own:\u003C\u002Fp>",{"id":136,"code":137,"type":76,"language":77,"highlight":138},"b20","function managedListener\u003CK extends keyof HTMLElementEventMap>(\n  target: HTMLElement,\n  type: K,\n  handler: (e: HTMLElementEventMap[K]) => void\n): Disposable {\n  target.addEventListener(type, handler);\n  return {\n    [Symbol.dispose]() {\n      target.removeEventListener(type, handler);\n    },\n  };\n}\n\nfunction trackHover(el: HTMLElement) {\n  using _enter = managedListener(el, 'mouseenter', onEnter);\n  using _leave = managedListener(el, 'mouseleave', onLeave);\n  \u002F\u002F both listeners are removed when this scope exits\n}",[],{"id":140,"html":141,"type":72},"b21","\u003Cp>Multiple \u003Ccode>using\u003C\u002Fcode> declarations in the same scope dispose in reverse order — last declared, first cleaned up — which mirrors how stack unwinding works and keeps teardown safe when resources depend on each other.\u003C\u002Fp>",{"id":143,"html":144,"text":145,"type":89,"level":31},"b22","\u003Ccode>DisposableStack\u003C\u002Fcode> for dynamic resource groups","DisposableStack for dynamic resource groups",{"id":147,"html":148,"type":72},"b23","\u003Cp>When the number of resources isn&#39;t known at compile time, \u003Ccode>DisposableStack\u003C\u002Fcode> (and its async counterpart \u003Ccode>AsyncDisposableStack\u003C\u002Fcode>) lets you register them at runtime:\u003C\u002Fp>",{"id":150,"code":151,"type":76,"language":77,"highlight":152},"b24","async function processAll(paths: string[]) {\n  await using stack = new AsyncDisposableStack();\n  const handles = await Promise.all(\n    paths.map(p => stack.use(openFile(p)))\n  );\n  await transformAll(handles);\n  \u002F\u002F every file handle is closed in reverse order here\n}",[],{"id":154,"html":155,"type":72},"b25","\u003Cp>\u003Ccode>stack.use(resource)\u003C\u002Fcode> returns the resource and registers it for disposal. When the stack itself disposes, everything registered to it disposes in reverse order. You get deterministic, ordered cleanup without writing a single \u003Ccode>finally\u003C\u002Fcode>.\u003C\u002Fp>",{"id":157,"html":158,"text":158,"type":89,"level":31},"b26","TypeScript and browser support",{"id":160,"html":161,"type":72},"b27","\u003Cp>TypeScript added \u003Ccode>using\u003C\u002Fcode> and \u003Ccode>await using\u003C\u002Fcode> in \u003Cstrong>version 5.2\u003C\u002Fstrong> (August 2023). To get the types for \u003Ccode>Symbol.dispose\u003C\u002Fcode>, \u003Ccode>Symbol.asyncDispose\u003C\u002Fcode>, \u003Ccode>DisposableStack\u003C\u002Fcode>, and \u003Ccode>AsyncDisposableStack\u003C\u002Fcode>, add \u003Ccode>&quot;ES2026&quot;\u003C\u002Fcode> to the \u003Ccode>lib\u003C\u002Fcode> array in your \u003Ccode>tsconfig.json\u003C\u002Fcode>:\u003C\u002Fp>",{"id":163,"code":164,"type":76,"language":165,"highlight":166},"b28","{\n  \"compilerOptions\": {\n    \"lib\": [\"DOM\", \"ES2026\"],\n    \"target\": \"ES2022\"\n  }\n}","json",[],{"id":168,"html":169,"type":72},"b29","\u003Cp>Note that \u003Ccode>lib\u003C\u002Fcode> controls which \u003Cem>type definitions\u003C\u002Fem> are available. The compiled output still targets whatever \u003Ccode>target\u003C\u002Fcode> is set to — TypeScript will emit try\u002Ffinally for older targets, so the runtime behavior is correct even in environments that don&#39;t natively support \u003Ccode>using\u003C\u002Fcode> yet.\u003C\u002Fp>",{"id":171,"html":172,"type":72},"b30","\u003Cp>Natively, \u003Ccode>using\u003C\u002Fcode> shipped in \u003Cstrong>Chrome 134\u003C\u002Fstrong> (March 2025), \u003Cstrong>Firefox 134\u003C\u002Fstrong>, and \u003Cstrong>Safari 18.2\u003C\u002Fstrong>. Node.js 22 supports it behind a flag; Node.js 24 enables it by default.\u003C\u002Fp>",{"id":174,"html":175,"type":72},"b31","\u003C!-- quiz:start -->",{"id":177,"html":178,"text":178,"type":89,"level":31},"b32","🧠 Test yourself",{"id":180,"html":181,"type":72},"b33","\u003Cp>Think it clicked? \u003Cstrong>\u003Ca href=\"https:\u002F\u002Fdaily-post-dev.netlify.app\u002Fquiz\u002Ftake.html?post=2026-07-24-using-explicit-resource-management\">Take the 6-question quiz →\u003C\u002Fa>\u003C\u002Fstrong>\u003C\u002Fp>",{"id":183,"html":184,"type":72},"b34","\u003Cp>\u003Cem>Instant feedback, a hint on every question, and an explanation for each answer — right or wrong.\u003C\u002Fem>\u003C\u002Fp>",{"id":186,"html":187,"type":72},"b35","\u003C!-- quiz:end -->",{"id":189,"html":190,"text":190,"type":89,"level":31},"b36","The takeaway",{"id":192,"html":193,"type":72},"b37","\u003Cp>Search your codebase for \u003Ccode>finally {\u003C\u002Fcode> blocks. The ones that exist only to release a resource — clear a timeout, remove a listener, close a connection — are candidates for \u003Ccode>using\u003C\u002Fcode>. Each one can move its cleanup from a \u003Ccode>finally\u003C\u002Fcode> block to the line where the resource is allocated, making the lifetime visible at a glance and eliminating a whole class of cleanup bugs.\u003C\u002Fp>",{"id":195,"html":196,"type":72},"b38","\u003Cp>\u003Ccode>using\u003C\u002Fcode> doesn&#39;t replace \u003Ccode>try\u002Fcatch\u003C\u002Fcode> for error handling. It replaces the \u003Ccode>finally\u003C\u002Fcode> that does nothing but clean up. That&#39;s a smaller scope, but it&#39;s the scope you write wrong the most often.\u003C\u002Fp>",{"id":198,"type":199},"b39","divider",{"id":201,"html":202,"type":72},"b40","\u003Cp>\u003Cem>Thanks for reading! Let&#39;s stay connected:\u003C\u002Fem>\u003C\u002Fp>",{"id":204,"type":205,"items":206,"ordered":18},"b41","list",[207,208,209,210,211],"⭐ \u003Cstrong>GitHub\u003C\u002Fstrong> — follow me and star the projects: \u003Ca href=\"https:\u002F\u002Fgithub.com\u002Fparsajiravand\">github.com\u002Fparsajiravand\u003C\u002Fa>","💬 \u003Cstrong>Discord\u003C\u002Fstrong> — join the frontend best-practices community: \u003Ca href=\"https:\u002F\u002Fdiscord.gg\u002Fd9KRhuAwQ\">discord.gg\u002Fd9KRhuAwQ\u003C\u002Fa>","📸 \u003Cstrong>Instagram\u003C\u002Fstrong> — frontend best practices, daily: \u003Ca href=\"https:\u002F\u002Fwww.instagram.com\u002Fbestpractice___\u002F\">@bestpractice___\u003C\u002Fa>","💼 \u003Cstrong>LinkedIn\u003C\u002Fstrong> — \u003Ca href=\"https:\u002F\u002Fwww.linkedin.com\u002Fin\u002Fparsa-jiravand\u002F\">linkedin.com\u002Fin\u002Fparsa-jiravand\u003C\u002Fa>","✉️ \u003Cstrong>Email\u003C\u002Fstrong> (work &amp; contract inquiries): \u003Ca href=\"mailto:bestpractice2026@gmail.com\">bestpractice2026@gmail.com\u003C\u002Fa>","You've written this pattern — or something close to it — many times:\n\n```ts\nconst timer = setTimeout(flush, 5000);\ntry {\n  await doWork();\n} finally {\n  clearTimeout(timer);\n}\n```\n\nThe cleanup is real and necessary. But it's twelve lines away from the allocation, and every time the function grows — another early return, another throw path — you have to remember to extend the `finally` block. Miss one and you've leaked a timer.\n\nTypeScript 5.2 (and TC39's Explicit Resource Management proposal) added a `using` declaration that ties cleanup directly to the variable binding. The scope exits → the resource disposes. No `finally` required.\n\n## What `using` does\n\n`using` works like `const` with one difference: when the block it was declared in exits — normally, via early return, or via an exception — it calls `[Symbol.dispose]()` on the value automatically.\n\n```ts\nclass ManagedTimer {\n  #id: ReturnType\u003Ctypeof setTimeout>;\n\n  constructor(fn: () => void, ms: number) {\n    this.#id = setTimeout(fn, ms);\n  }\n\n  [Symbol.dispose]() {\n    clearTimeout(this.#id);\n  }\n}\n\nasync function doWork() {\n  using _timer = new ManagedTimer(flush, 5000);\n  await processItems();\n  \u002F\u002F clearTimeout is called here, regardless of whether\n  \u002F\u002F processItems() returned normally or threw\n}\n```\n\nThe cleanup is now written at the allocation site. Anyone reading the function sees the timer and its lifetime in the same line. No `finally` block to track, no hidden path that forgets to clean up.\n\n\u003C!-- playground:start -->\n\n## 🎮 Try it yourself\n\n**[▶️ Open the interactive playground →](https:\u002F\u002Fdaily-post-dev.netlify.app\u002Fposts\u002F2026-07-24-using-explicit-resource-management\u002Fplayground\u002F)**\n\n_Runs right in your browser — poke at it and watch the concept react live._\n\n\u003C!-- playground:end -->\n\n## Async teardown with `await using`\n\nIf cleanup is asynchronous — closing a database connection, flushing a write buffer, calling an HTTP endpoint — you need `await using` instead:\n\n```ts\nclass DbConnection {\n  async [Symbol.asyncDispose]() {\n    await this.pool.end();\n  }\n}\n\nasync function runQuery(sql: string) {\n  await using conn = await openConnection();\n  return conn.execute(sql);\n  \u002F\u002F conn.pool.end() is awaited automatically when this returns\n}\n```\n\n`await using` calls `[Symbol.asyncDispose]()` and awaits it before the surrounding `async` function resolves. The caller never sees a half-torn-down resource.\n\n## Making your own disposables\n\nAny object with `[Symbol.dispose]()` (or `[Symbol.asyncDispose]()`) is a disposable. That includes objects you write yourself, but also wrappers you can add to things you don't own:\n\n```ts\nfunction managedListener\u003CK extends keyof HTMLElementEventMap>(\n  target: HTMLElement,\n  type: K,\n  handler: (e: HTMLElementEventMap[K]) => void\n): Disposable {\n  target.addEventListener(type, handler);\n  return {\n    [Symbol.dispose]() {\n      target.removeEventListener(type, handler);\n    },\n  };\n}\n\nfunction trackHover(el: HTMLElement) {\n  using _enter = managedListener(el, 'mouseenter', onEnter);\n  using _leave = managedListener(el, 'mouseleave', onLeave);\n  \u002F\u002F both listeners are removed when this scope exits\n}\n```\n\nMultiple `using` declarations in the same scope dispose in reverse order — last declared, first cleaned up — which mirrors how stack unwinding works and keeps teardown safe when resources depend on each other.\n\n## `DisposableStack` for dynamic resource groups\n\nWhen the number of resources isn't known at compile time, `DisposableStack` (and its async counterpart `AsyncDisposableStack`) lets you register them at runtime:\n\n```ts\nasync function processAll(paths: string[]) {\n  await using stack = new AsyncDisposableStack();\n  const handles = await Promise.all(\n    paths.map(p => stack.use(openFile(p)))\n  );\n  await transformAll(handles);\n  \u002F\u002F every file handle is closed in reverse order here\n}\n```\n\n`stack.use(resource)` returns the resource and registers it for disposal. When the stack itself disposes, everything registered to it disposes in reverse order. You get deterministic, ordered cleanup without writing a single `finally`.\n\n## TypeScript and browser support\n\nTypeScript added `using` and `await using` in **version 5.2** (August 2023). To get the types for `Symbol.dispose`, `Symbol.asyncDispose`, `DisposableStack`, and `AsyncDisposableStack`, add `\"ES2026\"` to the `lib` array in your `tsconfig.json`:\n\n```json\n{\n  \"compilerOptions\": {\n    \"lib\": [\"DOM\", \"ES2026\"],\n    \"target\": \"ES2022\"\n  }\n}\n```\n\nNote that `lib` controls which *type definitions* are available. The compiled output still targets whatever `target` is set to — TypeScript will emit try\u002Ffinally for older targets, so the runtime behavior is correct even in environments that don't natively support `using` yet.\n\nNatively, `using` shipped in **Chrome 134** (March 2025), **Firefox 134**, and **Safari 18.2**. Node.js 22 supports it behind a flag; Node.js 24 enables it by default.\n\n\u003C!-- quiz:start -->\n\n## 🧠 Test yourself\n\nThink it clicked? **[Take the 6-question quiz →](https:\u002F\u002Fdaily-post-dev.netlify.app\u002Fquiz\u002Ftake.html?post=2026-07-24-using-explicit-resource-management)**\n\n_Instant feedback, a hint on every question, and an explanation for each answer — right or wrong._\n\n\u003C!-- quiz:end -->\n\n## The takeaway\n\nSearch your codebase for `finally {` blocks. The ones that exist only to release a resource — clear a timeout, remove a listener, close a connection — are candidates for `using`. Each one can move its cleanup from a `finally` block to the line where the resource is allocated, making the lifetime visible at a glance and eliminating a whole class of cleanup bugs.\n\n`using` doesn't replace `try\u002Fcatch` for error handling. It replaces the `finally` that does nothing but clean up. That's a smaller scope, but it's the scope you write wrong the most often.\n\n---\n\n*Thanks for reading! Let's stay connected:*\n\n- ⭐ **GitHub** — follow me and star the projects: [github.com\u002Fparsajiravand](https:\u002F\u002Fgithub.com\u002Fparsajiravand)\n- 💬 **Discord** — join the frontend best-practices community: [discord.gg\u002Fd9KRhuAwQ](https:\u002F\u002Fdiscord.gg\u002Fd9KRhuAwQ)\n- 📸 **Instagram** — frontend best practices, daily: [@bestpractice___](https:\u002F\u002Fwww.instagram.com\u002Fbestpractice___\u002F)\n- 💼 **LinkedIn** — [linkedin.com\u002Fin\u002Fparsa-jiravand](https:\u002F\u002Fwww.linkedin.com\u002Fin\u002Fparsa-jiravand\u002F)\n- ✉️ **Email** (work & contract inquiries): [bestpractice2026@gmail.com](mailto:bestpractice2026@gmail.com)",{"title":214,"canonical":215,"description":216},"You still write `finally { resource.close() }`. The `using` keyword do","https:\u002F\u002Fbestpractic.org\u002Fblog\u002Fusing-explicit-resource-management","The Explicit Resource Management proposal adds a `using` declaration that calls cleanup the moment a scope exits — normal return, early return, or throw. No more try\u002Ffinally boiler","019fe660-75da-727d-a751-37288647c254",{"id":219,"locked":18},"019fe660-7c8d-7518-95f4-4f6d767f55cd",[221],{"id":222,"slug":34,"title":223,"_count":224},"019fe776-74a5-7729-aa90-9ad15f2ed3a7","Explicit resource management: the using declaration",{"questions":225},6,[227],{"locale":13,"slug":34},{"id":222,"slug":34,"title":223,"_count":229,"questionCount":225},{"questions":225},"\u003Cdiv class=\"shj shj-lang-ts shj-multiline\" data-lang=\"ts\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-kwd\">const\u003C\u002Fspan> timer \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-func\">setTimeout\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>flush\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> \u003Cspan class=\"shj-num\">5000\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n\u003Cspan class=\"shj-kwd\">try\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-func\">doWork\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">finally\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-func\">clearTimeout\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>timer\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>","\u003Cdiv class=\"shj shj-lang-ts shj-multiline\" data-lang=\"ts\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003Cdiv>7\u003C\u002Fdiv>\u003Cdiv>8\u003C\u002Fdiv>\u003Cdiv>9\u003C\u002Fdiv>\u003Cdiv>10\u003C\u002Fdiv>\u003Cdiv>11\u003C\u002Fdiv>\u003Cdiv>12\u003C\u002Fdiv>\u003Cdiv>13\u003C\u002Fdiv>\u003Cdiv>14\u003C\u002Fdiv>\u003Cdiv>15\u003C\u002Fdiv>\u003Cdiv>16\u003C\u002Fdiv>\u003Cdiv>17\u003C\u002Fdiv>\u003Cdiv>18\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-kwd\">class\u003C\u002Fspan> \u003Cspan class=\"shj-class\">ManagedTimer\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  #id\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-class\">ReturnType\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">&lt;\u003C\u002Fspan>\u003Cspan class=\"shj-kwd\">typeof\u003C\u002Fspan> setTimeout\u003Cspan class=\"shj-oper\">&gt;\u003C\u002Fspan>;\n\n  \u003Cspan class=\"shj-kwd\">constructor\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>fn\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">=&gt;\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">void\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> ms\u003Cspan class=\"shj-type\">: number\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n    \u003Cspan class=\"shj-kwd\">this\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>#id \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-func\">setTimeout\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>fn\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> ms\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\n  \u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-class\">Symbol\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>dispose\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n    \u003Cspan class=\"shj-func\">clearTimeout\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-kwd\">this\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>#id\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\n\u003Cspan class=\"shj-kwd\">async\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">function\u003C\u002Fspan> \u003Cspan class=\"shj-func\">doWork\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  using _timer \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">new\u003C\u002Fspan> \u003Cspan class=\"shj-class\">ManagedTimer\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>flush\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> \u003Cspan class=\"shj-num\">5000\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-func\">processItems\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-cmnt\">\u002F\u002F clearTimeout is called here, regardless of whether\n\u003C\u002Fspan>  \u003Cspan class=\"shj-cmnt\">\u002F\u002F processItems() returned normally or threw\n\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>","\u003Cdiv class=\"shj shj-lang-ts shj-multiline\" data-lang=\"ts\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003Cdiv>7\u003C\u002Fdiv>\u003Cdiv>8\u003C\u002Fdiv>\u003Cdiv>9\u003C\u002Fdiv>\u003Cdiv>10\u003C\u002Fdiv>\u003Cdiv>11\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-kwd\">class\u003C\u002Fspan> \u003Cspan class=\"shj-class\">DbConnection\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-kwd\">async\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-class\">Symbol\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>asyncDispose\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n    \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">this\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>pool\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">end\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\n\u003Cspan class=\"shj-kwd\">async\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">function\u003C\u002Fspan> \u003Cspan class=\"shj-func\">runQuery\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>sql\u003Cspan class=\"shj-type\">: string\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> using conn \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-func\">openConnection\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-kwd\">return\u003C\u002Fspan> conn\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">execute\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>sql\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-cmnt\">\u002F\u002F conn.pool.end() is awaited automatically when this returns\n\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>","\u003Cdiv class=\"shj shj-lang-ts shj-multiline\" data-lang=\"ts\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003Cdiv>7\u003C\u002Fdiv>\u003Cdiv>8\u003C\u002Fdiv>\u003Cdiv>9\u003C\u002Fdiv>\u003Cdiv>10\u003C\u002Fdiv>\u003Cdiv>11\u003C\u002Fdiv>\u003Cdiv>12\u003C\u002Fdiv>\u003Cdiv>13\u003C\u002Fdiv>\u003Cdiv>14\u003C\u002Fdiv>\u003Cdiv>15\u003C\u002Fdiv>\u003Cdiv>16\u003C\u002Fdiv>\u003Cdiv>17\u003C\u002Fdiv>\u003Cdiv>18\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-kwd\">function\u003C\u002Fspan> managedListener\u003Cspan class=\"shj-oper\">&lt;\u003C\u002Fspan>\u003Cspan class=\"shj-num\">K\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">extends\u003C\u002Fspan> keyof \u003Cspan class=\"shj-class\">HTMLElementEventMap\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">&gt;\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\n  target\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-class\">HTMLElement\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan>\n  \u003Cspan class=\"shj-kwd\">type\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-num\">K\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan>\n  handler\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>e\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-class\">HTMLElementEventMap\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-num\">K\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">=&gt;\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">void\u003C\u002Fspan>\n\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-class\">Disposable\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  target\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">addEventListener\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-kwd\">type\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> handler\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-kwd\">return\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n    \u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-class\">Symbol\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>dispose\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n      target\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">removeEventListener\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-kwd\">type\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> handler\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n    \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan>\n  \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>;\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\n\u003Cspan class=\"shj-kwd\">function\u003C\u002Fspan> \u003Cspan class=\"shj-func\">trackHover\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>el\u003Cspan class=\"shj-oper\">:\u003C\u002Fspan> \u003Cspan class=\"shj-class\">HTMLElement\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  using _enter \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-func\">managedListener\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>el\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> \u003Cspan class=\"shj-str\">'mouseenter'\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> onEnter\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  using _leave \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-func\">managedListener\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>el\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> \u003Cspan class=\"shj-str\">'mouseleave'\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">,\u003C\u002Fspan> onLeave\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-cmnt\">\u002F\u002F both listeners are removed when this scope exits\n\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>","\u003Cdiv class=\"shj shj-lang-ts shj-multiline\" data-lang=\"ts\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003Cdiv>7\u003C\u002Fdiv>\u003Cdiv>8\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-kwd\">async\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">function\u003C\u002Fspan> \u003Cspan class=\"shj-func\">processAll\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>paths\u003Cspan class=\"shj-type\">: string\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan> \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> using stack \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">new\u003C\u002Fspan> \u003Cspan class=\"shj-class\">AsyncDisposableStack\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-kwd\">const\u003C\u002Fspan> handles \u003Cspan class=\"shj-oper\">=\u003C\u002Fspan> \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-class\">Promise\u003C\u002Fspan>\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">all\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\n    paths\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">map\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>p \u003Cspan class=\"shj-kwd\">=&gt;\u003C\u002Fspan> stack\u003Cspan class=\"shj-oper\">.\u003C\u002Fspan>\u003Cspan class=\"shj-func\">use\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>\u003Cspan class=\"shj-func\">openFile\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>p\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>\n  \u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-kwd\">await\u003C\u002Fspan> \u003Cspan class=\"shj-func\">transformAll\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">(\u003C\u002Fspan>handles\u003Cspan class=\"shj-bracket\">)\u003C\u002Fspan>;\n  \u003Cspan class=\"shj-cmnt\">\u002F\u002F every file handle is closed in reverse order here\n\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>","\u003Cdiv class=\"shj shj-lang-json shj-multiline\" data-lang=\"json\">\u003Cdiv class=\"shj-scroll\">\u003Cdiv class=\"shj-numbers\">\u003Cdiv>1\u003C\u002Fdiv>\u003Cdiv>2\u003C\u002Fdiv>\u003Cdiv>3\u003C\u002Fdiv>\u003Cdiv>4\u003C\u002Fdiv>\u003Cdiv>5\u003C\u002Fdiv>\u003Cdiv>6\u003C\u002Fdiv>\u003C\u002Fdiv>\u003Cdiv class=\"shj-code\">\u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n  \u003Cspan class=\"shj-var\">\"compilerOptions\"\u003C\u002Fspan>: \u003Cspan class=\"shj-bracket\">{\u003C\u002Fspan>\n    \u003Cspan class=\"shj-var\">\"lib\"\u003C\u002Fspan>: \u003Cspan class=\"shj-bracket\">[\u003C\u002Fspan>\u003Cspan class=\"shj-str\">\"DOM\"\u003C\u002Fspan>, \u003Cspan class=\"shj-str\">\"ES2026\"\u003C\u002Fspan>\u003Cspan class=\"shj-bracket\">]\u003C\u002Fspan>,\n    \u003Cspan class=\"shj-var\">\"target\"\u003C\u002Fspan>: \u003Cspan class=\"shj-str\">\"ES2022\"\u003C\u002Fspan>\n  \u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\n\u003Cspan class=\"shj-bracket\">}\u003C\u002Fspan>\u003C\u002Fdiv>\u003C\u002Fdiv>\u003C\u002Fdiv>"]