@idealyst/theme 1.2.0 → 1.2.3

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": "@idealyst/theme",
3
- "version": "1.2.0",
3
+ "version": "1.2.3",
4
4
  "description": "Theming system for Idealyst Framework",
5
5
  "readme": "README.md",
6
6
  "main": "src/index.ts",
@@ -56,6 +56,9 @@
56
56
  "prepublishOnly": "echo 'Publishing TypeScript source directly'",
57
57
  "publish:npm": "npm publish"
58
58
  },
59
+ "dependencies": {
60
+ "@idealyst/tooling": "workspace:*"
61
+ },
59
62
  "peerDependencies": {
60
63
  "react-native-unistyles": ">=3.0.0"
61
64
  },
@@ -29,7 +29,19 @@
29
29
  * }))
30
30
  */
31
31
 
32
- const { loadThemeKeys } = require('./theme-analyzer');
32
+ // Theme analysis is provided by @idealyst/tooling (single source of truth)
33
+ // This uses the TypeScript Compiler API for accurate theme extraction
34
+ let loadThemeKeys;
35
+ try {
36
+ // Try to load from @idealyst/tooling (TypeScript-based analyzer)
37
+ // This is the preferred path as it's the single source of truth
38
+ const tooling = require('@idealyst/tooling');
39
+ loadThemeKeys = tooling.loadThemeKeys;
40
+ } catch (e) {
41
+ // Fallback to local implementation if tooling can't be loaded
42
+ // (e.g., when TypeScript runtime is not available)
43
+ loadThemeKeys = require('./theme-analyzer').loadThemeKeys;
44
+ }
33
45
 
34
46
  // ============================================================================
35
47
  // Global Extension Registry - Persists across files during build
@@ -547,8 +559,7 @@ module.exports = function idealystStylesPlugin({ types: t }) {
547
559
  }
548
560
  }
549
561
 
550
- // Log plugin initialization
551
- console.log('[idealyst-plugin] Plugin loaded (AST-based theme analysis)');
562
+ // Plugin initialization logged in debug mode only
552
563
 
