Skip to content

Commit

Permalink
feat(datasource/npm): massage non compliant npm repo strings (renovat…
Browse files Browse the repository at this point in the history
  • Loading branch information
olegkrivtsov committed Sep 23, 2021
1 parent ce82432 commit 4aa5cdc
Show file tree
Hide file tree
Showing 2 changed files with 138 additions and 0 deletions.
117 changes: 117 additions & 0 deletions lib/datasource/npm/get.spec.ts
Expand Up @@ -230,4 +230,121 @@ describe('datasource/npm/get', () => {

expect(httpMock.getTrace()).toMatchSnapshot();
});

it('massages non-compliant repository urls', async () => {
setNpmrc('registry=https://test.org\n_authToken=XXX');

httpMock
.scope('https://test.org')
.get('/@neutrinojs%2Freact')
.reply(200, {
name: '@neutrinojs/react',
repository: {
type: 'git',
url: 'https://github.com/neutrinojs/neutrino/tree/master/packages/react',
},
versions: { '1.0.0': {} },
'dist-tags': { latest: '1.0.0' },
});

const dep = await getDependency('@neutrinojs/react');

expect(dep.sourceUrl).toBe('https://github.com/neutrinojs/neutrino');
expect(dep.sourceDirectory).toBe('packages/react');

expect(httpMock.getTrace()).toMatchInlineSnapshot(`
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate, br",
"authorization": "Bearer XXX",
"host": "test.org",
"user-agent": "RenovateBot/0.0.0-semantic-release (https://github.com/renovatebot/renovate)",
},
"method": "GET",
"url": "https://test.org/@neutrinojs%2Freact",
},
]
`);
});

it('warns about repo directory override', async () => {
setNpmrc('registry=https://test.org\n_authToken=XXX');

httpMock
.scope('https://test.org')
.get('/@neutrinojs%2Freact')
.reply(200, {
name: '@neutrinojs/react',
repository: {
type: 'git',
url: 'https://github.com/neutrinojs/neutrino/tree/master/packages/react',
directory: 'path/to/directory',
},
versions: { '1.0.0': {} },
'dist-tags': { latest: '1.0.0' },
});

const dep = await getDependency('@neutrinojs/react');

expect(dep.sourceUrl).toBe('https://github.com/neutrinojs/neutrino');
expect(dep.sourceDirectory).toBe('packages/react');

expect(httpMock.getTrace()).toMatchInlineSnapshot(`
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate, br",
"authorization": "Bearer XXX",
"host": "test.org",
"user-agent": "RenovateBot/0.0.0-semantic-release (https://github.com/renovatebot/renovate)",
},
"method": "GET",
"url": "https://test.org/@neutrinojs%2Freact",
},
]
`);
});

it('does not massage non-github non-compliant repository urls', async () => {
setNpmrc('registry=https://test.org\n_authToken=XXX');

httpMock
.scope('https://test.org')
.get('/@neutrinojs%2Freact')
.reply(200, {
name: '@neutrinojs/react',
repository: {
type: 'git',
url: 'https://bitbucket.org/neutrinojs/neutrino/tree/master/packages/react',
},
versions: { '1.0.0': {} },
'dist-tags': { latest: '1.0.0' },
});

const dep = await getDependency('@neutrinojs/react');

expect(dep.sourceUrl).toBe(
'https://bitbucket.org/neutrinojs/neutrino/tree/master/packages/react'
);
expect(dep.sourceDirectory).toBeUndefined();

expect(httpMock.getTrace()).toMatchInlineSnapshot(`
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate, br",
"authorization": "Bearer XXX",
"host": "test.org",
"user-agent": "RenovateBot/0.0.0-semantic-release (https://github.com/renovatebot/renovate)",
},
"method": "GET",
"url": "https://test.org/@neutrinojs%2Freact",
},
]
`);
});
});
21 changes: 21 additions & 0 deletions lib/datasource/npm/get.ts
Expand Up @@ -80,6 +80,7 @@ export async function getDependency(
sourceUrl = res.repository.url;
}
}

// Simplify response before caching and returning
const dep: NpmDependency = {
name: res.name,
Expand All @@ -93,6 +94,26 @@ export async function getDependency(
if (res.repository?.directory) {
dep.sourceDirectory = res.repository.directory;
}

// Massage the repository URL for non-compliant strings for github (see issue #4610)
// Remove the non-compliant segments of path, so the URL looks like "<scheme>://<domain>/<vendor>/<repo>"
// and add directory to the repository
const sourceUrlCopy = `${sourceUrl}`;
const sourceUrlSplit: string[] = sourceUrlCopy.split('/');

if (sourceUrlSplit.length > 7 && sourceUrlSplit[2] === 'github.com') {
if (dep.sourceDirectory) {
logger.debug(
{ dependency: packageName },
`Ambiguity: dependency has the repository URL path and repository/directory set at once; have to override repository/directory`
);
}
dep.sourceUrl = sourceUrlSplit.slice(0, 5).join('/');
dep.sourceDirectory = sourceUrlSplit
.slice(7, sourceUrlSplit.length)
.join('/');
}

if (latestVersion.deprecated) {
dep.deprecationMessage = `On registry \`${registryUrl}\`, the "latest" version of dependency \`${packageName}\` has the following deprecation notice:\n\n\`${latestVersion.deprecated}\`\n\nMarking the latest version of an npm package as deprecated results in the entire package being considered deprecated, so contact the package author you think this is a mistake.`;
dep.deprecationSource = id;
Expand Down

0 comments on commit 4aa5cdc

Please sign in to comment.