{
  "$comment": "Unhappy Paths, Issue 01 test fixtures. Expected counts: graphemes via Intl.Segmenter (extended grapheme clusters, UAX #29), code points via Array.from, utf16 via String#length, utf8 via TextEncoder.",
  "counts": [
    {
      "id": "ascii",
      "label": "Plain ASCII",
      "text": "hello",
      "escaped": "hello",
      "expected": {
        "graphemes": 5,
        "codePoints": 5,
        "utf16": 5,
        "utf8": 5
      }
    },
    {
      "id": "precomposed",
      "label": "é, precomposed (NFC)",
      "text": "é",
      "escaped": "\\u00E9",
      "expected": {
        "graphemes": 1,
        "codePoints": 1,
        "utf16": 1,
        "utf8": 2
      }
    },
    {
      "id": "decomposed",
      "label": "é, decomposed (NFD)",
      "text": "é",
      "escaped": "e\\u0301",
      "expected": {
        "graphemes": 1,
        "codePoints": 2,
        "utf16": 2,
        "utf8": 3
      },
      "note": "Looks identical to the previous row; compares unequal unless both are normalized."
    },
    {
      "id": "arabic-harakat",
      "label": "Arabic word with diacritics",
      "text": "مَدْرَسَة",
      "escaped": "\\u0645\\u064E\\u062F\\u0652\\u0631\\u064E\\u0633\\u064E\\u0629",
      "expected": {
        "graphemes": 5,
        "codePoints": 9,
        "utf16": 9,
        "utf8": 18
      }
    },
    {
      "id": "mixed",
      "label": "Arabic, English and emoji",
      "text": "مرحبًا Sara 👋🏽",
      "escaped": "\\u0645\\u0631\\u062D\\u0628\\u064B\\u0627 Sara \\u{1F44B}\\u{1F3FD}",
      "expected": {
        "graphemes": 12,
        "codePoints": 14,
        "utf16": 16,
        "utf8": 26
      }
    },
    {
      "id": "emoji",
      "label": "Single emoji",
      "text": "🌍",
      "escaped": "\\u{1F30D}",
      "expected": {
        "graphemes": 1,
        "codePoints": 1,
        "utf16": 2,
        "utf8": 4
      }
    },
    {
      "id": "skin-tone",
      "label": "Emoji with skin tone modifier",
      "text": "👋🏽",
      "escaped": "\\u{1F44B}\\u{1F3FD}",
      "expected": {
        "graphemes": 1,
        "codePoints": 2,
        "utf16": 4,
        "utf8": 8
      }
    },
    {
      "id": "family",
      "label": "Family, ZWJ sequence",
      "text": "👨‍👩‍👧‍👦",
      "escaped": "\\u{1F468}\\u200D\\u{1F469}\\u200D\\u{1F467}\\u200D\\u{1F466}",
      "expected": {
        "graphemes": 1,
        "codePoints": 7,
        "utf16": 11,
        "utf8": 25
      },
      "note": "Drawn as one glyph only where the font supports the sequence; otherwise as several people side by side."
    },
    {
      "id": "flag",
      "label": "Flag (regional indicators J + P)",
      "text": "🇯🇵",
      "escaped": "\\u{1F1EF}\\u{1F1F5}",
      "expected": {
        "graphemes": 1,
        "codePoints": 2,
        "utf16": 4,
        "utf8": 8
      }
    },
    {
      "id": "keycap",
      "label": "Keycap digit one",
      "text": "1️⃣",
      "escaped": "1\\uFE0F\\u20E3",
      "expected": {
        "graphemes": 1,
        "codePoints": 3,
        "utf16": 3,
        "utf8": 7
      }
    },
    {
      "id": "zwsp",
      "label": "Text ending in a zero width space",
      "text": "admin​",
      "escaped": "admin\\u200B",
      "expected": {
        "graphemes": 6,
        "codePoints": 6,
        "utf16": 6,
        "utf8": 8
      },
      "note": "Renders exactly like \"admin\"."
    },
    {
      "id": "crlf",
      "label": "Windows line ending between letters",
      "text": "a\r\nb",
      "escaped": "a\\r\\nb",
      "expected": {
        "graphemes": 3,
        "codePoints": 4,
        "utf16": 4,
        "utf8": 4
      },
      "note": "CR LF is a single grapheme cluster."
    },
    {
      "id": "empty",
      "label": "Empty string",
      "text": "",
      "escaped": "",
      "expected": {
        "graphemes": 0,
        "codePoints": 0,
        "utf16": 0,
        "utf8": 0
      }
    }
  ],
  "direction": [
    {
      "id": "phone-in-arabic",
      "label": "Phone number inside Arabic",
      "text": "اتصل بنا على +44 20 7946 0123 من الأحد إلى الخميس.",
      "escaped": "\\u0627\\u062A\\u0635\\u0644 \\u0628\\u0646\\u0627 \\u0639\\u0644\\u0649 +44 20 7946 0123 \\u0645\\u0646 \\u0627\\u0644\\u0623\\u062D\\u062F \\u0625\\u0644\\u0649 \\u0627\\u0644\\u062E\\u0645\\u064A\\u0633.",
      "check": "The phone number reads +44 20 7946 0123, left to right, as one unit."
    },
    {
      "id": "sku-digits-first",
      "label": "Identifier starting with digits",
      "text": "رمز المنتج 2047-KB-NL متوفر حاليًا.",
      "escaped": "\\u0631\\u0645\\u0632 \\u0627\\u0644\\u0645\\u0646\\u062A\\u062C 2047-KB-NL \\u0645\\u062A\\u0648\\u0641\\u0631 \\u062D\\u0627\\u0644\\u064A\\u064B\\u0627.",
      "check": "The identifier is displayed as 2047-KB-NL, not split around the Arabic text."
    },
    {
      "id": "url-trailing-slash",
      "label": "URL ending in a slash",
      "text": "زوروا https://example.com/ar/ للمزيد من المعلومات.",
      "escaped": "\\u0632\\u0648\\u0631\\u0648\\u0627 https://example.com/ar/ \\u0644\\u0644\\u0645\\u0632\\u064A\\u062F \\u0645\\u0646 \\u0627\\u0644\\u0645\\u0639\\u0644\\u0648\\u0645\\u0627\\u062A.",
      "check": "The trailing slash stays at the end of the URL."
    },
    {
      "id": "name-colon-number",
      "label": "Arabic name, colon, number in English text",
      "text": "سارة الخطيب: 3 new messages",
      "escaped": "\\u0633\\u0627\\u0631\\u0629 \\u0627\\u0644\\u062E\\u0637\\u064A\\u0628: 3 new messages",
      "check": "In a left-to-right interface, “: 3” stays after the name, on the right."
    },
    {
      "id": "english-starts-arabic",
      "label": "English sentence that starts with an Arabic name",
      "text": "سارة الخطيب replied to your comment",
      "escaped": "\\u0633\\u0627\\u0631\\u0629 \\u0627\\u0644\\u062E\\u0637\\u064A\\u0628 replied to your comment",
      "check": "In an English interface the sentence is laid out left to right, even though its first strong character is Arabic."
    },
    {
      "id": "arabic-starts-latin",
      "label": "Arabic sentence that starts with an email address",
      "text": "sara@example.com هو بريدي الجديد",
      "escaped": "sara@example.com \\u0647\\u0648 \\u0628\\u0631\\u064A\\u062F\\u064A \\u0627\\u0644\\u062C\\u062F\\u064A\\u062F",
      "check": "In an Arabic interface (or with an explicit dir=\"rtl\") the sentence is right to left, even though it starts with Latin letters."
    },
    {
      "id": "quote-punctuation",
      "label": "English quotation ending in punctuation inside Arabic",
      "text": "كتب المستخدم: Hello, world!",
      "escaped": "\\u0643\\u062A\\u0628 \\u0627\\u0644\\u0645\\u0633\\u062A\\u062E\\u062F\\u0645: Hello, world!",
      "check": "The exclamation mark stays at the end of “Hello, world!”."
    },
    {
      "id": "no-strong",
      "label": "Text without strong characters",
      "text": "+44 (0) 20 7946 0123",
      "escaped": "+44 (0) 20 7946 0123",
      "check": "With dir=\"auto\" this resolves to left to right because there is no strong character; check your UI does not depend on that by accident."
    },
    {
      "id": "rlo-override",
      "label": "Right-to-left override in a file name",
      "text": "invoice‮txt.exe",
      "escaped": "invoice\\u202Etxt.exe",
      "check": "Renders as “invoiceexe.txt” in most contexts. Interfaces that show file names or other untrusted text should make bidi controls visible or remove them."
    },
    {
      "id": "isolates",
      "label": "Text with an explicit isolate (FSI…PDI)",
      "text": "المستخدم ⁨Sara Khatib⁩ متصل",
      "escaped": "\\u0627\\u0644\\u0645\\u0633\\u062A\\u062E\\u062F\\u0645 \\u2068Sara Khatib\\u2069 \\u0645\\u062A\\u0635\\u0644",
      "check": "Isolate controls work where markup is impossible, e.g. in title attributes or notifications. The name stays together."
    }
  ]
}