auklet 0.0.23 → 0.0.25

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/README.md CHANGED
@@ -125,10 +125,16 @@ Publish controls stay on CLI flags:
125
125
  auk publish --filter @scope/ui
126
126
  auk publish --version patch --dry-run
127
127
  auk publish --no-format
128
+ auk publish --otp 123456
128
129
  ```
129
130
 
130
131
  `--no-format` disables auklet's publish output formatter for that run. It is not
131
132
  configured in `package.json`.
133
+ Before writing versions, auklet checks npm authentication from each target
134
+ package directory. Package-local `.npmrc` files and
135
+ `package.json#publishConfig.registry` are respected.
136
+ `--otp` is forwarded to `pnpm publish` for npm accounts or organizations that
137
+ require publish 2FA. In CI, prefer an npm automation token.
132
138
 
133
139
  ## Configuration
134
140
 
@@ -3,8 +3,7 @@ import { createRequire } from 'node:module';
3
3
  import { execa } from 'execa';
4
4
  const require = createRequire(import.meta.url);
5
5
  const tsdownRunFile = require.resolve('tsdown/run');
6
- const currentExtension = import.meta.url.endsWith('.ts') ? 'ts' : 'js';
7
- const defaultConfigFile = fileURLToPath(new URL(`./tsdownConfig.${currentExtension}`, import.meta.url));
6
+ const defaultConfigFile = fileURLToPath(new URL('./tsdownConfig.js', import.meta.url));
8
7
  export function hasTsdownConfigArg(args) {
9
8
  return args.some((arg, index) => arg === '--no-config' ||
10
9
  arg === '-c' ||
@@ -1,4 +1,4 @@
1
- import { parseModuleId } from '#auklet/build/tsdown/parseModuleId';
1
+ import { parseModuleId } from 'conditional-export';
2
2
  import { createScopedAukletLogger } from '#auklet/logger';
3
3
  const logger = createScopedAukletLogger('build');
4
4
  const getExternal = (names) => {
@@ -6,7 +6,10 @@ export declare function ensurePnpm(): Promise<string>;
6
6
  export declare function readPnpmWorkspacePackages(root: string): Promise<WorkspacePackage[]>;
7
7
  export declare function runPnpmBuild(packageRoot: string): Promise<void>;
8
8
  export declare function runPnpmPublish(packageRoot: string, args: Array<string>): Promise<void>;
9
- export declare function runPnpmWhoami(root: string): Promise<string>;
9
+ export declare function runPnpmWhoami(packageRoot: string, options?: {
10
+ packageName?: string;
11
+ registry?: string;
12
+ }): Promise<string>;
10
13
  export declare function runPnpmOwnerAdd(packageName: string, user: string, options: {
11
14
  cwd: string;
12
15
  otp?: string;
@@ -5,7 +5,8 @@ import { readPnpmWorkspacePackageInfo } from '#auklet/workspace/packages';
5
5
  const supportedPnpmRange = '>=10.0.0';
6
6
  export class NpmPublishAuthenticationError extends Error {
7
7
  constructor(packageRoot) {
8
- super(`[publish] pnpm publish failed at ${packageRoot}: npm publish requires additional authentication.`);
8
+ super(`[publish] pnpm publish failed at ${packageRoot}: ` +
9
+ `npm publish requires additional authentication.`);
9
10
  }
10
11
  }
11
12
  const runPnpm = async (args, options = {}) => {
@@ -66,12 +67,17 @@ export async function runPnpmPublish(packageRoot, args) {
66
67
  throw new Error(`[publish] pnpm publish failed at ${packageRoot}.`);
67
68
  }
68
69
  }
69
- export async function runPnpmWhoami(root) {
70
- const result = await runPnpm(['whoami'], {
71
- cwd: root,
70
+ export async function runPnpmWhoami(packageRoot, options = {}) {
71
+ const args = ['whoami'];
72
+ if (options.registry)
73
+ args.push('--registry', options.registry);
74
+ const result = await runPnpm(args, {
75
+ cwd: packageRoot,
72
76
  });
73
77
  if (result.exitCode) {
74
- throw new Error('[publish] npm authentication is required before publishing.\n' +
78
+ const target = options.packageName ? ` for ${options.packageName}` : '';
79
+ const registry = options.registry ? ` at ${options.registry}` : '';
80
+ throw new Error(`[publish] npm authentication is required${target}${registry} before publishing.\n` +
75
81
  '[publish] Run `pnpm login` or configure an npm token before retrying.');
76
82
  }
77
83
  return String(result.stdout ?? '').trim();
@@ -1,3 +1,4 @@
1
+ import { isPlainObject, isString } from 'aidly';
1
2
  import { PnpmPublishApi } from '#auklet/publish/api/pnpmPublishApi';
2
3
  import { runPnpmWhoami } from '#auklet/publish/api/pnpmApi';
3
4
  import { logAuthenticationError } from '#auklet/publish/runner/packagePublisher';
@@ -16,7 +17,18 @@ export class PublishPreflight {
16
17
  async verifyAuthentication(plan) {
17
18
  if (plan.dryRun)
18
19
  return;
19
- await runPnpmWhoami(plan.root);
20
+ const checked = new Set();
21
+ for (const target of plan.targets) {
22
+ const registry = getPublishRegistry(target.packageJson.publishConfig);
23
+ const key = `${target.packageRoot}\n${registry ?? ''}`;
24
+ if (checked.has(key))
25
+ continue;
26
+ await runPnpmWhoami(target.packageRoot, {
27
+ packageName: target.packageName,
28
+ registry,
29
+ });
30
+ checked.add(key);
31
+ }
20
32
  }
21
33
  async verifyPnpmPublishDryRun(plan) {
22
34
  const options = {
@@ -34,3 +46,9 @@ export class PublishPreflight {
34
46
  }
35
47
  }
36
48
  }
49
+ const getPublishRegistry = (publishConfig) => {
50
+ if (!isPlainObject(publishConfig))
51
+ return undefined;
52
+ const registry = Reflect.get(publishConfig, 'registry');
53
+ return isString(registry) && registry.length > 0 ? registry : undefined;
54
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "auklet",
3
- "version": "0.0.23",
3
+ "version": "0.0.25",
4
4
  "type": "module",
5
5
  "author": "chentao.arthur",
6
6
  "description": "Build utilities for TypeScript packages and module CSS output.",
@@ -1,6 +0,0 @@
1
- export declare function parseModuleId(moduleId: string): {
2
- name: string;
3
- path: string;
4
- version: string;
5
- raw: string;
6
- };
@@ -1,100 +0,0 @@
1
- export function parseModuleId(moduleId) {
2
- let name = '';
3
- let path = '';
4
- let version = '';
5
- let buf = '';
6
- let slash = 0;
7
- let isScope = false;
8
- const set = (type) => {
9
- if (type === 'path')
10
- path = buf;
11
- if (type === 'name')
12
- name = buf;
13
- if (type === 'version')
14
- version = buf;
15
- buf = '';
16
- };
17
- const setValueBySlash = (char) => {
18
- if (!name) {
19
- set('name');
20
- }
21
- else if (!version) {
22
- set('version');
23
- }
24
- else {
25
- buf += char;
26
- }
27
- };
28
- for (let i = 0, l = moduleId.length; i < l; i++) {
29
- const char = moduleId[i];
30
- if (char === '@') {
31
- if (i === 0) {
32
- buf += char;
33
- isScope = true;
34
- }
35
- else if (!name) {
36
- if (isScope) {
37
- if (slash === 1 && buf[buf.length - 1] !== '/') {
38
- set('name');
39
- }
40
- else {
41
- buf += char;
42
- }
43
- }
44
- else {
45
- set('name');
46
- }
47
- }
48
- else {
49
- buf += char;
50
- }
51
- }
52
- else if (char === '/') {
53
- if (slash === 0) {
54
- if (!isScope) {
55
- setValueBySlash(char);
56
- }
57
- buf += char;
58
- }
59
- else if (slash === 1) {
60
- if (isScope) {
61
- setValueBySlash(char);
62
- }
63
- buf += char;
64
- }
65
- else {
66
- buf += char;
67
- }
68
- slash++;
69
- }
70
- else {
71
- buf += char;
72
- }
73
- }
74
- if (!name) {
75
- set('name');
76
- }
77
- else if (!version) {
78
- moduleId[name.length] === '@' ? set('version') : set('path');
79
- }
80
- else if (!path) {
81
- set('path');
82
- }
83
- if (path) {
84
- path = `.${path}`;
85
- }
86
- // `@vue` -> ''
87
- // `@vue/` -> ''
88
- // `@vue//` -> ''
89
- if (isScope && (slash === 0 || name[name.length - 1] === '/')) {
90
- name = '';
91
- path = '';
92
- version = '';
93
- }
94
- return {
95
- name,
96
- path,
97
- version,
98
- raw: moduleId,
99
- };
100
- }