-
Notifications
You must be signed in to change notification settings - Fork 2.3k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(manager/pep621): support pdm lock files (#22244)
Co-authored-by: Michael Kriese <[email protected]>
- Loading branch information
Showing
8 changed files
with
398 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,105 @@ | ||
import { join } from 'upath'; | ||
import { mockExecAll } from '../../../../test/exec-util'; | ||
import { fs, mockedFunction } from '../../../../test/util'; | ||
import { GlobalConfig } from '../../../config/global'; | ||
import type { RepoGlobalConfig } from '../../../config/types'; | ||
import { getPkgReleases as _getPkgReleases } from '../../datasource'; | ||
import type { UpdateArtifactsConfig } from '../types'; | ||
import { updateArtifacts } from './artifacts'; | ||
|
||
jest.mock('../../../util/fs'); | ||
jest.mock('../../datasource'); | ||
|
||
const getPkgReleases = mockedFunction(_getPkgReleases); | ||
|
||
const config: UpdateArtifactsConfig = {}; | ||
const adminConfig: RepoGlobalConfig = { | ||
localDir: join('/tmp/github/some/repo'), | ||
cacheDir: join('/tmp/cache'), | ||
containerbaseDir: join('/tmp/cache/containerbase'), | ||
}; | ||
|
||
describe('modules/manager/pep621/artifacts', () => { | ||
describe('updateArtifacts()', () => { | ||
it('return null if all processors returns are empty', async () => { | ||
const updatedDeps = [ | ||
{ | ||
packageName: 'dep1', | ||
}, | ||
]; | ||
const result = await updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config, | ||
updatedDeps, | ||
}); | ||
expect(result).toBeNull(); | ||
}); | ||
|
||
it('return processor result', async () => { | ||
const execSnapshots = mockExecAll(); | ||
GlobalConfig.set({ ...adminConfig, binarySource: 'docker' }); | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
fs.readLocalFile.mockResolvedValueOnce('old test content'); | ||
fs.readLocalFile.mockResolvedValueOnce('new test content'); | ||
// pdm | ||
getPkgReleases.mockResolvedValueOnce({ | ||
releases: [{ version: 'v2.6.1' }, { version: 'v2.5.0' }], | ||
}); | ||
|
||
const updatedDeps = [{ packageName: 'dep1' }]; | ||
const result = await updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config: {}, | ||
updatedDeps, | ||
}); | ||
expect(result).toEqual([ | ||
{ | ||
file: { | ||
contents: 'new test content', | ||
path: 'pdm.lock', | ||
type: 'addition', | ||
}, | ||
}, | ||
]); | ||
expect(execSnapshots).toMatchObject([ | ||
{ | ||
cmd: 'docker pull containerbase/sidecar', | ||
options: { | ||
encoding: 'utf-8', | ||
}, | ||
}, | ||
{ | ||
cmd: 'docker ps --filter name=renovate_sidecar -aq', | ||
options: { | ||
encoding: 'utf-8', | ||
}, | ||
}, | ||
{ | ||
cmd: | ||
'docker run --rm --name=renovate_sidecar --label=renovate_child ' + | ||
'-v "/tmp/github/some/repo":"/tmp/github/some/repo" ' + | ||
'-v "/tmp/cache":"/tmp/cache" ' + | ||
'-e BUILDPACK_CACHE_DIR ' + | ||
'-e CONTAINERBASE_CACHE_DIR ' + | ||
'-w "/tmp/github/some/repo" ' + | ||
'containerbase/sidecar ' + | ||
'bash -l -c "' + | ||
'install-tool pdm v2.5.0 ' + | ||
'&& ' + | ||
'pdm update dep1' + | ||
'"', | ||
options: { | ||
cwd: '/tmp/github/some/repo', | ||
encoding: 'utf-8', | ||
env: { | ||
BUILDPACK_CACHE_DIR: '/tmp/cache/containerbase', | ||
CONTAINERBASE_CACHE_DIR: '/tmp/cache/containerbase', | ||
}, | ||
}, | ||
}, | ||
]); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
import is from '@sindresorhus/is'; | ||
import { writeLocalFile } from '../../../util/fs'; | ||
import type { UpdateArtifact, UpdateArtifactsResult } from '../types'; | ||
import { processors } from './processors'; | ||
|
||
export async function updateArtifacts( | ||
updateArtifact: UpdateArtifact | ||
): Promise<UpdateArtifactsResult[] | null> { | ||
const { packageFileName, newPackageFileContent } = updateArtifact; | ||
|
||
await writeLocalFile(packageFileName, newPackageFileContent); | ||
|
||
// process specific tool sets | ||
const result: UpdateArtifactsResult[] = []; | ||
for (const processor of processors) { | ||
const artifactUpdates = await processor.updateArtifacts(updateArtifact); | ||
if (is.array(artifactUpdates)) { | ||
result.push(...artifactUpdates); | ||
} | ||
} | ||
|
||
return result.length > 0 ? result : null; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,8 +1,11 @@ | ||
import { PypiDatasource } from '../../datasource/pypi'; | ||
export { extractPackageFile } from './extract'; | ||
export { updateArtifacts } from './artifacts'; | ||
|
||
export const supportedDatasources = [PypiDatasource.id]; | ||
|
||
export const supportsLockFileMaintenance = true; | ||
|
||
export const defaultConfig = { | ||
fileMatch: ['(^|/)pyproject\\.toml$'], | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,172 @@ | ||
import { join } from 'upath'; | ||
import { mockExecAll } from '../../../../../test/exec-util'; | ||
import { fs, mockedFunction } from '../../../../../test/util'; | ||
import { GlobalConfig } from '../../../../config/global'; | ||
import type { RepoGlobalConfig } from '../../../../config/types'; | ||
import { getPkgReleases as _getPkgReleases } from '../../../datasource'; | ||
import type { UpdateArtifactsConfig } from '../../types'; | ||
import { PdmProcessor } from './pdm'; | ||
|
||
jest.mock('../../../../util/fs'); | ||
jest.mock('../../../datasource'); | ||
|
||
const getPkgReleases = mockedFunction(_getPkgReleases); | ||
|
||
const config: UpdateArtifactsConfig = {}; | ||
const adminConfig: RepoGlobalConfig = { | ||
localDir: join('/tmp/github/some/repo'), | ||
cacheDir: join('/tmp/cache'), | ||
containerbaseDir: join('/tmp/cache/containerbase'), | ||
}; | ||
|
||
const processor = new PdmProcessor(); | ||
|
||
describe('modules/manager/pep621/processors/pdm', () => { | ||
describe('updateArtifacts()', () => { | ||
it('return null if there is no lock file', async () => { | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
const updatedDeps = [{ packageName: 'dep1' }]; | ||
const result = await processor.updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config, | ||
updatedDeps, | ||
}); | ||
expect(result).toBeNull(); | ||
}); | ||
|
||
it('return null if the lock file is unchanged', async () => { | ||
const execSnapshots = mockExecAll(); | ||
GlobalConfig.set({ ...adminConfig, binarySource: 'docker' }); | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
fs.readLocalFile.mockResolvedValueOnce('test content'); | ||
fs.readLocalFile.mockResolvedValueOnce('test content'); | ||
// pdm | ||
getPkgReleases.mockResolvedValueOnce({ | ||
releases: [{ version: 'v2.6.1' }, { version: 'v2.5.0' }], | ||
}); | ||
|
||
const updatedDeps = [{ packageName: 'dep1' }]; | ||
const result = await processor.updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config: {}, | ||
updatedDeps, | ||
}); | ||
expect(result).toBeNull(); | ||
expect(execSnapshots).toMatchObject([ | ||
{ | ||
cmd: 'docker pull containerbase/sidecar', | ||
}, | ||
{ | ||
cmd: 'docker ps --filter name=renovate_sidecar -aq', | ||
}, | ||
{ | ||
cmd: | ||
'docker run --rm --name=renovate_sidecar --label=renovate_child ' + | ||
'-v "/tmp/github/some/repo":"/tmp/github/some/repo" ' + | ||
'-v "/tmp/cache":"/tmp/cache" ' + | ||
'-e BUILDPACK_CACHE_DIR ' + | ||
'-e CONTAINERBASE_CACHE_DIR ' + | ||
'-w "/tmp/github/some/repo" ' + | ||
'containerbase/sidecar ' + | ||
'bash -l -c "' + | ||
'install-tool pdm v2.5.0 ' + | ||
'&& ' + | ||
'pdm update dep1' + | ||
'"', | ||
}, | ||
]); | ||
}); | ||
|
||
it('returns artifact error', async () => { | ||
const execSnapshots = mockExecAll(); | ||
GlobalConfig.set({ ...adminConfig, binarySource: 'docker' }); | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
fs.readLocalFile.mockImplementationOnce(() => { | ||
throw new Error('test error'); | ||
}); | ||
|
||
const updatedDeps = [{ packageName: 'dep1' }]; | ||
const result = await processor.updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config: {}, | ||
updatedDeps, | ||
}); | ||
expect(result).toEqual([ | ||
{ artifactError: { lockFile: 'pdm.lock', stderr: 'test error' } }, | ||
]); | ||
expect(execSnapshots).toEqual([]); | ||
}); | ||
|
||
it('return update dep update', async () => { | ||
const execSnapshots = mockExecAll(); | ||
GlobalConfig.set(adminConfig); | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
fs.readLocalFile.mockResolvedValueOnce('test content'); | ||
fs.readLocalFile.mockResolvedValueOnce('changed test content'); | ||
// pdm | ||
getPkgReleases.mockResolvedValueOnce({ | ||
releases: [{ version: 'v2.6.1' }, { version: 'v2.5.0' }], | ||
}); | ||
|
||
const updatedDeps = [{ packageName: 'dep1' }, { packageName: 'dep2' }]; | ||
const result = await processor.updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config: {}, | ||
updatedDeps, | ||
}); | ||
expect(result).toEqual([ | ||
{ | ||
file: { | ||
contents: 'changed test content', | ||
path: 'pdm.lock', | ||
type: 'addition', | ||
}, | ||
}, | ||
]); | ||
expect(execSnapshots).toMatchObject([ | ||
{ | ||
cmd: 'pdm update dep1 dep2', | ||
}, | ||
]); | ||
}); | ||
|
||
it('return update on lockfileMaintenance', async () => { | ||
const execSnapshots = mockExecAll(); | ||
GlobalConfig.set(adminConfig); | ||
fs.getSiblingFileName.mockReturnValueOnce('pdm.lock'); | ||
fs.readLocalFile.mockResolvedValueOnce('test content'); | ||
fs.readLocalFile.mockResolvedValueOnce('changed test content'); | ||
// pdm | ||
getPkgReleases.mockResolvedValueOnce({ | ||
releases: [{ version: 'v2.6.1' }, { version: 'v2.5.0' }], | ||
}); | ||
|
||
const result = await processor.updateArtifacts({ | ||
packageFileName: 'pyproject.toml', | ||
newPackageFileContent: '', | ||
config: { | ||
updateType: 'lockFileMaintenance', | ||
}, | ||
updatedDeps: [], | ||
}); | ||
expect(result).toEqual([ | ||
{ | ||
file: { | ||
contents: 'changed test content', | ||
path: 'pdm.lock', | ||
type: 'addition', | ||
}, | ||
}, | ||
]); | ||
expect(execSnapshots).toMatchObject([ | ||
{ | ||
cmd: 'pdm update', | ||
}, | ||
]); | ||
}); | ||
}); | ||
}); |
Oops, something went wrong.