Skip to content

v1.3.0

Latest

Choose a tag to compare

@eddyloewen eddyloewen released this 28 Oct 13:32
· 1 commit to main since this release

ADDED

  • renderer benchmark in benchmark/: npm run bench measures render() headless on a js-framework-benchmark style table with that benchmark's operation set plus hydration, npm run bench:compare measures main right after it on the same machine and flags deviations, --base <ref> compares against any commit, --micro includes the part binding strategies. Every operation has a post-condition on the DOM, a measurement whose post-condition fails is reported as invalid. See benchmark/README.md.
  • the benchmark runs on every pull request, measures the base commit in the same job and posts the report as a sticky comment on the pull request. Tests and benchmark run for pull requests against any branch, not only main.
  • examples/showcase/ walks through every documented feature, one section per docs chapter. examples/hydration/ plays hydration through with a mutation log: server markup, hydration and the updates afterwards. examples/index.html links all example pages.

FIXED

  • #168 hydrated templates bind their parts to the server rendered DOM. Updates after hydration reach attributes, text, child nodes and lists. The first client values go through the normal update, server rendered templates, lists, text nodes and attributes that match are left untouched.
  • #115 hydration does not depend on the whitespace around the markers anymore.
  • arrays are synced by walking the live DOM instead of an index snapshot: hydrated templates survive other items the server rendered around them, array items whose server markers do not match are rendered client side, DOM nodes in arrays can be reordered, and list updates got considerably faster.
  • a nested template at the root of a template no longer confuses the marker lookup (PartMarkers.createFromStartNode is nesting aware)
  • #172 arrays nested in an array are rendered flat, like the server renders them, client side and on hydration
  • #173 functions as array items are resolved completely, a function that returns a template or another function works like a function as a single value
  • #157 an array item that switches to a different template, or between a text and a template, is rendered fresh at its index, also after the array shrank and grew again. null and undefined items of an array render nothing, like on the server
  • #167 toString() leaves out an attribute whose value is null or undefined, like the DOM renderer removes it. An attribute with several interpolations keeps writing every value as text
  • #169 toString() writes a camelCase property binding as the dash-case attribute that maps back to the property on upgrade, .sliderOptions becomes slider-options
  • #163 an attribute whose name starts with "on" is written as an attribute when its value is not a function, so on="${state}" or once="${flag}" work on an element. A function is the "old school" event listener, client side and in toString()
  • #174 a declarative shadow root (<template shadowrootmode>) gets the element styles and the global styles adopted on the first render and follows global style changes
  • a global style that is added in the same mutation batch as other DOM changes is adopted, the global styles store looks at every record of a batch
  • #121 the custom directive example in the templates docs is a Directive class wrapped with defineDirective(), a plain function does not work at that position

CHANGED

  • parts are bound by walking the comment markers with a TreeWalker instead of precomputed node paths, for client renders and hydration alike. Part construction no longer renders, values only flow through update(), hydration is the first update with a hydrate flag. This removes the double diffing on first render.
  • TemplateResult.parseParts() returns the part descriptors without path
  • ?attribute bindings write name="" for true also when the attribute is present with another value, for example a reflected name="false" in server rendered markup, and remove the attribute for false and the string 'false'
  • server rendered markers that do not match the template are reported with console.warn and the template is rendered client side instead

What's Changed

  • chore(benchmark): renderer benchmark with headless run, report and PR comment by @eddyloewen in #170
  • fix(hydration): bind parts to the live DOM via comment markers by @eddyloewen in #171
  • fix(renderer): array items get the same treatment as a single value by @eddyloewen in #176
  • fix(toString): null attribute values are left out, camelCase property bindings become dash-case attributes by @eddyloewen in #177
  • fix(renderer): an attribute that starts with "on" is only an event listener when the value is a function by @eddyloewen in #178
  • fix(styles): adopt element and global styles into a declarative shadow root by @eddyloewen in #179
  • docs(templates): custom directives are Directive classes wrapped with defineDirective() by @eddyloewen in #180
  • chore(ejs): ignore the .claude directory by @eddyloewen in #182
  • chore(ejs): bump version to 1.3.0 by @eddyloewen in #181

Full Changelog: v1.2.12...v1.3.0