Skip to content

Commit 77b8b52

Browse files
hindicatorarcanis
andauthored
add readme to publishBody (#5374)
* add readme to publishBody * clean test with example * add fallback to project name * cleaning * fix getPublishAccess * cleaning * remove unused parameter * Tweaks * Tweaks tests * Versions * Update publish.test.ts --------- Co-authored-by: Maël Nison <[email protected]>
1 parent bf9a113 commit 77b8b52

File tree

4 files changed

+103
-25
lines changed

4 files changed

+103
-25
lines changed

.yarn/versions/d25ca604.yml

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
releases:
2+
"@yarnpkg/cli": patch
3+
"@yarnpkg/plugin-npm": patch
4+
5+
declined:
6+
- "@yarnpkg/plugin-compat"
7+
- "@yarnpkg/plugin-constraints"
8+
- "@yarnpkg/plugin-dlx"
9+
- "@yarnpkg/plugin-essentials"
10+
- "@yarnpkg/plugin-init"
11+
- "@yarnpkg/plugin-interactive-tools"
12+
- "@yarnpkg/plugin-nm"
13+
- "@yarnpkg/plugin-npm-cli"
14+
- "@yarnpkg/plugin-pack"
15+
- "@yarnpkg/plugin-patch"
16+
- "@yarnpkg/plugin-pnp"
17+
- "@yarnpkg/plugin-pnpm"
18+
- "@yarnpkg/plugin-stage"
19+
- "@yarnpkg/plugin-typescript"
20+
- "@yarnpkg/plugin-version"
21+
- "@yarnpkg/plugin-workspace-tools"
22+
- "@yarnpkg/builder"
23+
- "@yarnpkg/core"
24+
- "@yarnpkg/doctor"

packages/acceptance-tests/pkg-tests-core/sources/utils/tests.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -458,6 +458,9 @@ export const startPackageServer = ({type}: { type: keyof typeof packageServerUrl
458458
return processError(response, 401, `Invalid`);
459459
}
460460

461+
if (typeof body.readme !== `string` && name === `readme-required`)
462+
return processError(response, 400, `Missing readme`);
463+
461464
const [version] = Object.keys(body.versions);
462465
if (!body.versions[version].gitHead && name === `githead-required`)
463466
return processError(response, 400, `Missing gitHead`);

packages/acceptance-tests/pkg-tests-specs/sources/commands/publish.test.ts

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
import {npath, xfs} from '@yarnpkg/fslib';
2+
13
export {};
24

35
const {
@@ -68,4 +70,20 @@ describe(`publish`, () => {
6870
},
6971
})).resolves.toBeTruthy();
7072
}));
73+
74+
test(`should publish a package with the readme content`, makeTemporaryEnv({
75+
name: `readme-required`,
76+
version: `1.0.0`,
77+
}, async ({path, run, source}) => {
78+
await run(`install`);
79+
80+
const readmePath = npath.toPortablePath(`${path}/README.md`);
81+
await xfs.writeFilePromise(readmePath, `# title\n`);
82+
83+
await run(`npm`, `publish`, {
84+
env: {
85+
YARN_NPM_AUTH_TOKEN: validLogins.fooUser.npmAuthToken,
86+
},
87+
});
88+
}));
7189
});

packages/plugin-npm/sources/npmPublishUtils.ts

