auklet 0.0.19 → 0.0.21

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.
Files changed (101) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +183 -393
  3. package/bin/entry.mjs +5 -0
  4. package/dist/build/bundleConfig.js +3 -2
  5. package/dist/build/cliOverrides.d.ts +22 -0
  6. package/dist/build/cliOverrides.js +22 -0
  7. package/dist/build/moduleConfig.js +1 -1
  8. package/dist/build/runTsdown.d.ts +2 -0
  9. package/dist/build/runTsdown.js +4 -3
  10. package/dist/build/tsdown/common.d.ts +2 -2
  11. package/dist/build/tsdown/context.d.ts +2 -1
  12. package/dist/build/tsdown/context.js +2 -1
  13. package/dist/build/tsdown/define.js +3 -2
  14. package/dist/build/tsdown/dependencies.js +3 -1
  15. package/dist/build/tsdown/entries.d.ts +2 -2
  16. package/dist/build/tsdown/entries.js +10 -10
  17. package/dist/build/tsdown/types.d.ts +1 -0
  18. package/dist/cli/build.d.ts +5 -0
  19. package/dist/cli/build.js +30 -0
  20. package/dist/cli/buildArgs.d.ts +8 -0
  21. package/dist/cli/buildArgs.js +114 -0
  22. package/dist/cli/buildCss.d.ts +12 -0
  23. package/dist/cli/buildCss.js +53 -0
  24. package/dist/cli/dev.d.ts +1 -0
  25. package/dist/cli/dev.js +39 -0
  26. package/dist/cli/main.d.ts +1 -0
  27. package/dist/cli/main.js +95 -0
  28. package/dist/cli/publish.d.ts +2 -0
  29. package/dist/cli/publish.js +9 -0
  30. package/dist/config.d.ts +3 -1
  31. package/dist/config.js +7 -1
  32. package/dist/configLoader.d.ts +1 -0
  33. package/dist/configLoader.js +42 -61
  34. package/dist/css/production/buildReporter.d.ts +3 -0
  35. package/dist/css/production/buildReporter.js +19 -0
  36. package/dist/css/production/builder.d.ts +8 -3
  37. package/dist/css/production/builder.js +9 -13
  38. package/dist/css/vite/hmr.js +10 -8
  39. package/dist/css/vite/moduleGraph/graph.js +2 -3
  40. package/dist/css/vite/moduleGraph/packageSource/monorepo.d.ts +5 -1
  41. package/dist/css/vite/moduleGraph/packageSource/monorepo.js +42 -33
  42. package/dist/css/vite/moduleGraph/packageSource/singlePackage.js +3 -3
  43. package/dist/css/vite/moduleGraph/requestCache.d.ts +4 -4
  44. package/dist/css/vite/moduleGraph/requestCache.js +8 -4
  45. package/dist/css/vite/moduleGraph/styleCodeFactory.js +4 -4
  46. package/dist/css/vite/moduleGraph/types.d.ts +0 -1
  47. package/dist/css/watch/watcher.d.ts +0 -1
  48. package/dist/css/watch/watcher.js +9 -15
  49. package/dist/index.d.ts +6 -7
  50. package/dist/index.js +5 -5
  51. package/dist/logger.d.ts +5 -0
  52. package/dist/logger.js +14 -0
  53. package/dist/publish/api/gitApi.d.ts +7 -0
  54. package/dist/publish/api/gitApi.js +55 -0
  55. package/dist/publish/api/packageJsonApi.d.ts +7 -0
  56. package/dist/publish/api/packageJsonApi.js +35 -0
  57. package/dist/publish/api/pnpmApi.d.ts +9 -0
  58. package/dist/publish/api/pnpmApi.js +85 -0
  59. package/dist/publish/api/pnpmPublishApi.d.ts +4 -0
  60. package/dist/publish/api/pnpmPublishApi.js +7 -0
  61. package/dist/publish/api/publishArgs.d.ts +2 -0
  62. package/dist/publish/api/publishArgs.js +25 -0
  63. package/dist/publish/api/publishHookApi.d.ts +10 -0
  64. package/dist/publish/api/publishHookApi.js +53 -0
  65. package/dist/publish/cli.d.ts +2 -0
  66. package/dist/publish/cli.js +95 -0
  67. package/dist/publish/ownerRunner.d.ts +6 -0
  68. package/dist/publish/ownerRunner.js +22 -0
  69. package/dist/publish/publishRunner.d.ts +16 -0
  70. package/dist/publish/publishRunner.js +108 -0
  71. package/dist/publish/runner/packageBuilder.d.ts +4 -0
  72. package/dist/publish/runner/packageBuilder.js +16 -0
  73. package/dist/publish/runner/packagePublisher.d.ts +7 -0
  74. package/dist/publish/runner/packagePublisher.js +21 -0
  75. package/dist/publish/runner/publishFailureReporter.d.ts +3 -0
  76. package/dist/publish/runner/publishFailureReporter.js +14 -0
  77. package/dist/publish/runner/publishOutputFormatter.d.ts +2 -0
  78. package/dist/publish/runner/publishOutputFormatter.js +83 -0
  79. package/dist/publish/runner/publishPreflight.d.ts +8 -0
  80. package/dist/publish/runner/publishPreflight.js +26 -0
  81. package/dist/publish/runner/publishSummaryReporter.d.ts +10 -0
  82. package/dist/publish/runner/publishSummaryReporter.js +81 -0
  83. package/dist/publish/runner/publishTargetError.d.ts +9 -0
  84. package/dist/publish/runner/publishTargetError.js +14 -0
  85. package/dist/publish/runner/releaseGitController.d.ts +10 -0
  86. package/dist/publish/runner/releaseGitController.js +41 -0
  87. package/dist/publish/runner/versionWriter.d.ts +13 -0
  88. package/dist/publish/runner/versionWriter.js +78 -0
  89. package/dist/publish/targetResolver.d.ts +7 -0
  90. package/dist/publish/targetResolver.js +195 -0
  91. package/dist/publish/types.d.ts +70 -0
  92. package/dist/publish/types.js +0 -0
  93. package/dist/publish/version.d.ts +5 -0
  94. package/dist/publish/version.js +55 -0
  95. package/dist/types.d.ts +8 -7
  96. package/dist/workspace/packages.d.ts +9 -0
  97. package/dist/workspace/packages.js +62 -0
  98. package/dist/workspace/root.d.ts +1 -0
  99. package/dist/workspace/root.js +14 -0
  100. package/package.json +15 -7
  101. package/bin/entry.cjs +0 -163
