mirror of https://github.com/actions/setup-python
Add support to .tool-version file format
Create a function to parse tool-version (asdf-vm) format, add the associated tests, and updated the documentation Ticket-ID: #571
This commit is contained in:
parent
bd6b4b6205
commit
892baae68b
|
@ -1,6 +1,7 @@
|
||||||
import * as cache from '@actions/cache';
|
import * as cache from '@actions/cache';
|
||||||
import * as core from '@actions/core';
|
import * as core from '@actions/core';
|
||||||
import {
|
import {
|
||||||
|
parsePythonVersionFile,
|
||||||
validateVersion,
|
validateVersion,
|
||||||
validatePythonVersionFormatForPyPy,
|
validatePythonVersionFormatForPyPy,
|
||||||
isCacheFeatureAvailable
|
isCacheFeatureAvailable
|
||||||
|
@ -9,6 +10,20 @@ import {
|
||||||
jest.mock('@actions/cache');
|
jest.mock('@actions/cache');
|
||||||
jest.mock('@actions/core');
|
jest.mock('@actions/core');
|
||||||
|
|
||||||
|
describe('parsePythonVersionFile', () => {
|
||||||
|
it('handle the content of a .python-version file', () => {
|
||||||
|
expect(parsePythonVersionFile('3.6')).toEqual('3.6')
|
||||||
|
});
|
||||||
|
|
||||||
|
it('trims extra spaces at the end of the content', () => {
|
||||||
|
expect(parsePythonVersionFile('3.7 ')).toEqual('3.7')
|
||||||
|
});
|
||||||
|
|
||||||
|
it('parses correctly the content of .tool-version files', () => {
|
||||||
|
expect(parsePythonVersionFile('python 3.7')).toEqual('3.7')
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('validatePythonVersionFormatForPyPy', () => {
|
describe('validatePythonVersionFormatForPyPy', () => {
|
||||||
it.each([
|
it.each([
|
||||||
['3.6', true],
|
['3.6', true],
|
||||||
|
|
|
@ -239,9 +239,10 @@ jobs:
|
||||||
|
|
||||||
## Using the `python-version-file` input
|
## Using the `python-version-file` input
|
||||||
|
|
||||||
`setup-python` action can read Python or PyPy version from a version file. `python-version-file` input is used for specifying the path to the version file. If the file that was supplied to `python-version-file` input doesn't exist, the action will fail with error.
|
The python-version-file input accepts a path to a file containing the version of Python to be used by a project, for example .python-version, or .tool-versions.
|
||||||
|
If both the python-version and the python-version-file inputs are provided then the python-version input is used.
|
||||||
|
|
||||||
>In case both `python-version` and `python-version-file` inputs are supplied, the `python-version-file` input will be ignored due to its lower priority.
|
> The action will search for the python version file relative to the repository root.
|
||||||
|
|
||||||
```yaml
|
```yaml
|
||||||
steps:
|
steps:
|
||||||
|
|
|
@ -5,7 +5,7 @@ import * as path from 'path';
|
||||||
import * as os from 'os';
|
import * as os from 'os';
|
||||||
import fs from 'fs';
|
import fs from 'fs';
|
||||||
import {getCacheDistributor} from './cache-distributions/cache-factory';
|
import {getCacheDistributor} from './cache-distributions/cache-factory';
|
||||||
import {isCacheFeatureAvailable, logWarning, IS_MAC} from './utils';
|
import {parsePythonVersionFile, isCacheFeatureAvailable, logWarning, IS_MAC} from './utils';
|
||||||
|
|
||||||
function isPyPyVersion(versionSpec: string) {
|
function isPyPyVersion(versionSpec: string) {
|
||||||
return versionSpec.startsWith('pypy');
|
return versionSpec.startsWith('pypy');
|
||||||
|
@ -37,20 +37,29 @@ function resolveVersionInput() {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (versionFile) {
|
if (versionFile) {
|
||||||
if (!fs.existsSync(versionFile)) {
|
const versionFilePath = path.join(
|
||||||
|
process.env.GITHUB_WORKSPACE!,
|
||||||
|
versionFile
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!fs.existsSync(versionFilePath)) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
`The specified python version file at: ${versionFile} doesn't exist.`
|
`The specified python version file at: ${versionFilePath} doesn't exist.`
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
const version = fs.readFileSync(versionFile, 'utf8');
|
|
||||||
|
const version = parsePythonVersionFile(fs.readFileSync(versionFilePath, 'utf8'));
|
||||||
core.info(`Resolved ${versionFile} as ${version}`);
|
core.info(`Resolved ${versionFile} as ${version}`);
|
||||||
|
|
||||||
return [version];
|
return [version];
|
||||||
}
|
}
|
||||||
|
|
||||||
logWarning(
|
logWarning(
|
||||||
"Neither 'python-version' nor 'python-version-file' inputs were supplied. Attempting to find '.python-version' file."
|
"Neither 'python-version' nor 'python-version-file' inputs were supplied. Attempting to find '.python-version' file."
|
||||||
);
|
);
|
||||||
|
|
||||||
versionFile = '.python-version';
|
versionFile = '.python-version';
|
||||||
|
|
||||||
if (fs.existsSync(versionFile)) {
|
if (fs.existsSync(versionFile)) {
|
||||||
const version = fs.readFileSync(versionFile, 'utf8');
|
const version = fs.readFileSync(versionFile, 'utf8');
|
||||||
core.info(`Resolved ${versionFile} as ${version}`);
|
core.info(`Resolved ${versionFile} as ${version}`);
|
||||||
|
|
16
src/utils.ts
16
src/utils.ts
|
@ -28,6 +28,22 @@ export interface IPyPyManifestRelease {
|
||||||
files: IPyPyManifestAsset[];
|
files: IPyPyManifestAsset[];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function parsePythonVersionFile(contents: string): string {
|
||||||
|
let pythonVersion: string | undefined;
|
||||||
|
|
||||||
|
// Try to find the version in tool-version file
|
||||||
|
const found = contents.match(/^(?:python\s+)?v?(?<version>[^\s]+)$/m);
|
||||||
|
pythonVersion = found?.groups?.version;
|
||||||
|
|
||||||
|
// In the case of an unknown format,
|
||||||
|
// return as is and evaluate the version separately.
|
||||||
|
if (!pythonVersion) {
|
||||||
|
pythonVersion = contents.trim();
|
||||||
|
}
|
||||||
|
|
||||||
|
return pythonVersion as string;
|
||||||
|
}
|
||||||
|
|
||||||
/** create Symlinks for downloaded PyPy
|
/** create Symlinks for downloaded PyPy
|
||||||
* It should be executed only for downloaded versions in runtime, because
|
* It should be executed only for downloaded versions in runtime, because
|
||||||
* toolcache versions have this setup.
|
* toolcache versions have this setup.
|
||||||
|
|
Loading…
Reference in New Issue