/
get-npm-username.test.js
106 lines (75 loc) · 3.41 KB
/
get-npm-username.test.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
"use strict";
jest.mock("npm-registry-fetch");
const fetch = require("npm-registry-fetch");
const { loggingOutput } = require("@lerna-test/helpers/logging-output");
const { getNpmUsername } = require("../lib/get-npm-username");
fetch.json.mockImplementation(() => Promise.resolve({ username: "lerna-test" }));
describe("getNpmUsername", () => {
const origConsoleError = console.error;
beforeEach(() => {
console.error = jest.fn();
});
afterEach(() => {
console.error = origConsoleError;
});
test("fetches whoami endpoint after profile 404", async () => {
fetch.json.mockImplementationOnce(() => {
const err = new Error("third-party profile fail");
err.code = "E404";
return Promise.reject(err);
});
const opts = { registry: "such-config-wow" };
const username = await getNpmUsername(opts);
expect(username).toBe("lerna-test");
expect(fetch.json).toHaveBeenLastCalledWith("/-/whoami", expect.objectContaining({ fetchRetries: 0 }));
});
test("throws an error when successful fetch yields empty username", async () => {
fetch.json.mockImplementationOnce(() => Promise.resolve({ username: undefined }));
await expect(getNpmUsername({ stub: true })).rejects.toThrow(
"You must be logged in to publish packages. Use `npm login` and try again."
);
expect(console.error).not.toHaveBeenCalled();
});
test("logs failure message before throwing validation error", async () => {
fetch.json.mockImplementationOnce(() => {
const err = new Error("legacy npm Enterprise profile fail");
err.code = "E500";
return Promise.reject(err);
});
fetch.json.mockImplementationOnce(() => {
const err = new Error("third-party whoami fail");
err.code = "E404";
return Promise.reject(err);
});
const opts = { registry: "https://registry.npmjs.org/" };
await expect(getNpmUsername(opts)).rejects.toThrow(
"Authentication error. Use `npm whoami` to troubleshoot."
);
expect(console.error).toHaveBeenCalledWith("third-party whoami fail");
});
test("logs failure message when npm returns forbidden response", async () => {
fetch.json.mockImplementationOnce(() => {
const err = new Error("npm profile fail due to insufficient permissions");
err.code = "E403";
return Promise.reject(err);
});
const opts = { registry: "https://registry.npmjs.org/" };
await expect(getNpmUsername(opts)).rejects.toThrow(
"Access verification failed. Ensure that your npm access token has both read and write access, or remove the verifyAccess option to skip this verification. Note that npm automation tokens do NOT have read access (https://docs.npmjs.com/creating-and-viewing-access-tokens)."
);
expect(console.error).toHaveBeenCalledWith("npm profile fail due to insufficient permissions");
});
test("allows third-party registries to fail with a stern warning", async () => {
fetch.json.mockImplementationOnce(() => {
const err = new Error("many third-party registries do not support npm whoami");
err.code = "E401";
return Promise.reject(err);
});
const opts = { registry: "http://my-own-private-idaho.com" };
const username = await getNpmUsername(opts);
expect(username).toBeUndefined();
expect(loggingOutput("warn")).toContain(
"Unable to determine npm username from third-party registry, this command will likely fail soon!"
);
});
});