@react-email/render 0.0.17 → 1.0.0-canary.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -15,7 +15,7 @@ type Options = {
15
15
  htmlToTextOptions?: HtmlToTextOptions;
16
16
  });
17
17
 
18
- declare const render: (component: React.ReactElement, options?: Options) => string;
18
+ declare const render: (component: React.ReactElement, options?: Options) => Promise<string>;
19
19
 
20
20
  declare const renderAsync: (component: React.ReactElement, options?: Options) => Promise<string>;
21
21
 
@@ -15,7 +15,7 @@ type Options = {
15
15
  htmlToTextOptions?: HtmlToTextOptions;
16
16
  });
17
17
 
18
- declare const render: (component: React.ReactElement, options?: Options) => string;
18
+ declare const render: (component: React.ReactElement, options?: Options) => Promise<string>;
19
19
 
20
20
  declare const renderAsync: (component: React.ReactElement, options?: Options) => Promise<string>;
21
21
 
@@ -70,8 +70,7 @@ __export(browser_exports, {
70
70
  });
71
71
  module.exports = __toCommonJS(browser_exports);
72
72
 
73
- // src/shared/render.ts
74
- var ReactDomServer = __toESM(require("react-dom/server"));
73
+ // src/browser/render.ts
75
74
  var import_html_to_text = require("html-to-text");
76
75
 
77
76
  // src/shared/utils/pretty.ts
@@ -97,34 +96,73 @@ var plainTextSelectors = [
97
96
  }
98
97
  ];
99
98
 
100
- // src/shared/render.ts
101
- var render = (component, options) => {
99
+ // src/browser/render.ts
100
+ var decoder = new TextDecoder("utf-8");
101
+ var readStream = (stream) => __async(void 0, null, function* () {
102
+ let result = "";
103
+ if ("pipeTo" in stream) {
104
+ const writableStream = new WritableStream({
105
+ write(chunk) {
106
+ result += decoder.decode(chunk);
107
+ }
108
+ });
109
+ yield stream.pipeTo(writableStream);
110
+ } else {
111
+ throw new Error(
112
+ "For some reason, the Node version of `react-dom/server` has been imported instead of the browser one.",
113
+ {
114
+ cause: {
115
+ stream
116
+ }
117
+ }
118
+ );
119
+ }
120
+ return result;
121
+ });
122
+ var render = (component, options) => __async(void 0, null, function* () {
123
+ const { default: reactDOMServer } = yield import("react-dom/server");
124
+ let html;
125
+ if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
126
+ html = yield readStream(
127
+ yield reactDOMServer.renderToReadableStream(component)
128
+ );
129
+ } else {
130
+ yield new Promise((resolve, reject) => {
131
+ const stream = reactDOMServer.renderToPipeableStream(component, {
132
+ onAllReady() {
133
+ return __async(this, null, function* () {
134
+ html = yield readStream(stream);
135
+ resolve();
136
+ });
137
+ },
138
+ onError(error) {
139
+ reject(error);
140
+ }
141
+ });
142
+ });
143
+ }
102
144
  if (options == null ? void 0 : options.plainText) {
103
- return renderAsPlainText(component, options);
145
+ return (0, import_html_to_text.convert)(html, __spreadValues({
146
+ selectors: plainTextSelectors
147
+ }, options.htmlToTextOptions));
104
148
  }
105
149
  const doctype = '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">';
106
- const markup = ReactDomServer.renderToStaticMarkup(component);
107
- const document = `${doctype}${markup}`;
108
- if (options && options.pretty) {
150
+ const document = `${doctype}${html.replace(/<!DOCTYPE.*?>/, "")}`;
151
+ if (options == null ? void 0 : options.pretty) {
109
152
  return pretty(document);
110
153
  }
111
154
  return document;
112
- };
113
- var renderAsPlainText = (component, options) => {
114
- return (0, import_html_to_text.convert)(ReactDomServer.renderToStaticMarkup(component), __spreadValues({
115
- selectors: plainTextSelectors
116
- }, (options == null ? void 0 : options.plainText) === true ? options.htmlToTextOptions : {}));
117
- };
155
+ });
118
156
 
119
157
  // src/browser/render-async.ts
120
158
  var import_html_to_text2 = require("html-to-text");
