1"""
2 pygments.lexers.jsx
3 ~~~~~~~~~~~~~~~~~~~
4
5 Lexers for JSX (React) and TSX (TypeScript flavor).
6
7 :copyright: Copyright 2006-2025 by the Pygments team, see AUTHORS.
8 :license: BSD, see LICENSE for details.
9"""
10
11import re
12
13from pygments.lexer import bygroups, default, include, inherit
14from pygments.lexers.javascript import JavascriptLexer, TypeScriptLexer
15from pygments.token import Name, Operator, Punctuation, String, Text, \
16 Whitespace
17
18__all__ = ['JsxLexer', 'TsxLexer']
19
20_JSX_RULES = {
21 "jsx": [
22 (r"</?>", Punctuation), # JSXFragment <>|</>
23 (r"(<)(\w+)(\.?)", bygroups(Punctuation, Name.Tag, Punctuation), "tag"),
24 (
25 r"(</)(\w+)(>)",
26 bygroups(Punctuation, Name.Tag, Punctuation),
27 ),
28 (
29 r"(</)(\w+)",
30 bygroups(Punctuation, Name.Tag),
31 "fragment",
32 ), # Same for React.Context
33 ],
34 "tag": [
35 (r"\s+", Whitespace),
36 (r"([\w-]+)(\s*)(=)(\s*)", bygroups(Name.Attribute, Whitespace, Operator, Whitespace), "attr"),
37 (r"[{}]+", Punctuation),
38 (r"[\w\.]+", Name.Attribute),
39 (r"(/?)(\s*)(>)", bygroups(Punctuation, Text, Punctuation), "#pop"),
40 ],
41 "fragment": [
42 (r"(.)(\w+)", bygroups(Punctuation, Name.Attribute)),
43 (r"(>)", bygroups(Punctuation), "#pop"),
44 ],
45 "attr": [
46 (r"\{", Punctuation, "expression"),
47 (r'".*?"', String, "#pop"),
48 (r"'.*?'", String, "#pop"),
49 default("#pop"),
50 ],
51 "expression": [
52 (r"\{", Punctuation, "#push"),
53 (r"\}", Punctuation, "#pop"),
54 include("root"),
55 ],
56}
57
58
59class JsxLexer(JavascriptLexer):
60 """For JavaScript Syntax Extension (JSX).
61 """
62
63 name = "JSX"
64 aliases = ["jsx", "react"]
65 filenames = ["*.jsx", "*.react"]
66 mimetypes = ["text/jsx", "text/typescript-jsx"]
67 url = "https://facebook.github.io/jsx/"
68 version_added = '2.17'
69
70 flags = re.MULTILINE | re.DOTALL
71
72 # Use same tokens as `JavascriptLexer`, but with tags and attributes support
73 tokens = {
74 "root": [
75 include("jsx"),
76 inherit,
77 ],
78 **_JSX_RULES}
79
80
81class TsxLexer(TypeScriptLexer):
82 """For TypeScript with embedded JSX
83 """
84
85 name = "TSX"
86 aliases = ["tsx"]
87 filenames = ["*.tsx"]
88 mimetypes = ["text/typescript-tsx"]
89 url = "https://www.typescriptlang.org/docs/handbook/jsx.html"
90 version_added = '2.19'
91
92 flags = re.MULTILINE | re.DOTALL
93
94 # Use same tokens as `TypescriptLexer`, but with tags and attributes support
95 tokens = {
96 "root": [
97 include("jsx"),
98 inherit,
99 ],
100 **_JSX_RULES}