|
| 1 | +import { describe, expect, it } from "vitest"; |
| 2 | +import { injectPreviewVariables } from "./previewVariables"; |
| 3 | + |
| 4 | +const SCRIPT = '<script data-hf-preview-variables>window.__hfVariables={"a":1};</script>'; |
| 5 | + |
| 6 | +describe("injectPreviewVariables", () => { |
| 7 | + it.each([ |
| 8 | + [ |
| 9 | + "<!doctype html><html><head>x</head></html>", |
| 10 | + "<!doctype html><html><head>", |
| 11 | + "x</head></html>", |
| 12 | + ], |
| 13 | + [ |
| 14 | + "<!DOCTYPE html><HTML lang='en'><HEAD id='h'>x", |
| 15 | + "<!DOCTYPE html><HTML lang='en'><HEAD id='h'>", |
| 16 | + "x", |
| 17 | + ], |
| 18 | + ["<!doctype html><html lang='en'>x", "<!doctype html><html lang='en'>", "x"], |
| 19 | + [" \n<!DOCTYPE html>x", " \n<!DOCTYPE html>", "x"], |
| 20 | + ["fragment", "", "fragment"], |
| 21 | + ["x<!doctype html>y", "", "x<!doctype html>y"], |
| 22 | + ["<headless>x", "<headless>", "x"], |
| 23 | + ["<head attr='>'>x", "<head attr='>", "'>x"], |
| 24 | + ["<html><head", "<html>", "<head"], |
| 25 | + ["<head<head>x", "<head<head>", "x"], |
| 26 | + ])("preserves insertion boundaries (case %#)", (html, before, after) => { |
| 27 | + expect(injectPreviewVariables(html, { a: 1 })).toBe(before + SCRIPT + after); |
| 28 | + }); |
| 29 | + |
| 30 | + it.each(["<head", "<html"])("handles repeated unterminated %s prefixes", (prefix) => { |
| 31 | + const malformed = prefix.repeat(20_000); |
| 32 | + expect(injectPreviewVariables(malformed, { a: 1 })).toBe(SCRIPT + malformed); |
| 33 | + expect(injectPreviewVariables(malformed + ">tail", { a: 1 })).toBe( |
| 34 | + malformed + ">" + SCRIPT + "tail", |
| 35 | + ); |
| 36 | + }); |
| 37 | + |
| 38 | + it("escapes script-breaking input before inserting it", () => { |
| 39 | + expect(injectPreviewVariables("<head>", { a: "</script>" })).toBe( |
| 40 | + '<head><script data-hf-preview-variables>window.__hfVariables={"a":"\\u003c/script>"};</script>', |
| 41 | + ); |
| 42 | + }); |
| 43 | +}); |
0 commit comments