@decocms/start 0.36.4 → 0.36.5

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@decocms/start",
3
- "version": "0.36.4",
3
+ "version": "0.36.5",
4
4
  "type": "module",
5
5
  "description": "Deco framework for TanStack Start - CMS bridge, admin protocol, hooks, schema generation",
6
6
  "main": "./src/index.ts",
@@ -171,6 +171,55 @@ export function transformJsx(content: string): TransformResult {
171
171
  notes.push("Replaced 'class' in interface definitions with 'className'");
172
172
  }
173
173
 
174
+ // Remove `alt` prop from non-img elements (<a>, <iframe>, <div>, etc.)
175
+ // In React, `alt` is only valid on <img>, <input type="image">, <area>
176
+ const altOnNonImgRegex = /(<(?:a|iframe|div|span|button|section)\s[^>]*?)\s+alt=(?:\{[^}]*\}|"[^"]*"|'[^']*')/g;
177
+ if (altOnNonImgRegex.test(result)) {
178
+ result = result.replace(
179
+ /(<(?:a|iframe|div|span|button|section)\s[^>]*?)\s+alt=(?:\{[^}]*\}|"[^"]*"|'[^']*')/g,
180
+ "$1",
181
+ );
182
+ changed = true;
183
+ notes.push("Removed invalid alt prop from non-img elements");
184
+ }
185
+
186
+ // Remove `type` prop from non-form elements (<span>, <div>, etc.)
187
+ // In React, `type` is only valid on <input>, <button>, <select>, <textarea>, <script>, <style>, <link>
188
+ const typeOnInvalidRegex = /(<(?:span|div|p|section|header|footer|nav|main|article|aside)\s[^>]*?)\s+type=(?:\{[^}]*\}|"[^"]*"|'[^']*')/g;
189
+ if (typeOnInvalidRegex.test(result)) {
190
+ result = result.replace(
191
+ /(<(?:span|div|p|section|header|footer|nav|main|article|aside)\s[^>]*?)\s+type=(?:\{[^}]*\}|"[^"]*"|'[^']*')/g,
192
+ "$1",
193
+ );
194
+ changed = true;
195
+ notes.push("Removed invalid type prop from non-form elements");
196
+ }
197
+
198
+ // setTimeout/setInterval return type: use window.setTimeout for correct typing
199
+ // In Node/CF Workers, setTimeout returns Timeout object, not number
200
+ // window.setTimeout always returns number
201
+ if (/\bsetTimeout\b/.test(result) && /:\s*number/.test(result)) {
202
+ // Only replace bare setTimeout when it's assigned to a typed variable
203
+ result = result.replace(
204
+ /\b(?<!window\.)setTimeout\(/g,
205
+ "window.setTimeout(",
206
+ );
207
+ result = result.replace(
208
+ /\b(?<!window\.)setInterval\(/g,
209
+ "window.setInterval(",
210
+ );
211
+ result = result.replace(
212
+ /\b(?<!window\.)clearTimeout\(/g,
213
+ "window.clearTimeout(",
214
+ );
215
+ result = result.replace(
216
+ /\b(?<!window\.)clearInterval\(/g,
217
+ "window.clearInterval(",
218
+ );
219
+ changed = true;
220
+ notes.push("Prefixed setTimeout/setInterval with window. for correct typing");
221
+ }
222
+
174
223
  // Ensure React import exists if we introduced React.* references
175
224
  if (
176
225
  (result.includes("React.") || result.includes("React,")) &&
@@ -25,7 +25,7 @@ interface AppAutoconfigurator {
25
25
  }
26
26
 
27
27
  const KNOWN_APPS: Record<string, AppAutoconfigurator> = {
28
- "deco-resend": async (block: any) => {
28
+ "deco-resend": async (block: any): Promise<Record<string, InvokeAction>> => {
29
29
  try {
30
30
  const [resendClient, resendActions] = await Promise.all([
31
31
  import("@decocms/apps/resend/client" as string),
@@ -40,7 +40,7 @@ const KNOWN_APPS: Record<string, AppAutoconfigurator> = {
40
40
  "[autoconfig] deco-resend: no API key found." +
41
41
  " Set DECO_CRYPTO_KEY to decrypt CMS secrets, or set RESEND_API_KEY as fallback.",
42
42
  );
43
- return {};
43
+ return {} as Record<string, InvokeAction>;
44
44
  }
45
45
 
46
46
  configureResend({