Skip to content

Commit 27a9c94

Browse files
authored
Make Jsx.element a private empty record to avoid unnecessary Primitive_option.some (#7450)
* Update react bindings in tests * Rename jsx preserve test to group jsx tests together * Add test for optional props * Make Jsx.element a private empty record to avoid unnecessary Primitive_option.some * Analysis test output change * Naming in test * CHANGELOG
1 parent 6e7f3d3 commit 27a9c94

16 files changed

+628
-2840
lines changed

CHANGELOG.md

+4
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,10 @@
3939

4040
- AST: Add bar location to `case`. https://github.com/rescript-lang/rescript/pull/7407
4141

42+
#### :nail_care: Polish
43+
44+
- Make `Jsx.element` a private empty record to avoid unnecessary `Primitive_option.some`. https://github.com/rescript-lang/rescript/pull/7450
45+
4246
# 12.0.0-alpha.12
4347

4448
#### :bug: Bug fix

runtime/Jsx.res

+4-1
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,10 @@
2222
* along with this program; if not, write to the Free Software
2323
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
2424

25-
type element
25+
// Define this as a private empty record so that the compiler does not
26+
// unnecessarily add `Primitive_option.some` calls for optional props.
27+
type element = private {}
28+
2629
type ref
2730

2831
@val external null: element = "null"

scripts/test.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ if (mochaTest) {
9292
// I can't run because Mocha doesn't support jsx.
9393
// We also want to keep the output as is.
9494
"--ignore",
95-
"tests/tests/src/preserve_jsx_test.mjs",
95+
"tests/tests/src/jsx_preserve_test.mjs",
9696
],
9797
{
9898
cwd: projectDir,

tests/analysis_tests/tests/src/expected/Completion.res.txt

+1-1
Large diffs are not rendered by default.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// Generated by ReScript, PLEASE EDIT WITH CARE
2+
3+
import * as JsxRuntime from "react/jsx-runtime";
4+
5+
function Jsx_optional_props_test$ComponentWithOptionalProps(props) {
6+
return null;
7+
}
8+
9+
let ComponentWithOptionalProps = {
10+
make: Jsx_optional_props_test$ComponentWithOptionalProps
11+
};
12+
13+
let _element = JsxRuntime.jsx(Jsx_optional_props_test$ComponentWithOptionalProps, {
14+
i: 1,
15+
s: "test",
16+
element: JsxRuntime.jsx("div", {})
17+
});
18+
19+
export {
20+
ComponentWithOptionalProps,
21+
_element,
22+
}
23+
/* _element Not a pure module */
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
@@config({flags: ["-bs-jsx", "4"]})
2+
3+
module ComponentWithOptionalProps = {
4+
@react.component
5+
let make = (
6+
~i as _: option<int>=?,
7+
~s as _: option<string>=?,
8+
~element as _: option<React.element>=?,
9+
) => React.null
10+
}
11+
12+
let _element = <ComponentWithOptionalProps i=1 s="test" element={<div />} />

tests/tests/src/preserve_jsx_test.mjs renamed to tests/tests/src/jsx_preserve_test.mjs

+26-17
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,13 @@
11
// Generated by ReScript, PLEASE EDIT WITH CARE
22

3-
import * as Primitive_option from "rescript/lib/es6/Primitive_option.js";
43
import * as JsxRuntime from "react/jsx-runtime";
54

6-
let React = {};
7-
8-
let ReactDOM = {};
9-
10-
function Preserve_jsx_test$Icon(props) {
5+
function Jsx_preserve_test$Icon(props) {
116
return <strong />;
127
}
138

149
let Icon = {
15-
make: Preserve_jsx_test$Icon
10+
make: Jsx_preserve_test$Icon
1611
};
1712

1813
let _single_element_child = <div>
@@ -25,11 +20,11 @@ let _multiple_element_children = <div>
2520
<h1>
2621
{"Hello, world!"}
2722
</h1>
28-
<Preserve_jsx_test$Icon />
23+
<Jsx_preserve_test$Icon />
2924
</div>;
3025

3126
let _single_element_fragment = <>
32-
{Primitive_option.some(<input />)}
27+
{<input />}
3328
</>;
3429

3530
let _multiple_element_fragment = <>
@@ -134,33 +129,33 @@ function QueryClientProvider(props) { return props.children }
134129

135130
let A = {};
136131

137-
function Preserve_jsx_test$B(props) {
132+
function Jsx_preserve_test$B(props) {
138133
return <p>
139134
{"Hello, world!"}
140135
</p>;
141136
}
142137

143138
let B = {
144-
make: Preserve_jsx_test$B
139+
make: Jsx_preserve_test$B
145140
};
146141

147142
let _external_component_with_children = <QueryClientProvider>
148143
<strong />
149-
<Preserve_jsx_test$B />
144+
<Jsx_preserve_test$B />
150145
</QueryClientProvider>;
151146

152-
function Preserve_jsx_test$MyWeirdComponent(props) {
147+
function Jsx_preserve_test$MyWeirdComponent(props) {
153148
return <p>
154149
{"foo"}
155150
{props["\\\"MyWeirdProp\""]}
156151
</p>;
157152
}
158153

159154
let MyWeirdComponent = {
160-
make: Preserve_jsx_test$MyWeirdComponent
155+
make: Jsx_preserve_test$MyWeirdComponent
161156
};
162157

163-
let _escaped_jsx_prop = <Preserve_jsx_test$MyWeirdComponent
158+
let _escaped_jsx_prop = <Jsx_preserve_test$MyWeirdComponent
164159
MyWeirdProp="bar"
165160
/>;
166161

@@ -194,9 +189,21 @@ let _large_component = <div
194189
</p>
195190
</div>;
196191

192+
function Jsx_preserve_test$ComponentWithOptionalProps(props) {
193+
return null;
194+
}
195+
196+
let ComponentWithOptionalProps = {
197+
make: Jsx_preserve_test$ComponentWithOptionalProps
198+
};
199+
200+
let _optional_props = <Jsx_preserve_test$ComponentWithOptionalProps
201+
i={1}
202+
s="test"
203+
element={<div />}
204+
/>;
205+
197206
export {
198-
React,
199-
ReactDOM,
200207
Icon,
201208
_single_element_child,
202209
_multiple_element_children,
@@ -219,5 +226,7 @@ export {
219226
MyWeirdComponent,
220227
_escaped_jsx_prop,
221228
_large_component,
229+
ComponentWithOptionalProps,
230+
_optional_props,
222231
}
223232
/* _single_element_child Not a pure module */

tests/tests/src/preserve_jsx_test.res renamed to tests/tests/src/jsx_preserve_test.res

+11-64
Original file line numberDiff line numberDiff line change
@@ -2,70 +2,6 @@
22
flags: ["-bs-jsx", "4", "-bs-jsx-preserve"],
33
})
44

5-
module React = {
6-
type element = Jsx.element
7-
8-
@val external null: element = "null"
9-
10-
external float: float => element = "%identity"
11-
external int: int => element = "%identity"
12-
external string: string => element = "%identity"
13-
14-
external array: array<element> => element = "%identity"
15-
16-
type componentLike<'props, 'return> = Jsx.componentLike<'props, 'return>
17-
18-
type component<'props> = Jsx.component<'props>
19-
20-
external component: componentLike<'props, element> => component<'props> = "%identity"
21-
22-
@module("react")
23-
external createElement: (component<'props>, 'props) => element = "createElement"
24-
25-
@module("react")
26-
external cloneElement: (element, 'props) => element = "cloneElement"
27-
28-
@module("react")
29-
external isValidElement: 'a => bool = "isValidElement"
30-
31-
@variadic @module("react")
32-
external createElementVariadic: (component<'props>, 'props, array<element>) => element =
33-
"createElement"
34-
35-
@module("react/jsx-runtime")
36-
external jsx: (component<'props>, 'props) => element = "jsx"
37-
38-
@module("react/jsx-runtime")
39-
external jsxKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsx"
40-
41-
@module("react/jsx-runtime")
42-
external jsxs: (component<'props>, 'props) => element = "jsxs"
43-
44-
@module("react/jsx-runtime")
45-
external jsxsKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsxs"
46-
47-
type fragmentProps = {children?: element}
48-
49-
@module("react/jsx-runtime") external jsxFragment: component<fragmentProps> = "Fragment"
50-
}
51-
52-
module ReactDOM = {
53-
external someElement: React.element => option<React.element> = "%identity"
54-
55-
@module("react/jsx-runtime")
56-
external jsx: (string, JsxDOM.domProps) => Jsx.element = "jsx"
57-
58-
@module("react/jsx-runtime")
59-
external jsxKeyed: (string, JsxDOM.domProps, ~key: string=?, @ignore unit) => Jsx.element = "jsx"
60-
61-
@module("react/jsx-runtime")
62-
external jsxs: (string, JsxDOM.domProps) => Jsx.element = "jsxs"
63-
64-
@module("react/jsx-runtime")
65-
external jsxsKeyed: (string, JsxDOM.domProps, ~key: string=?, @ignore unit) => Jsx.element =
66-
"jsxs"
67-
}
68-
695
module Icon = {
706
@react.component
717
let make = () => {
@@ -179,3 +115,14 @@ let _large_component =
179115
</strong>
180116
<p> {React.int(5)} </p>
181117
</div>
118+
119+
module ComponentWithOptionalProps = {
120+
@react.component
121+
let make = (
122+
~i as _: option<int>=?,
123+
~s as _: option<string>=?,
124+
~element as _: option<React.element>=?,
125+
) => React.null
126+
}
127+
128+
let _optional_props = <ComponentWithOptionalProps i=1 s="test" element={<div />} />

tests/tests/src/react.mjs

+15-4
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,32 @@
11
// Generated by ReScript, PLEASE EDIT WITH CARE
22

3-
4-
let Ref = {};
3+
import * as React from "react";
54

65
let Children = {};
76

87
let Context = {};
98

109
let Fragment = {};
1110

11+
let StrictMode = {};
12+
1213
let Suspense = {};
1314

15+
function lazy_(load) {
16+
return React.lazy(async () => ({
17+
default: await load()
18+
}));
19+
}
20+
21+
let Uncurried = {};
22+
1423
export {
15-
Ref,
1624
Children,
1725
Context,
1826
Fragment,
27+
StrictMode,
1928
Suspense,
29+
lazy_,
30+
Uncurried,
2031
}
21-
/* No side effect */
32+
/* react Not a pure module */

0 commit comments

Comments
 (0)