All files / src/internal/client/dom/blocks html.js

100% Statements 90/90
96.29% Branches 26/27
100% Functions 1/1
100% Lines 84/84

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 852x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 94x 94x 94x 94x 94x 94x 94x 94x 160x 160x 160x 64x 64x 64x 160x 160x 158x 158x 158x 45x 45x 45x 45x 45x 94x 45x 50x 50x 50x 45x 45x 1x 1x 1x 44x 44x 44x 44x 44x 113x 113x 158x 99x 113x 113x 113x 113x 113x 113x 158x 15x 15x 113x 113x 113x 113x 113x 113x 158x 15x 19x 19x 158x 98x 98x 158x 94x 94x  
/** @import { Effect, TemplateNode } from '#client' */
import { HYDRATION_ERROR } from '../../../../constants.js';
import { block, branch, destroy_effect } from '../../reactivity/effects.js';
import { hydrate_next, hydrate_node, hydrating, set_hydrate_node } from '../hydration.js';
import { create_fragment_from_html } from '../reconciler.js';
import { assign_nodes } from '../template.js';
import * as w from '../../warnings.js';
 
/**
 * @param {Element | Text | Comment} node
 * @param {() => string} get_value
 * @param {boolean} svg
 * @param {boolean} mathml
 * @returns {void}
 */
export function html(node, get_value, svg, mathml) {
	var anchor = node;
 
	var value = '';
 
	/** @type {Effect | null} */
	var effect;
 
	block(() => {
		if (value === (value = get_value())) return;
 
		if (effect) {
			destroy_effect(effect);
			effect = null;
		}
 
		if (value === '') return;
 
		effect = branch(() => {
			if (hydrating) {
				var next = hydrate_next();
				var last = next;
 
				while (
					next !== null &&
					(next.nodeType !== 8 || /** @type {Comment} */ (next).data !== '')
				) {
					last = next;
					next = /** @type {TemplateNode} */ (next.nextSibling);
				}
 
				if (next === null) {
					w.hydration_mismatch();
					throw HYDRATION_ERROR;
				}
 
				assign_nodes(hydrate_node, last);
				anchor = set_hydrate_node(next);
				return;
			}
 
			var html = value + '';
			if (svg) html = `<svg>${html}</svg>`;
			else if (mathml) html = `<math>${html}</math>`;
 
			// Don't use create_fragment_with_script_from_html here because that would mean script tags are executed.
			// @html is basically `.innerHTML = ...` and that doesn't execute scripts either due to security reasons.
			/** @type {DocumentFragment | Element} */
			var node = create_fragment_from_html(html);
 
			if (svg || mathml) {
				node = /** @type {Element} */ (node.firstChild);
			}
 
			assign_nodes(
				/** @type {TemplateNode} */ (node.firstChild),
				/** @type {TemplateNode} */ (node.lastChild)
			);
 
			if (svg || mathml) {
				while (node.firstChild) {
					anchor.before(node.firstChild);
				}
			} else {
				anchor.before(node);
			}
		});
	});
}