Skip to content

Commit

Permalink
feat: add repology datasource (#6465)
Browse files Browse the repository at this point in the history
Co-authored-by: Michael Kriese <michael.kriese@visualon.de>
  • Loading branch information
ppmathis and viceice committed Jun 8, 2020
1 parent 8b25686 commit 4513c94
Show file tree
Hide file tree
Showing 6 changed files with 507 additions and 0 deletions.
1 change: 1 addition & 0 deletions lib/datasource/repology/__fixtures__/gcc-defaults.json
@@ -0,0 +1 @@
[{"repo":"astra_stable","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"astra_current","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"debian_oldstable","subrepo":"oldstable/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"debian_stable","subrepo":"stable/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.181","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"debian_testing","subrepo":"testing/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"debian_unstable","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"debian_experimental","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.187","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"deepin_unstable","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.176","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"devuan_1_0","subrepo":"jessie/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.136","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"devuan_2_0","subrepo":"ascii/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"devuan_3_0","subrepo":"beowulf/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.181","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"devuan_4_0","subrepo":"chimaera/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"devuan_unstable","subrepo":"unstable/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"ubuntu_12_04","subrepo":"precise/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.112","maintainers":["debian-gcc@lists.debian.org","aloiret@debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.112ubuntu5"},{"repo":"kali_rolling","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"pardus","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"parrot","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"pureos_amber","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.181","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["misc"],"status":"outdated","origversion":null},{"repo":"pureos_landing","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["misc"],"status":"outdated","origversion":null},{"repo":"raspbian_oldstable","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.168","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":null},{"repo":"raspbian_stable","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.181","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.181+rpi2"},{"repo":"raspbian_testing","subrepo":"main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.185.1+rpi1"},{"repo":"ubuntu_14_04","subrepo":"trusty/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.124","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.124ubuntu6"},{"repo":"ubuntu_16_04","subrepo":"xenial/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.150","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.150ubuntu1"},{"repo":"ubuntu_18_04","subrepo":"bionic/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.176","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.176ubuntu2"},{"repo":"ubuntu_18_04","subrepo":"bionic-updates/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.176","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.176ubuntu2.3"},{"repo":"ubuntu_19_10","subrepo":"eoan/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.185.1ubuntu1"},{"repo":"ubuntu_20_04","subrepo":"focal/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.185.1ubuntu2"},{"repo":"ubuntu_20_10","subrepo":"groovy/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.185.1","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.185.1ubuntu2"},{"repo":"trisquel_6_0","subrepo":"toutatis/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.112","maintainers":["debian-gcc@lists.debian.org","aloiret@debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.112ubuntu5"},{"repo":"trisquel_7_0","subrepo":"belenos/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.124","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.124ubuntu6"},{"repo":"trisquel_8_0","subrepo":"flidas/main","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"1.150","maintainers":["debian-gcc@lists.debian.org","doko@debian.org"],"categories":["devel"],"status":"outdated","origversion":"1.150ubuntu1"},{"repo":"altsisyphus","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"9","maintainers":["bircoph@altlinux.org"],"summary":"ALT Linux Team GNU Compiler Collection Setup","categories":["Development/Other"],"status":"newest","origversion":"9-alt2"},{"repo":"alt_p9","srcname":"gcc-defaults","visiblename":"gcc-defaults","version":"8","maintainers":["glebfm@altlinux.org"],"summary":"ALT Linux Team GNU Compiler Collection Setup","categories":["Development/Other"],"status":"outdated","origversion":"8-alt2"}]
1 change: 1 addition & 0 deletions lib/datasource/repology/__fixtures__/nginx.json

Large diffs are not rendered by default.

178 changes: 178 additions & 0 deletions lib/datasource/repology/__snapshots__/index.spec.ts.snap
@@ -0,0 +1,178 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`datasource/repology/index getReleases returns correct version for binary package 1`] = `
Object {
"releases": Array [
Object {
"version": "1.14.2-2+deb10u1",
},
],
}
`;

exports[`datasource/repology/index getReleases returns correct version for binary package 2`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
]
`;

exports[`datasource/repology/index getReleases returns correct version for source package 1`] = `
Object {
"releases": Array [
Object {
"version": "1.181",
},
],
}
`;

exports[`datasource/repology/index getReleases returns correct version for source package 2`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=gcc-defaults",
},
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=srcname&target_page=api_v1_project&noautoresolve=on&name=gcc-defaults",
},
]
`;

exports[`datasource/repology/index getReleases returns null for empty result 1`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=srcname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
]
`;

exports[`datasource/repology/index getReleases returns null for missing repository or package 1`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=this_should&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=never-exist",
},
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=this_should&name_type=srcname&target_page=api_v1_project&noautoresolve=on&name=never-exist",
},
]
`;

exports[`datasource/repology/index getReleases returns null for unsupported repository 1`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=unsupported_repo&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=unsupported_repo&name_type=srcname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
]
`;

exports[`datasource/repology/index getReleases throws error on unexpected response during binary package lookup 1`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
]
`;

exports[`datasource/repology/index getReleases throws error on unexpected response during source package lookup 1`] = `
Array [
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=binname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
Object {
"headers": Object {
"accept": "application/json",
"accept-encoding": "gzip, deflate",
"host": "repology.org",
"user-agent": "https://github.com/renovatebot/renovate",
},
"method": "GET",
"url": "https://repology.org/tools/project-by?repo=debian_stable&name_type=srcname&target_page=api_v1_project&noautoresolve=on&name=nginx",
},
]
`;

exports[`datasource/repology/index getReleases throws without repository and package name 1`] = `Array []`;
156 changes: 156 additions & 0 deletions lib/datasource/repology/index.spec.ts
@@ -0,0 +1,156 @@
import fs from 'fs';
import * as httpMock from '../../../test/httpMock';
import { getName } from '../../../test/util';
import { DATASOURCE_FAILURE } from '../../constants/error-messages';
import * as ds from '.';

const repologyApiHost = 'https://repology.org/';

type mockResponse = { status: number; body?: string };

const mockProjectBy = (
repo: string,
name: string,
binary: mockResponse,
source: mockResponse
) => {
const endpoint = '/tools/project-by';
const defaultParams = {
target_page: 'api_v1_project',
noautoresolve: 'on',
};

if (binary) {
httpMock
.scope(repologyApiHost)
.get(endpoint)
.query({ ...defaultParams, repo, name, name_type: 'binname' })
.reply(binary.status, binary.body);
}

if (source) {
httpMock
.scope(repologyApiHost)
.get(endpoint)
.query({ ...defaultParams, repo, name, name_type: 'srcname' })
.reply(source.status, source.body);
}
};

const fixtureNginx = fs.readFileSync(
`${__dirname}/__fixtures__/nginx.json`,
'utf8'
);
const fixtureGccDefaults = fs.readFileSync(
`${__dirname}/__fixtures__/gcc-defaults.json`,
'utf8'
);

describe(getName(__filename), () => {
describe('getReleases', () => {
beforeEach(() => {
httpMock.setup();
});

afterEach(() => httpMock.reset());

it('returns null for empty result', async () => {
mockProjectBy(
'debian_stable',
'nginx',
{ status: 200, body: '[]' },
{ status: 200, body: '[]' }
);

expect(
await ds.getReleases({ lookupName: 'debian_stable/nginx' })
).toBeNull();
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('returns null for missing repository or package', async () => {
mockProjectBy(
'this_should',
'never-exist',
{ status: 404 },
{ status: 404 }
);

expect(
await ds.getReleases({ lookupName: 'this_should/never-exist' })
).toBeNull();
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('returns null for unsupported repository', async () => {
mockProjectBy(
'unsupported_repo',
'nginx',
{ status: 403 },
{ status: 403 }
);

expect(
await ds.getReleases({ lookupName: 'unsupported_repo/nginx' })
).toBeNull();
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('throws error on unexpected response during binary package lookup', async () => {
mockProjectBy('debian_stable', 'nginx', { status: 500 }, null);

await expect(
ds.getReleases({ lookupName: 'debian_stable/nginx' })
).rejects.toThrow(DATASOURCE_FAILURE);
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('throws error on unexpected response during source package lookup', async () => {
mockProjectBy('debian_stable', 'nginx', { status: 404 }, { status: 500 });

await expect(
ds.getReleases({ lookupName: 'debian_stable/nginx' })
).rejects.toThrow(DATASOURCE_FAILURE);
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('throws without repository and package name', async () => {
await expect(
ds.getReleases({ lookupName: 'invalid-lookup-name' })
).rejects.toThrow(DATASOURCE_FAILURE);
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('returns correct version for binary package', async () => {
mockProjectBy(
'debian_stable',
'nginx',
{ status: 200, body: fixtureNginx },
null
);

const res = await ds.getReleases({ lookupName: 'debian_stable/nginx' });
expect(res).toMatchSnapshot();
expect(res.releases).toHaveLength(1);
expect(res.releases[0].version).toBeString();
expect(httpMock.getTrace()).toMatchSnapshot();
});

it('returns correct version for source package', async () => {
mockProjectBy(
'debian_stable',
'gcc-defaults',
{ status: 404 },
{ status: 200, body: fixtureGccDefaults }
);

const res = await ds.getReleases({
lookupName: 'debian_stable/gcc-defaults',
});
expect(res).toMatchSnapshot();
expect(res.releases).toHaveLength(1);
expect(res.releases[0].version).toBeString();
expect(httpMock.getTrace()).toMatchSnapshot();
});
});
});

0 comments on commit 4513c94

Please sign in to comment.