Skip to content

Commit f95e969

Browse files
committed
fix(jsx-email): make check/build use template previewProps by default; add --use-preview-props flag docs and safer props parsing
1 parent ce7582d commit f95e969

File tree

2 files changed

+26
-4
lines changed

2 files changed

+26
-4
lines changed

packages/jsx-email/src/cli/commands/build.mts

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,10 @@ Builds a template and saves the result
8383
--props A JSON string containing props to be passed to the email template
8484
This is usually only useful when building a single template, unless all of your
8585
templates share the same props.
86+
--use-preview-props / --no-use-preview-props
87+
When set, use the \`previewProps\` exported by the template file (if present).
88+
Default behavior: if \`--props\` is not provided and the template exports
89+
\`previewProps\`, those props will be used.
8690
8791
{underline Examples}
8892
$ email build ./src/emails
@@ -115,8 +119,25 @@ export const build = async (options: BuildOptions): Promise<BuildResult> => {
115119
process.exit(1);
116120
}
117121

118-
// const extension = plain ? '.txt' : '.html';
119-
const renderProps = usePreviewProps ? template.previewProps || {} : JSON.parse(props);
122+
// Determine the props to render with,
123+
// precedence: explicit --props > --use-preview-props (or default) > empty object
124+
// Note: when building a directory, each file's own exported previewProps will be used
125+
// if --props is omitted and the export exists.
126+
let renderProps: Record<string, any> = {};
127+
const hasExplicitProps = typeof props === 'string' && props.trim() !== '';
128+
129+
if (hasExplicitProps) {
130+
try {
131+
renderProps = JSON.parse(props);
132+
} catch (err) {
133+
log.error(chalk`{red Invalid --props JSON:} ${(err as Error).message}`);
134+
process.exit(1);
135+
}
136+
} else if (usePreviewProps !== false && 'previewProps' in template) {
137+
// Use previewProps by default when available, unless explicitly disabled via --no-use-preview-props
138+
const pp = (template as any).previewProps;
139+
renderProps = pp && typeof pp === 'object' ? pp : {};
140+
}
120141
const fileExt = extname(path);
121142
const templateName = basename(path, fileExt).replace(/-[^-]{8}$/, '');
122143
const component = componentExport(renderProps);

packages/jsx-email/src/cli/commands/check.mts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,8 @@ Check jsx-email templates for client compatibility
5656
5757
{underline Examples}
5858
$ email check ./emails/Batman.tsx
59-
`;
59+
\nNote: If the template file exports \`previewProps\`, those props will be used when
60+
rendering the template for checks. This mirrors the Preview app behavior.`;
6061

6162
const runCheck = (fileName: string, html: string) => {
6263
const bytes = Buffer.byteLength(html, 'utf8');
@@ -131,7 +132,7 @@ export const command: CommandFn = async (argv: CheckOptions, input) => {
131132
log(chalk`{blue Checking email template for Client Compatibility...}\n`);
132133

133134
const [file] = await buildTemplates({
134-
buildOptions: { showStats: false, writeToFile: false },
135+
buildOptions: { showStats: false, writeToFile: false, usePreviewProps: true },
135136
targetPath: input[0]
136137
});
137138

0 commit comments

Comments
 (0)