553
564
  return {
554
565
  name: 'idealyst-styles',
@@ -783,13 +794,13 @@ module.exports = function idealystStylesPlugin({ types: t }) {
783
794
  const keys = loadThemeKeys(opts, rootDir, t, verboseMode);
784
795
  const expandedVariants = [];
785
796
 
786
- // Debug for View only
787
- if (componentName === 'View') {
788
- console.log(`\n========== VIEW KEYS DEBUG ==========`);
789
- console.log(`rootDir: ${rootDir}`);
790
- console.log(`keys.sizes.view: ${JSON.stringify(keys?.sizes?.view)}`);
791
- console.log(`keys.intents: ${JSON.stringify(keys?.intents)}`);
792
- console.log(`======================================\n`);
797
+ // Debug for View only (verbose mode)
798
+ if (verboseMode && componentName === 'View') {
799
+ verbose(`\n========== VIEW KEYS DEBUG ==========`);
800
+ verbose(`rootDir: ${rootDir}`);
801
+ verbose(`keys.sizes.view: ${JSON.stringify(keys?.sizes?.view)}`);
802
+ verbose(`keys.intents: ${JSON.stringify(keys?.intents)}`);
803
+ verbose(`======================================\n`);
793
804
  }
794
805
 
795
806
  try {
@@ -252,6 +252,25 @@ function extractThemeKeysFromAST(themeFilePath, babelTypes, verboseMode) {
252
252
  }
253
253
  }
254
254
 
255
+ /**
256
+ * Process a builder chain that ends with .build() - extracts theme keys.
257
+ * Can be called on any node that is a .build() call expression.
258
+ */
259
+ function processBuilderChainNode(node) {
260
+ if (!t.isCallExpression(node)) return;
261
+ if (!t.isMemberExpression(node.callee)) return;
262
+ if (!t.isIdentifier(node.callee.property, { name: 'build' })) return;
263
+
264
+ const { calls, baseThemeVar } = traceBuilderChain(node);
265
+
266
+ if (baseThemeVar) {
267
+ log('Found fromTheme with base:', baseThemeVar);
268
+ analyzeBaseTheme(baseThemeVar);
269
+ }
270
+
271
+ processBuilderCalls(calls);
272
+ }
273
+
255
274
  // Second pass: find theme builder chains
256
275
  traverse(ast, {
257
276
  VariableDeclarator(path) {
@@ -262,14 +281,7 @@ function extractThemeKeysFromAST(themeFilePath, babelTypes, verboseMode) {
262
281
  t.isMemberExpression(init.callee) &&
263
282
  t.isIdentifier(init.callee.property, { name: 'build' })) {
264
283
 
265
- const { calls, baseThemeVar } = traceBuilderChain(init);
266
-
267
- if (baseThemeVar) {
268
- log('Found fromTheme with base:', baseThemeVar);
269
- analyzeBaseTheme(baseThemeVar);
270
- }
271
-
272
- processBuilderCalls(calls);
284
+ processBuilderChainNode(init);
273
285
  }
274
286
  },
275
287
 
@@ -285,14 +297,62 @@ function extractThemeKeysFromAST(themeFilePath, babelTypes, verboseMode) {
285
297
  t.isMemberExpression(init.callee) &&
286
298
  t.isIdentifier(init.callee.property, { name: 'build' })) {
287
299
 
288
- const { calls, baseThemeVar } = traceBuilderChain(init);
300
+ processBuilderChainNode(init);
301
+ }
302
+ }
303
+ },
304
+
305
+ // Handle StyleSheet.configure({ themes: { light: ..., dark: ... } })
306
+ CallExpression(path) {
307
+ const { node } = path;
289
308
 
290
- if (baseThemeVar) {
291
- log('Found fromTheme with base:', baseThemeVar);
292
- analyzeBaseTheme(baseThemeVar);
293
- }
309
+ // Check for StyleSheet.configure(...)
310
+ if (!t.isMemberExpression(node.callee)) return;
311
+ if (!t.isIdentifier(node.callee.object, { name: 'StyleSheet' })) return;
312
+ if (!t.isIdentifier(node.callee.property, { name: 'configure' })) return;
294
313
 
295
- processBuilderCalls(calls);
314
+ log('Found StyleSheet.configure call');
315
+
316
+ const configArg = node.arguments[0];
317
+ if (!t.isObjectExpression(configArg)) return;
318
+
319
+ // Find the 'themes' property
320
+ for (const prop of configArg.properties) {
321
+ if (!t.isObjectProperty(prop)) continue;
322
+
323
+ const keyName = t.isIdentifier(prop.key) ? prop.key.name :
324
+ t.isStringLiteral(prop.key) ? prop.key.value : null;
325
+
326
+ if (keyName !== 'themes') continue;
327
+ if (!t.isObjectExpression(prop.value)) continue;
328
+
329
+ log('Found themes object in StyleSheet.configure');
330
+
331
+ // Process each theme definition
332
+ for (const themeProp of prop.value.properties) {
333
+ if (!t.isObjectProperty(themeProp)) continue;
334
+
335
+ const themeName = t.isIdentifier(themeProp.key) ? themeProp.key.name :
336
+ t.isStringLiteral(themeProp.key) ? themeProp.key.value : null;
337
+
338
+ if (!themeName) continue;
339
+
340
+ const themeValue = themeProp.value;
341
+ log(` Processing theme '${themeName}'`);
342
+
343
+ // Case 1: Inline builder chain - fromTheme(x).build() or createTheme().build()
344
+ if (t.isCallExpression(themeValue) &&
345
+ t.isMemberExpression(themeValue.callee) &&
346
+ t.isIdentifier(themeValue.callee.property, { name: 'build' })) {
347
+
348
+ log(` Found inline builder chain for '${themeName}'`);
349
+ processBuilderChainNode(themeValue);
350
+ }
351
+ // Case 2: Variable reference - analyze the referenced variable's file
352
+ else if (t.isIdentifier(themeValue)) {
353
+ log(` Found variable reference '${themeValue.name}' for '${themeName}'`);
354
+ analyzeBaseTheme(themeValue.name);
355
+ }
296
356
  }
297
357
  }
298
358
  }
@@ -325,18 +385,22 @@ function loadThemeKeys(opts, rootDir, babelTypes, verboseMode) {
325
385
  ? nodePath.resolve(rootDir, themePath)
326
386
  : require.resolve(themePath, { paths: [rootDir] });
327
387
 
328
- console.log('[idealyst-plugin] Analyzing theme file:', resolvedPath);
388
+ if (verboseMode) {
389
+ console.log('[idealyst-plugin] Analyzing theme file:', resolvedPath);
390
+ }
329
391
 
330
392
  themeKeys = extractThemeKeysFromAST(resolvedPath, babelTypes, verboseMode);
331
393
 
332
- // Always log the extracted keys
333
- console.log('[idealyst-plugin] Extracted theme keys:');
334
- console.log(' intents:', themeKeys.intents);
335
- console.log(' radii:', themeKeys.radii);
336
- console.log(' shadows:', themeKeys.shadows);
337
- console.log(' sizes:');
338
- for (const [component, sizes] of Object.entries(themeKeys.sizes)) {
339
- console.log(` ${component}:`, sizes);
394
+ // Log extracted keys in verbose mode
395
+ if (verboseMode) {
396
+ console.log('[idealyst-plugin] Extracted theme keys:');
397
+ console.log(' intents:', themeKeys.intents);
398
+ console.log(' radii:', themeKeys.radii);
399
+ console.log(' shadows:', themeKeys.shadows);
400
+ console.log(' sizes:');
401
+ for (const [component, sizes] of Object.entries(themeKeys.sizes)) {
402
+ console.log(` ${component}:`, sizes);
403
+ }
340
404
  }
341
405
 
342
406
  return themeKeys;