package/dist/config.d.ts CHANGED
@@ -1,5 +1,6 @@
1
1
  import type { AukletConfig, StyleDependencyGroup } from '#auklet/types';
2
- export declare const aukletConfigFile = "auklet.config.ts";
2
+ export declare const aukletConfigFiles: string[];
3
+ export declare function isAukletConfigFile(file: string): boolean;
3
4
  export declare const aukletDefaultOptions: {
4
5
  source: string;
5
6
  output: string;
@@ -42,3 +43,4 @@ export declare function normalizeAukletConfig(config?: AukletConfig): {
42
43
  };
43
44
  };
44
45
  };
46
+ export declare function defineConfig(config: AukletConfig): AukletConfig;
package/dist/config.js CHANGED
@@ -1,4 +1,7 @@
1
- export const aukletConfigFile = 'auklet.config.ts';
1
+ export const aukletConfigFiles = ['auklet.config.js', 'auklet.config.mjs'];
2
+ export function isAukletConfigFile(file) {
3
+ return aukletConfigFiles.includes(file);
4
+ }
2
5
  export const aukletDefaultOptions = {
3
6
  source: 'src',
4
7
  output: 'dist',
@@ -45,3 +48,6 @@ export function normalizeAukletConfig(config = {}) {
45
48
  },
46
49
  };
47
50
  }
51
+ export function defineConfig(config) {
52
+ return config;
53
+ }
@@ -1,3 +1,4 @@
1
1
  import type { AukletConfig, LoadAukletConfigOptions } from '#auklet/types';
2
+ export declare function resolveAukletConfigPath(packageRoot: string, configFile?: string): string | null;
2
3
  export declare function resolveAukletConfigModule(module: Record<string, unknown>): AukletConfig;
3
4
  export declare function loadAukletConfig(packageRoot: string, options?: LoadAukletConfigOptions): Promise<AukletConfig>;
@@ -1,79 +1,60 @@
1
1
  import fs from 'node:fs';
2
2
  import path from 'node:path';