121
- var decoder = new TextDecoder("utf-8");
122
- var readStream = (stream) => __async(void 0, null, function* () {
159
+ var decoder2 = new TextDecoder("utf-8");
160
+ var readStream2 = (stream) => __async(void 0, null, function* () {
123
161
  let result = "";
124
162
  if ("pipeTo" in stream) {
125
163
  const writableStream = new WritableStream({
126
164
  write(chunk) {
127
- result += decoder.decode(chunk);
165
+ result += decoder2.decode(chunk);
128
166
  }
129
167
  });
130
168
  yield stream.pipeTo(writableStream);
@@ -144,7 +182,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
144
182
  const { default: reactDOMServer } = yield import("react-dom/server");
145
183
  let html;
146
184
  if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
147
- html = yield readStream(
185
+ html = yield readStream2(
148
186
  yield reactDOMServer.renderToReadableStream(component)
149
187
  );
150
188
  } else {
@@ -152,7 +190,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
152
190
  const stream = reactDOMServer.renderToPipeableStream(component, {
153
191
  onAllReady() {
154
192
  return __async(this, null, function* () {
155
- html = yield readStream(stream);
193
+ html = yield readStream2(stream);
156
194
  resolve();
157
195
  });
158
196
  },
@@ -35,8 +35,7 @@ var __async = (__this, __arguments, generator) => {
35
35
  });
36
36
  };
37
37
 
38
- // src/shared/render.ts
39
- import * as ReactDomServer from "react-dom/server";
38
+ // src/browser/render.ts
40
39
  import { convert } from "html-to-text";
41
40
 
42
41
  // src/shared/utils/pretty.ts
@@ -62,34 +61,73 @@ var plainTextSelectors = [
62
61
  }
63
62
  ];
64
63
 
65
- // src/shared/render.ts
66
- var render = (component, options) => {
64
+ // src/browser/render.ts
65
+ var decoder = new TextDecoder("utf-8");
66
+ var readStream = (stream) => __async(void 0, null, function* () {
67
+ let result = "";
68
+ if ("pipeTo" in stream) {
69
+ const writableStream = new WritableStream({
70
+ write(chunk) {
71
+ result += decoder.decode(chunk);
72
+ }
73
+ });
74
+ yield stream.pipeTo(writableStream);
75
+ } else {
76
+ throw new Error(
77
+ "For some reason, the Node version of `react-dom/server` has been imported instead of the browser one.",
78
+ {
79
+ cause: {
80
+ stream
81
+ }
82
+ }
83
+ );
84
+ }
85
+ return result;
86
+ });
87
+ var render = (component, options) => __async(void 0, null, function* () {
88
+ const { default: reactDOMServer } = yield import("react-dom/server");
89
+ let html;
90
+ if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
91
+ html = yield readStream(
92
+ yield reactDOMServer.renderToReadableStream(component)
93
+ );
94
+ } else {
95
+ yield new Promise((resolve, reject) => {
96
+ const stream = reactDOMServer.renderToPipeableStream(component, {
97
+ onAllReady() {
98
+ return __async(this, null, function* () {
99
+ html = yield readStream(stream);
100
+ resolve();
101
+ });
102
+ },
103
+ onError(error) {
104
+ reject(error);
105
+ }
106
+ });
107
+ });
108
+ }
67
109
  if (options == null ? void 0 : options.plainText) {
68
- return renderAsPlainText(component, options);
110
+ return convert(html, __spreadValues({
111
+ selectors: plainTextSelectors
112
+ }, options.htmlToTextOptions));
69
113
  }
70
114
  const doctype = '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">';
71
- const markup = ReactDomServer.renderToStaticMarkup(component);
72
- const document = `${doctype}${markup}`;
73
- if (options && options.pretty) {
115
+ const document = `${doctype}${html.replace(/<!DOCTYPE.*?>/, "")}`;
116
+ if (options == null ? void 0 : options.pretty) {
74
117
  return pretty(document);
75
118
  }
76
119
  return document;
77
- };
78
- var renderAsPlainText = (component, options) => {
79
- return convert(ReactDomServer.renderToStaticMarkup(component), __spreadValues({
80
- selectors: plainTextSelectors
81
- }, (options == null ? void 0 : options.plainText) === true ? options.htmlToTextOptions : {}));
82
- };
120
+ });
83
121
 
84
122
  // src/browser/render-async.ts
85
123
  import { convert as convert2 } from "html-to-text";
86
- var decoder = new TextDecoder("utf-8");
87
- var readStream = (stream) => __async(void 0, null, function* () {
124
+ var decoder2 = new TextDecoder("utf-8");
125
+ var readStream2 = (stream) => __async(void 0, null, function* () {
88
126
  let result = "";
89
127
  if ("pipeTo" in stream) {
90
128
  const writableStream = new WritableStream({
91
129
  write(chunk) {
92
- result += decoder.decode(chunk);
130
+ result += decoder2.decode(chunk);
93
131
  }
94
132
  });
95
133
  yield stream.pipeTo(writableStream);
@@ -109,7 +147,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
109
147
  const { default: reactDOMServer } = yield import("react-dom/server");
110
148
  let html;
111
149
  if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
112
- html = yield readStream(
150
+ html = yield readStream2(
113
151
  yield reactDOMServer.renderToReadableStream(component)
114
152
  );
115
153
  } else {
@@ -117,7 +155,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
117
155
  const stream = reactDOMServer.renderToPipeableStream(component, {
118
156
  onAllReady() {
119
157
  return __async(this, null, function* () {
120
- html = yield readStream(stream);
158
+ html = yield readStream2(stream);
121
159
  resolve();
122
160
  });
123
161
  },
@@ -15,8 +15,11 @@ type Options = {
15
15
  htmlToTextOptions?: HtmlToTextOptions;
16
16
  });
17
17
 
18
- declare const render: (component: React.ReactElement, options?: Options) => string;
18
+ declare const render: (component: React.ReactElement, options?: Options) => Promise<string>;
19
19
 
20
+ /**
21
+ * @deprecated use `render`
22
+ */
20
23
  declare const renderAsync: (component: React.ReactElement, options?: Options) => Promise<string>;
21
24
 
22
25
  declare const plainTextSelectors: SelectorDefinition[];
@@ -15,8 +15,11 @@ type Options = {
15
15
  htmlToTextOptions?: HtmlToTextOptions;
16
16
  });
17
17
 
18
- declare const render: (component: React.ReactElement, options?: Options) => string;
18
+ declare const render: (component: React.ReactElement, options?: Options) => Promise<string>;
19
19
 
20
+ /**
21
+ * @deprecated use `render`
22
+ */
20
23
  declare const renderAsync: (component: React.ReactElement, options?: Options) => Promise<string>;
21
24
 
22
25
  declare const plainTextSelectors: SelectorDefinition[];
@@ -70,8 +70,8 @@ __export(node_exports, {
70
70
  });
71
71
  module.exports = __toCommonJS(node_exports);
72
72
 
73
- // src/shared/render.ts
74
- var ReactDomServer = __toESM(require("react-dom/server"));
73
+ // src/node/render.ts
74
+ var import_node_stream = require("stream");
75
75
  var import_html_to_text = require("html-to-text");
76
76
 
77
77
  // src/shared/utils/pretty.ts
@@ -97,42 +97,86 @@ var plainTextSelectors = [
97
97
  }
98
98
  ];
99
99
 
100
- // src/shared/render.ts
101
- var render = (component, options) => {
100
+ // src/node/render.ts
101
+ var decoder = new TextDecoder("utf-8");
102
+ var readStream = (stream) => __async(void 0, null, function* () {
103
+ let result = "";
104
+ if ("pipeTo" in stream) {
105
+ const writableStream = new WritableStream({
106
+ write(chunk) {
107
+ result += decoder.decode(chunk);
108
+ }
109
+ });
110
+ yield stream.pipeTo(writableStream);
111
+ } else {
112
+ const writable = new import_node_stream.Writable({
113
+ write(chunk, _encoding, callback) {
114
+ result += decoder.decode(chunk);
115
+ callback();
116
+ }
117
+ });
118
+ stream.pipe(writable);
119
+ return new Promise((resolve, reject) => {
120
+ writable.on("error", reject);
121
+ writable.on("close", () => {
122
+ resolve(result);
123
+ });
124
+ });
125
+ }
126
+ return result;
127
+ });
128
+ var render = (component, options) => __async(void 0, null, function* () {
129
+ const { default: reactDOMServer } = yield import("react-dom/server");
130
+ let html;
131
+ if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
132
+ html = yield readStream(
133
+ yield reactDOMServer.renderToReadableStream(component)
134
+ );
135
+ } else {
136
+ yield new Promise((resolve, reject) => {
137
+ const stream = reactDOMServer.renderToPipeableStream(component, {
138
+ onAllReady() {
139
+ return __async(this, null, function* () {
140
+ html = yield readStream(stream);
141
+ resolve();
142
+ });
143
+ },
144
+ onError(error) {
145
+ reject(error);
146
+ }
147
+ });
148
+ });
149
+ }
102
150
  if (options == null ? void 0 : options.plainText) {
103
- return renderAsPlainText(component, options);
151
+ return (0, import_html_to_text.convert)(html, __spreadValues({
152
+ selectors: plainTextSelectors
153
+ }, options.htmlToTextOptions));
104
154
  }
105
155
  const doctype = '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">';
106
- const markup = ReactDomServer.renderToStaticMarkup(component);
107
- const document = `${doctype}${markup}`;
108
- if (options && options.pretty) {
156
+ const document = `${doctype}${html.replace(/<!DOCTYPE.*?>/, "")}`;
157
+ if (options == null ? void 0 : options.pretty) {
109
158
  return pretty(document);
110
159
  }
111
160
  return document;
112
- };
113
- var renderAsPlainText = (component, options) => {
114
- return (0, import_html_to_text.convert)(ReactDomServer.renderToStaticMarkup(component), __spreadValues({
115
- selectors: plainTextSelectors
116
- }, (options == null ? void 0 : options.plainText) === true ? options.htmlToTextOptions : {}));
117
- };
161
+ });
118
162
 
119
163
  // src/node/render-async.ts
120
- var import_node_stream = require("stream");
164
+ var import_node_stream2 = require("stream");
121
165
  var import_html_to_text2 = require("html-to-text");
122
- var decoder = new TextDecoder("utf-8");
123
- var readStream = (stream) => __async(void 0, null, function* () {
166
+ var decoder2 = new TextDecoder("utf-8");
167
+ var readStream2 = (stream) => __async(void 0, null, function* () {
124
168
  let result = "";
125
169
  if ("pipeTo" in stream) {
126
170
  const writableStream = new WritableStream({
127
171
  write(chunk) {
128
- result += decoder.decode(chunk);
172
+ result += decoder2.decode(chunk);
129
173
  }
130
174
  });
131
175
  yield stream.pipeTo(writableStream);
132
176
  } else {
133
- const writable = new import_node_stream.Writable({
177
+ const writable = new import_node_stream2.Writable({
134
178
  write(chunk, _encoding, callback) {
135
- result += decoder.decode(chunk);
179
+ result += decoder2.decode(chunk);
136
180
  callback();
137
181
  }
138
182
  });
@@ -150,7 +194,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
150
194
  const { default: reactDOMServer } = yield import("react-dom/server");
151
195
  let html;
152
196
  if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
153
- html = yield readStream(
197
+ html = yield readStream2(
154
198
  yield reactDOMServer.renderToReadableStream(component)
155
199
  );
156
200
  } else {
@@ -158,7 +202,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
158
202
  const stream = reactDOMServer.renderToPipeableStream(component, {
159
203
  onAllReady() {
160
204
  return __async(this, null, function* () {
161
- html = yield readStream(stream);
205
+ html = yield readStream2(stream);
162
206
  resolve();
163
207
  });
164
208
  },
@@ -35,8 +35,8 @@ var __async = (__this, __arguments, generator) => {
35
35
  });
36
36
  };
37
37
 
38
- // src/shared/render.ts
39
- import * as ReactDomServer from "react-dom/server";
38
+ // src/node/render.ts
39
+ import { Writable } from "node:stream";
40
40
  import { convert } from "html-to-text";
41
41
 
42
42
  // src/shared/utils/pretty.ts
@@ -62,42 +62,86 @@ var plainTextSelectors = [
62
62
  }
63
63
  ];
64
64
 
65
- // src/shared/render.ts
66
- var render = (component, options) => {
65
+ // src/node/render.ts
66
+ var decoder = new TextDecoder("utf-8");
67
+ var readStream = (stream) => __async(void 0, null, function* () {
68
+ let result = "";
69
+ if ("pipeTo" in stream) {
70
+ const writableStream = new WritableStream({
71
+ write(chunk) {
72
+ result += decoder.decode(chunk);
73
+ }
74
+ });
75
+ yield stream.pipeTo(writableStream);
76
+ } else {
77
+ const writable = new Writable({
78
+ write(chunk, _encoding, callback) {
79
+ result += decoder.decode(chunk);
80
+ callback();
81
+ }
82
+ });
83
+ stream.pipe(writable);
84
+ return new Promise((resolve, reject) => {
85
+ writable.on("error", reject);
86
+ writable.on("close", () => {
87
+ resolve(result);
88
+ });
89
+ });
90
+ }
91
+ return result;
92
+ });
93
+ var render = (component, options) => __async(void 0, null, function* () {
94
+ const { default: reactDOMServer } = yield import("react-dom/server");
95
+ let html;
96
+ if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
97
+ html = yield readStream(
98
+ yield reactDOMServer.renderToReadableStream(component)
99
+ );
100
+ } else {
101
+ yield new Promise((resolve, reject) => {
102
+ const stream = reactDOMServer.renderToPipeableStream(component, {
103
+ onAllReady() {
104
+ return __async(this, null, function* () {
105
+ html = yield readStream(stream);
106
+ resolve();
107
+ });
108
+ },
109
+ onError(error) {
110
+ reject(error);
111
+ }
112
+ });
113
+ });
114
+ }
67
115
  if (options == null ? void 0 : options.plainText) {
68
- return renderAsPlainText(component, options);
116
+ return convert(html, __spreadValues({
117
+ selectors: plainTextSelectors
118
+ }, options.htmlToTextOptions));
69
119
  }
70
120
  const doctype = '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">';
71
- const markup = ReactDomServer.renderToStaticMarkup(component);
72
- const document = `${doctype}${markup}`;
73
- if (options && options.pretty) {
121
+ const document = `${doctype}${html.replace(/<!DOCTYPE.*?>/, "")}`;
122
+ if (options == null ? void 0 : options.pretty) {
74
123
  return pretty(document);
75
124
  }
76
125
  return document;
77
- };
78
- var renderAsPlainText = (component, options) => {
79
- return convert(ReactDomServer.renderToStaticMarkup(component), __spreadValues({
80
- selectors: plainTextSelectors
81
- }, (options == null ? void 0 : options.plainText) === true ? options.htmlToTextOptions : {}));
82
- };
126
+ });
83
127
 
84
128
  // src/node/render-async.ts
85
- import { Writable } from "node:stream";
129
+ import { Writable as Writable2 } from "node:stream";
86
130
  import { convert as convert2 } from "html-to-text";
87
- var decoder = new TextDecoder("utf-8");
88
- var readStream = (stream) => __async(void 0, null, function* () {
131
+ var decoder2 = new TextDecoder("utf-8");
132
+ var readStream2 = (stream) => __async(void 0, null, function* () {
89
133
  let result = "";
90
134
  if ("pipeTo" in stream) {
91
135
  const writableStream = new WritableStream({
92
136
  write(chunk) {
93
- result += decoder.decode(chunk);
137
+ result += decoder2.decode(chunk);
94
138
  }
95
139
  });
96
140
  yield stream.pipeTo(writableStream);
97
141
  } else {
98
- const writable = new Writable({
142
+ const writable = new Writable2({
99
143
  write(chunk, _encoding, callback) {
100
- result += decoder.decode(chunk);
144
+ result += decoder2.decode(chunk);
101
145
  callback();
102
146
  }
103
147
  });
@@ -115,7 +159,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
115
159
  const { default: reactDOMServer } = yield import("react-dom/server");
116
160
  let html;
117
161
  if (Object.hasOwn(reactDOMServer, "renderToReadableStream")) {
118
- html = yield readStream(
162
+ html = yield readStream2(
119
163
  yield reactDOMServer.renderToReadableStream(component)
120
164
  );
121
165
  } else {
@@ -123,7 +167,7 @@ var renderAsync = (component, options) => __async(void 0, null, function* () {
123
167
  const stream = reactDOMServer.renderToPipeableStream(component, {
124
168
  onAllReady() {
125
169
  return __async(this, null, function* () {
126
- html = yield readStream(stream);
170
+ html = yield readStream2(stream);
127
171
  resolve();
128
172
  });
129
173
  },
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@react-email/render",
3
- "version": "0.0.17",
3
+ "version": "1.0.0-canary.1",
4
4
  "description": "Transform React components into HTML email templates",
5
5
  "sideEffects": false,
6
6
  "main": "./dist/browser/index.js",
@@ -82,11 +82,10 @@
82
82
  "react-promise-suspense": "0.3.4"
83
83
  },
84
84
  "peerDependencies": {
85
- "react": "^18.2.0",
86
- "react-dom": "^18.2.0"
85
+ "react": "^18.0 || ^19.0 || ^19.0.0-rc",
86
+ "react-dom": "^18.0 || ^19.0 || ^19.0.0-rc"
87
87
  },
88
88
  "devDependencies": {
89
- "@babel/preset-react": "7.23.3",
90
89
  "@edge-runtime/vm": "3.1.8",
91
90
  "@types/html-to-text": "9.0.4",
92
91
  "@types/js-beautify": "1.14.3",