Lines changed: 58 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,21 @@
1-
import {execUtils} from '@yarnpkg/core';
2-
import {Workspace, structUtils} from '@yarnpkg/core';
3-
import {PortablePath} from '@yarnpkg/fslib';
4-
import {packUtils} from '@yarnpkg/plugin-pack';
5-
import {createHash} from 'crypto';
6-
import ssri from 'ssri';
7-
import {URL} from 'url';
8-
9-
import {normalizeRegistry} from './npmConfigUtils';
10-
11-
export async function makePublishBody(workspace: Workspace, buffer: Buffer, {access, tag, registry, gitHead}: {access: string | undefined, tag: string, registry: string, gitHead?: string}) {
12-
const configuration = workspace.project.configuration;
13-
1+
import {execUtils, Ident} from '@yarnpkg/core';
2+
import {Workspace, structUtils} from '@yarnpkg/core';
3+
import {PortablePath, xfs, npath} from '@yarnpkg/fslib';
4+
import {packUtils} from '@yarnpkg/plugin-pack';
5+
import {createHash} from 'crypto';
6+
import ssri from 'ssri';
7+
import {URL} from 'url';
8+
9+
import {normalizeRegistry} from './npmConfigUtils';
10+
11+
type PublishAdditionalParams = {
12+
access: string | undefined;
13+
tag: string;
14+
registry: string;
15+
gitHead?: string;
16+
};
17+
18+
export async function makePublishBody(workspace: Workspace, buffer: Buffer, {access, tag, registry, gitHead}: PublishAdditionalParams) {
1419
const ident = workspace.manifest.name!;
1520
const version = workspace.manifest.version!;
1621

@@ -19,17 +24,8 @@ export async function makePublishBody(workspace: Workspace, buffer: Buffer, {acc
1924
const shasum = createHash(`sha1`).update(buffer).digest(`hex`);
2025
const integrity = ssri.fromData(buffer).toString();
2126

22-
if (typeof access === `undefined`) {
23-
if (workspace.manifest.publishConfig && typeof workspace.manifest.publishConfig.access === `string`) {
24-
access = workspace.manifest.publishConfig.access;
25-
} else if (configuration.get(`npmPublishAccess`) !== null) {
26-
access = configuration.get(`npmPublishAccess`)!;
27-
} else if (ident.scope) {
28-
access = `restricted`;
29-
} else {
30-
access = `public`;
31-
}
32-
}
27+
const publishAccess = access ?? getPublishAccess(workspace, ident);
28+
const readmeContent = await getReadmeContent(workspace);
3329

3430
const raw = await packUtils.genPackageManifest(workspace);
3531

@@ -50,7 +46,7 @@ export async function makePublishBody(workspace: Workspace, buffer: Buffer, {acc
5046
},
5147
},
5248
name,
53-
access,
49+
access: publishAccess,
5450

5551
[`dist-tags`]: {
5652
[tag]: version,
@@ -75,6 +71,7 @@ export async function makePublishBody(workspace: Workspace, buffer: Buffer, {acc
7571
},
7672
},
7773
},
74+
readme: readmeContent,
7875
};
7976
}
8077

@@ -88,3 +85,39 @@ export async function getGitHead(workingDir: PortablePath) {
8885
return undefined;
8986
}
9087
}
88+
89+
export function getPublishAccess(workspace: Workspace, ident: Ident): string {
90+
const configuration = workspace.project.configuration;
91+
92+
if (workspace.manifest.publishConfig && typeof workspace.manifest.publishConfig.access === `string`)
93+
return workspace.manifest.publishConfig.access;
94+
95+
if (configuration.get(`npmPublishAccess`) !== null)
96+
return configuration.get(`npmPublishAccess`)!;
97+
98+
const access = ident.scope
99+
? `restricted`
100+
: `public`;
101+
102+
return access;
103+
}
104+
105+
export async function getReadmeContent(workspace: Workspace): Promise<string> {
106+
const readmePath = npath.toPortablePath(`${workspace.cwd}/README.md`);
107+
108+
const ident = workspace.manifest.name!;
109+
const packageName = structUtils.stringifyIdent(ident);
110+
111+
let readme = `# ${packageName}\n`;
112+
try {
113+
readme = await xfs.readFilePromise(readmePath, `utf8`);
114+
} catch (err) {
115+
if (err.code === `ENOENT`) {
116+
return readme;
117+
} else {
118+
throw err;
119+
}
120+
}
121+
122+
return readme;
123+
}

0 commit comments

Comments
 (0)