3
- import { fileURLToPath, pathToFileURL } from 'node:url';
4
- import ts from 'typescript';
5
- import { aukletConfigFile } from '#auklet/config';
6
- const importAukletConfigModule = async (configPath, href) => {
7
- try {
8
- return (await import(href));
9
- }
10
- catch (error) {
11
- if (!isUnknownTsExtensionError(error) || !configPath.endsWith('.ts')) {
12
- throw error;
13
- }
14
- return importTsOptionsModule(href);
15
- }
16
- };
17
- const importTsOptionsModule = async (href) => {
18
- const configPath = fileURLToPath(href);
19
- const source = fs.readFileSync(configPath, 'utf8');
20
- const output = ts.transpileModule(source, {
21
- compilerOptions: {
22
- esModuleInterop: true,
23
- module: ts.ModuleKind.ESNext,
24
- target: ts.ScriptTarget.ES2020,
25
- },
26
- fileName: configPath,
27
- });
28
- const tempFile = path.join(path.dirname(configPath), `.auklet.config.${process.pid}.${Date.now()}.mjs`);
29
- fs.writeFileSync(tempFile, output.outputText);
30
- try {
31
- return (await import(pathToFileURL(tempFile).href));
32
- }
33
- finally {
34
- fs.rmSync(tempFile, { force: true });
35
- }
3
+ import { pathToFileURL } from 'node:url';
4
+ import { isPlainObject } from 'aidly';
5
+ import { aukletConfigFiles, isAukletConfigFile } from '#auklet/config';
6
+ const asRecord = (value) => {
7
+ return isPlainObject(value) ? value : null;
36
8
  };
37
- const isUnknownTsExtensionError = (error) => {
38
- return (error instanceof TypeError &&
39
- 'code' in error &&
40
- error.code === 'ERR_UNKNOWN_FILE_EXTENSION');
9
+ const assertSupportedConfigFile = (configFile) => {
10
+ const basename = path.basename(configFile);
11
+ if (isAukletConfigFile(basename))
12
+ return;
13
+ throw new Error('[auklet] unsupported config file: ' +
14
+ basename +
15
+ '. Use auklet.config.js or auklet.config.mjs and export `config`.');
41
16
  };
42
- const asRecord = (value) => {
43
- if (!value || typeof value !== 'object' || Array.isArray(value)) {
17
+ export function resolveAukletConfigPath(packageRoot, configFile) {
18
+ if (!fs.existsSync(packageRoot))
44
19
  return null;
20
+ if (configFile) {
21
+ assertSupportedConfigFile(configFile);
22
+ const configPath = path.join(packageRoot, configFile);
23
+ return fs.existsSync(configPath) ? configPath : null;
24
+ }
25
+ const configPaths = aukletConfigFiles
26
+ .map((file) => path.join(packageRoot, file))
27
+ .filter((file) => fs.existsSync(file));
28
+ if (configPaths.length > 1) {
29
+ throw new Error('[auklet] found multiple config files: ' +
30
+ configPaths.map((file) => path.basename(file)).join(', ') +
31
+ '. Keep only one auklet config file.');
32
+ }
33
+ if (configPaths[0])
34
+ return configPaths[0];
35
+ for (const file of fs.readdirSync(packageRoot)) {
36
+ if (file.startsWith('auklet.config.') && !isAukletConfigFile(file)) {
37
+ assertSupportedConfigFile(file);
38
+ }
45
39
  }
46
- return value;
47
- };
40
+ return null;
41
+ }
48
42
  export function resolveAukletConfigModule(module) {
49
- const candidates = [
50
- module,
51
- asRecord(module.default),
52
- asRecord(module['module.exports']),
53
- ];
54
- for (const candidate of candidates) {
55
- if (!candidate)
56
- continue;
57
- const config = asRecord(candidate.config);
58
- if (config) {
59
- return config;
60
- }
43
+ const config = asRecord(module.config);
44
+ if (!config) {
45
+ throw new Error('[auklet] config file must export `config`.');
61
46
  }
62
- return {};
47
+ return config;
63
48
  }
64
49
  export async function loadAukletConfig(packageRoot, options = {}) {
65
- const configPath = path.join(packageRoot, options.configFile ?? aukletConfigFile);
66
- if (!fs.existsSync(configPath)) {
50
+ const configPath = resolveAukletConfigPath(packageRoot, options.configFile);
51
+ if (!configPath) {
67
52
  return {};
68
53
  }
69
54
  const url = pathToFileURL(configPath);
70
55
  if (options.cacheBust) {
71
56
  url.searchParams.set('t', Date.now().toString());
72
57
  }
73
- if (configPath.endsWith('.ts')) {
74
- const module = await importTsOptionsModule(url.href);
75
- return resolveAukletConfigModule(module);
76
- }
77
- const module = await importAukletConfigModule(configPath, url.href);
58
+ const module = (await import(url.href));
78
59
  return resolveAukletConfigModule(module);
79
60
  }
@@ -0,0 +1,3 @@
1
+ import type { AukletLogger } from '#auklet/logger';
2
+ import type { ModuleStyleBuildResult } from '#auklet/types';
3
+ export declare function logModuleStyleBuildResult(logger: AukletLogger, result: ModuleStyleBuildResult, elapsed: number): void;
@@ -0,0 +1,19 @@
1
+ import path from 'node:path';
2
+ export function logModuleStyleBuildResult(logger, result, elapsed) {
3
+ logger.step(`Build ${path.basename(result.packageRoot)}`);
4
+ logger.item(logger.colors.bold(logger.colors.yellow(String(result.styleFiles.length))), logger.colors.bold(logger.colors.white(' source style file(s), ')), logger.colors.bold(logger.colors.yellow(String(result.outputs.length))), logger.colors.bold(logger.colors.white(' output entry file(s)')));
5
+ if (result.outputs.length) {
6
+ const rows = result.outputs.map((output) => [
7
+ logger.path(path.relative(result.packageRoot, output.file)),
8
+ `${(output.size / 1000).toFixed(2)} kB`,
9
+ ]);
10
+ const sizeWidth = Math.max(...rows.map(([, size]) => String(size).length));
11
+ logger.rows({
12
+ rows: rows.map(([file, size]) => [
13
+ file,
14
+ logger.colors.gray(String(size).padStart(sizeWidth)),
15
+ ]),
16
+ });
17
+ }
18
+ logger.success('Build complete in ', logger.duration(elapsed));
19
+ }
@@ -2,10 +2,15 @@ import type { ModuleStyleBuildConfig, ModuleStyleBuildContext, ModuleStyleBuildO
2
2
  export declare class ModuleStyleBuilder {
3
3
  private readonly config;
4
4
  private readonly context;
5
- private readonly logger?;
6
5
  constructor(context?: ModuleStyleBuildContext, config?: ModuleStyleBuildConfig);
7
- build(options?: ModuleStyleBuildOptions): Promise<void>;
8
- private logOutputs;
6
+ build(options?: ModuleStyleBuildOptions): Promise<{
7
+ packageRoot: string;
8
+ styleFiles: string[];
9
+ outputs: {
10
+ file: string;
11
+ size: number;
12
+ }[];
13
+ }>;
9
14
  private createBuildContext;
10
15
  private createPackageContext;
11
16
  }
@@ -1,14 +1,12 @@
1
- import path from 'node:path';
1
+ import fs from 'node:fs';
2
2
  import { normalizeAukletConfig } from '#auklet/config';
3
3
  import { moduleStyleBuildConfig } from '#auklet/css/config';
4
4
  import { StylePackageContext } from '#auklet/css/core/stylePackageContext';
5
5
  import { ModuleStyleOutputWriter } from '#auklet/css/production/moduleOutputWriter';
6
6
  import { PackageStyleEntryWriter } from '#auklet/css/production/packageEntryWriter';
7
- import { toPosixPath } from '#auklet/utils';
8
7
  export class ModuleStyleBuilder {
9
8
  config;
10
9
  context;
11
- logger;
12
10
  constructor(context = {}, config = moduleStyleBuildConfig) {
13
11
  this.config = config;
14
12
  this.context = {
@@ -17,12 +15,10 @@ export class ModuleStyleBuilder {
17
15
  output: context.output,
18
16
  ...context,
19
17
  };
20
- this.logger = context.logger;
21
18
  }
22
19
  async build(options = {}) {
23
20
  const rawConfig = options.aukletConfig ?? this.context.aukletConfig ?? {};
24
21
  const normalizedConfig = normalizeAukletConfig(rawConfig);
25
- const logger = options.logger ?? this.logger;
26
22
  const context = this.createBuildContext(normalizedConfig);
27
23
  const packageContext = this.createPackageContext(context, normalizedConfig);
28
24
  const writerOptions = {
@@ -33,17 +29,17 @@ export class ModuleStyleBuilder {
33
29
  const packageWriter = new PackageStyleEntryWriter(writerOptions);
34
30
  const packageOutput = packageWriter.write();
35
31
  const outputs = packageOutput ? [packageOutput] : [];
36
- logger?.log?.(`[auklet:css] build ${path.basename(context.packageRoot)}`);
37
32
  if (normalizedConfig.modules) {
38
33
  outputs.push(...new ModuleStyleOutputWriter(writerOptions).write());
39
34
  }
40
- this.logOutputs(context, packageContext.styleFiles, outputs, logger);
41
- }
42
- logOutputs(context, styleFiles, outputs, logger) {
43
- logger?.log?.(`[auklet:css] ${styleFiles.length} source style file(s), ${outputs.length} output entry file(s)`);
44
- for (const output of outputs) {
45
- logger?.log?.(`[auklet:css] + ${toPosixPath(path.relative(context.packageRoot, output))}`);
46
- }
35
+ return {
36
+ packageRoot: context.packageRoot,
37
+ styleFiles: packageContext.styleFiles,
38
+ outputs: outputs.map((file) => ({
39
+ file,
40
+ size: fs.statSync(file).size,
41
+ })),
42
+ };
47
43
  }
48
44
  createBuildContext(config) {
49
45
  return {
@@ -1,15 +1,17 @@
1
1
  import path from 'node:path';
2
+ import { isString } from 'aidly';
2
3
  import { normalizeFileKey } from '#auklet/utils';
4
+ import { createScopedAukletLogger } from '#auklet/logger';
3
5
  // package CSS 的 HMR 不能直接走 Vite 原生 CSS 文件链路:
4
- // - 浏览器 import 的是 auklet-css:* 虚拟 CSS 模块,不是真实的
6
+ // 1. 浏览器 import 的是 auklet-css:* 虚拟 CSS 模块,不是真实的
5
7
  // packages/*/src/**/*.css 文件,所以真实 CSS 变化时 Vite 的 modules 可能为空。
6
- // - Vite dev 会把 CSS 转成自接受的 JS 模块,重新执行模块里的 updateStyle()
8
+ // 2. Vite dev 会把 CSS 转成自接受的 JS 模块,重新执行模块里的 updateStyle()
7
9
  // 才能更新样式,因此这里手动发送 js-update,而不是 css-update。
8
- // - @tailwindcss/vite 会在相关 CSS 变化时主动发 full-reload。package CSS 已由
10
+ // 3. @tailwindcss/vite 会在相关 CSS 变化时主动发 full-reload。package CSS 已由
9
11
  // 这个插件接管 HMR 时,需要在一个很短的窗口内吞掉这次 reload。
10
- const HMR_LOG_PREFIX = '[auklet:css:vite]';
11
12
  const FULL_RELOAD_SUPPRESS_MS = 100;
12
13
  const DUPLICATE_UPDATE_IGNORE_MS = 500;
14
+ const logger = createScopedAukletLogger('css:vite');
13
15
  const toBrowserVirtualPath = (id) => {
14
16
  return `/@id/${id.replace('\0', '__x00__')}`;
15
17
  };
@@ -58,13 +60,13 @@ export class AukletStyleHmr {
58
60
  installFullReloadGuard(server) {
59
61
  const send = server.ws.send.bind(server.ws);
60
62
  server.ws.send = ((payload, data) => {
61
- if (typeof payload !== 'string' &&
63
+ if (!isString(payload) &&
62
64
  payload.type === 'full-reload' &&
63
65
  this.shouldSuppressFullReload()) {
64
- console.info(`${HMR_LOG_PREFIX} suppressed package css full-reload`);
66
+ logger.info('suppressed package css full-reload');
65
67
  return;
66
68
  }
67
- if (typeof payload === 'string') {
69
+ if (isString(payload)) {
68
70
  send(payload, data);
69
71
  return;
70
72
  }
@@ -98,7 +100,7 @@ export class AukletStyleHmr {
98
100
  isWithinCircularImport: false,
99
101
  };
100
102
  });
101
- console.info(`${HMR_LOG_PREFIX} package css hmr ${getRelativeFile(context.file)} tracked=${virtualIds.length} updates=${updates.length}`);
103
+ logger.info(`package css hmr ${getRelativeFile(context.file)} tracked=${virtualIds.length} updates=${updates.length}`);
102
104
  if (updates.length) {
103
105
  context.server.ws.send({
104
106
  type: 'update',
@@ -1,5 +1,5 @@
1
1
  import path from 'node:path';
2
- import { aukletConfigFile } from '#auklet/config';
2
+ import { isAukletConfigFile } from '#auklet/config';
3
3
  import { loadAukletConfig } from '#auklet/configLoader';
4
4
  import { moduleStyleBuildConfig } from '#auklet/css/config';
5
5
  import { parsePackageStyleId } from '#auklet/css/vite/moduleGraph/styleId';
@@ -22,7 +22,6 @@ export class ModuleStyleGraph {
22
22
  (options.mode ?? 'package') === 'monorepo'
23
23
  ? new MonorepoPackageSource({
24
24
  root: normalizeFileKey(options.root),
25
- packagesDir: options.packagesDir ?? 'packages',
26
25
  styleExtensions: this.config.styleExtensions,
27
26
  })
28
27
  : new SinglePackageSource({
@@ -38,7 +37,7 @@ export class ModuleStyleGraph {
38
37
  return this.packageSource.isSourceGraphFile(file);
39
38
  }
40
39
  isStyleConfigFile(file) {
41
- return normalizeFileKey(file).endsWith(aukletConfigFile);
40
+ return isAukletConfigFile(path.basename(normalizeFileKey(file)));
42
41
  }
43
42
  isStyleFile(file) {
44
43
  return this.config.styleExtensions.includes(path.extname(file));
@@ -1,18 +1,22 @@
1
+ import type { WorkspacePackageInfo } from '#auklet/workspace/packages';
1
2
  import type { StylePackageInfo, StylePackageSource } from '#auklet/css/vite/moduleGraph/packageSource/types';
2
3
  export type MonorepoPackageSourceOptions = {
3
4
  root: string;
4
- packagesDir: string;
5
5
  styleExtensions: Array<string>;
6
+ readWorkspacePackages?: (root: string) => Array<WorkspacePackageInfo>;
6
7
  };
7
8
  export declare class MonorepoPackageSource implements StylePackageSource {
8
9
  private readonly options;
9
10
  private packages?;
10
11
  private packageNames?;
11
12
  private readonly root;
13
+ private readonly rawRoot;
12
14
  constructor(options: MonorepoPackageSourceOptions);
13
15
  getPackages(): StylePackageInfo[];
14
16
  getPackageNames(): string[];
15
17
  isKnownPackageName(packageName: string): boolean;
16
18
  isSourceGraphFile(file: string): boolean;
17
19
  getWatchRoots(): Promise<string[]>;
20
+ private getWorkspacePackages;
21
+ private isWorkspaceRootPackage;
18
22
  }
@@ -1,43 +1,24 @@
1
1
  import fs from 'node:fs';
2
2
  import path from 'node:path';
3
- import { aukletConfigFile } from '#auklet/config';
3
+ import { aukletConfigFiles, isAukletConfigFile } from '#auklet/config';
4
4
  import { SOURCE_MODULE_RE } from '#auklet/css/constants';
5
- import { normalizeFileKey, toWatchPath } from '#auklet/utils';
5
+ import { normalizeFileKey, toPosixPath, toWatchPath } from '#auklet/utils';
6
+ import { readPnpmWorkspacePackageInfoSync } from '#auklet/workspace/packages';
6
7
  export class MonorepoPackageSource {
7
8
  options;
8
9
  packages;
9
10
  packageNames;
10
11
  root;
12
+ rawRoot;
11
13
  constructor(options) {
12
14
  this.options = options;
13
15
  this.root = normalizeFileKey(options.root);
16
+ this.rawRoot = toPosixPath(path.resolve(options.root));
14
17
  }
15
18
  getPackages() {
16
19
  if (this.packages)
17
20
  return this.packages;
18
- const packagesRoot = path.join(this.root, this.options.packagesDir);
19
- if (!fs.existsSync(packagesRoot)) {
20
- this.packages = [];
21
- return this.packages;
22
- }
23
- this.packages = fs
24
- .readdirSync(packagesRoot, { withFileTypes: true })
25
- .filter((entry) => entry.isDirectory())
26
- .flatMap((entry) => {
27
- const packageRoot = path.join(packagesRoot, entry.name);
28
- const packageJsonPath = path.join(packageRoot, 'package.json');
29
- if (!fs.existsSync(packageJsonPath))
30
- return [];
31
- const pkg = JSON.parse(fs.readFileSync(packageJsonPath, 'utf8'));
32
- if (!pkg.name)
33
- return [];
34
- return [
35
- {
36
- packageName: pkg.name,
37
- packageRoot,
38
- },
39
- ];
40
- });
21
+ this.packages = this.getWorkspacePackages() ?? [];
41
22
  return this.packages;
42
23
  }
43
24
  getPackageNames() {
@@ -49,21 +30,49 @@ export class MonorepoPackageSource {
49
30
  }
50
31
  isSourceGraphFile(file) {
51
32
  const normalizedFile = normalizeFileKey(file);
52
- const packagesRoot = normalizeFileKey(path.join(this.root, this.options.packagesDir));
53
- if (!normalizedFile.startsWith(`${packagesRoot}/`)) {
33
+ const packages = this.getPackages();
34
+ if (!packages.some((item) => isPackageFile(item, normalizedFile))) {
54
35
  return false;
55
36
  }
56
- if (normalizedFile.endsWith(aukletConfigFile))
37
+ if (isAukletConfigFile(path.basename(normalizedFile)))
57
38
  return true;
58
39
  if (SOURCE_MODULE_RE.test(normalizedFile))
59
40
  return true;
60
41
  return this.options.styleExtensions.some((extension) => normalizedFile.endsWith(extension));
61
42
  }
62
43
  async getWatchRoots() {
63
- const packagesRoot = path.join(this.root, this.options.packagesDir);
64
- return [
65
- toWatchPath(packagesRoot, '*', 'src'),
66
- toWatchPath(packagesRoot, '*', aukletConfigFile),
67
- ];
44
+ return this.getPackages().flatMap((item) => [
45
+ toWatchPath(item.packageRoot, 'src'),
46
+ ...aukletConfigFiles.map((file) => toWatchPath(item.packageRoot, file)),
47
+ ]);
48
+ }
49
+ getWorkspacePackages() {
50
+ const readWorkspacePackages = this.options.readWorkspacePackages;
51
+ if (!readWorkspacePackages &&
52
+ !fs.existsSync(path.join(this.options.root, 'pnpm-workspace.yaml'))) {
53
+ return null;
54
+ }
55
+ try {
56
+ const readPackages = readWorkspacePackages ?? readPnpmWorkspacePackageInfoSync;
57
+ return readPackages(this.options.root)
58
+ .filter((item) => !this.isWorkspaceRootPackage(item))
59
+ .map((item) => ({
60
+ packageName: item.name,
61
+ packageRoot: normalizeFileKey(item.path),
62
+ }));
63
+ }
64
+ catch (error) {
65
+ throw new Error('[auklet:css] failed to read pnpm workspace packages for Vite monorepo mode.', { cause: error });
66
+ }
67
+ }
68
+ isWorkspaceRootPackage(item) {
69
+ const normalizedPackageRoot = normalizeFileKey(item.path);
70
+ const rawPackageRoot = toPosixPath(path.resolve(item.path));
71
+ return (normalizedPackageRoot === this.root || rawPackageRoot === this.rawRoot);
68
72
  }
69
73
  }
74
+ const isPackageFile = (item, normalizedFile) => {
75
+ const packageRoot = normalizeFileKey(item.packageRoot);
76
+ return (normalizedFile === packageRoot ||
77
+ normalizedFile.startsWith(`${packageRoot}/`));
78
+ };
@@ -1,6 +1,6 @@
1
1
  import fs from 'node:fs';
2
2
  import path from 'node:path';
3
- import { aukletConfigFile, normalizeAukletConfig } from '#auklet/config';
3
+ import { aukletConfigFiles, isAukletConfigFile, normalizeAukletConfig, } from '#auklet/config';
4
4
  import { loadAukletConfig } from '#auklet/configLoader';
5
5
  import { SOURCE_MODULE_RE } from '#auklet/css/constants';
6
6
  import { normalizeFileKey, toWatchPath } from '#auklet/utils';
@@ -27,7 +27,7 @@ export class SinglePackageSource {
27
27
  const normalizedFile = normalizeFileKey(file);
28
28
  if (!this.isInsidePackage(normalizedFile))
29
29
  return false;
30
- if (normalizedFile.endsWith(aukletConfigFile))
30
+ if (isAukletConfigFile(path.basename(normalizedFile)))
31
31
  return true;
32
32
  if (SOURCE_MODULE_RE.test(normalizedFile))
33
33
  return true;
@@ -37,7 +37,7 @@ export class SinglePackageSource {
37
37
  const normalizedConfig = normalizeAukletConfig(await this.loadAukletConfig(this.root, { cacheBust: true }));
38
38
  return [
39
39
  toWatchPath(this.root, normalizedConfig.source),
40
- toWatchPath(this.root, aukletConfigFile),
40
+ ...aukletConfigFiles.map((file) => toWatchPath(this.root, file)),
41
41
  ];
42
42
  }
43
43
  getPackageInfo() {
@@ -9,7 +9,7 @@ export type PackageStyleContext = {
9
9
  context: ResolvedModuleStyleBuildContext;
10
10
  packageContext: StylePackageContext;
11
11
  packageName: string;
12
- configPath: string;
12
+ configPaths: Array<string>;
13
13
  resolver: WorkspaceStyleResolver;
14
14
  sourceRoot: string;
15
15
  styleProcessor: StyleProcessor;
@@ -27,6 +27,9 @@ export declare class ModuleStyleGraphRequestCache {
27
27
  getPackageNames(): string[];
28
28
  isKnownPackageName(packageName: string): boolean;
29
29
  getContext(parsed: PackageStyleId): Promise<PackageStyleContext | {
30
+ context: ResolvedModuleStyleBuildContext;
31
+ configPaths: string[];
32
+ packageContext: StylePackageContext;
30
33
  normalizedConfig: {
31
34
  source: string;
32
35
  output: string;
@@ -54,10 +57,7 @@ export declare class ModuleStyleGraphRequestCache {
54
57
  };
55
58
  };
56
59
  };
57
- context: ResolvedModuleStyleBuildContext;
58
- packageContext: StylePackageContext;
59
60
  packageName: string;
60
- configPath: string;
61
61
  resolver: WorkspaceStyleResolver;
62
62
  sourceRoot: string;
63
63
  styleProcessor: StyleProcessor;
@@ -1,6 +1,6 @@
1
1
  import path from 'node:path';
2
- import { aukletConfigFile, normalizeAukletConfig } from '#auklet/config';
3
- import { loadAukletConfig } from '#auklet/configLoader';
2
+ import { loadAukletConfig, resolveAukletConfigPath, } from '#auklet/configLoader';
3
+ import { aukletConfigFiles, normalizeAukletConfig } from '#auklet/config';
4
4
  import { StylePackageContext } from '#auklet/css/core/stylePackageContext';
5
5
  export class ModuleStyleGraphRequestCache {
6
6
  options;
@@ -31,6 +31,10 @@ export class ModuleStyleGraphRequestCache {
31
31
  if (!stylePackage)
32
32
  return null;
33
33
  const packageRoot = stylePackage.packageRoot;
34
+ const configPath = resolveAukletConfigPath(packageRoot);
35
+ const configPaths = configPath
36
+ ? [configPath]
37
+ : aukletConfigFiles.map((file) => path.join(packageRoot, file));
34
38
  const rawConfig = await this.loadAukletConfig(packageRoot, {
35
39
  cacheBust: true,
36
40
  });
@@ -46,11 +50,11 @@ export class ModuleStyleGraphRequestCache {
46
50
  normalizedConfig,
47
51
  });
48
52
  return {
49
- normalizedConfig,
50
53
  context,
54
+ configPaths,
51
55
  packageContext,
56
+ normalizedConfig,
52
57
  packageName: parsed.packageName,
53
- configPath: path.join(packageRoot, aukletConfigFile),
54
58
  resolver: packageContext.resolver,
55
59
  sourceRoot: packageContext.sourceRoot,
56
60
  styleProcessor: packageContext.styleProcessor,
@@ -53,7 +53,7 @@ export class StyleCodeFactory {
53
53
  async createDependencyStyleCode(context, cache, specifiers, mapSpecifier = (specifier) => specifier) {
54
54
  const results = [];
55
55
  const imports = [];
56
- const watchFiles = [context.configPath];
56
+ const watchFiles = [...context.configPaths];
57
57
  for (const specifier of specifiers) {
58
58
  const outputSpecifier = mapSpecifier(specifier);
59
59
  const parsed = this.parsePackageStyleIdInRequest(outputSpecifier, cache);
@@ -83,7 +83,7 @@ export class StyleCodeFactory {
83
83
  const { themeFiles } = context.packageContext;
84
84
  const targetThemeNames = themeNames ?? context.packageContext.themeNames;
85
85
  const root = context.styleProcessor.createRoot();
86
- const watchFiles = [context.configPath, ...themeFiles.values()];
86
+ const watchFiles = [...context.configPaths, ...themeFiles.values()];
87
87
  const dependencyResults = [];
88
88
  for (const themeName of targetThemeNames) {
89
89
  for (const part of createThemeEntryParts(context.normalizedConfig, themeName, {
@@ -122,7 +122,7 @@ export class StyleCodeFactory {
122
122
  }
123
123
  return {
124
124
  code: root.nodes?.length ? context.styleProcessor.stringify(root) : '',
125
- watchFiles: [context.configPath, ...styleFiles],
125
+ watchFiles: [...context.configPaths, ...styleFiles],
126
126
  };
127
127
  }
128
128
  async createSourceModuleStyleCode(context, cache, stylePath) {
@@ -162,7 +162,7 @@ export class StyleCodeFactory {
162
162
  .filter((code) => code.trim())
163
163
  .join('\n'),
164
164
  watchFiles: [
165
- context.configPath,
165
+ ...context.configPaths,
166
166
  ...styleFiles,
167
167
  ...moduleStyleWatchFiles,
168
168
  ...sourceFiles.filter((file) => /\.(ts|tsx)$/.test(file)),
@@ -1,7 +1,6 @@
1
1
  import type { AukletConfig, ModuleStyleBuildConfig } from '#auklet/types';
2
2
  export interface ModuleStyleGraphOptions {
3
3
  root: string;
4
- packagesDir?: string;
5
4
  mode?: 'monorepo' | 'package';
6
5
  config?: ModuleStyleBuildConfig;
7
6
  loadAukletConfig?: LoadAukletConfig;
@@ -2,7 +2,6 @@ import type { ModuleStyleBuildConfig, ModuleStyleBuildContext } from '#auklet/ty
2
2
  export declare class ModuleStyleWatcher {
3
3
  private readonly config;
4
4
  private readonly context;
5
- private readonly logger?;
6
5
  private timer;
7
6
  private isBuilding;
8
7
  private shouldRebuild;