Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 5ccb29d

Browse filesBrowse files
Install multiple python versions (actions#567)
1 parent c3e0339 commit 5ccb29d
Copy full SHA for 5ccb29d

File tree

Expand file treeCollapse file tree

5 files changed

+190
-57
lines changed
Filter options
Expand file treeCollapse file tree

5 files changed

+190
-57
lines changed

‎.github/workflows/test-pypy.yml

Copy file name to clipboardExpand all lines: .github/workflows/test-pypy.yml
+42Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,4 +124,46 @@ jobs:
124124
EXECUTABLE=${EXECUTABLE/-/} # remove the first '-' in "pypy-X.Y" -> "pypyX.Y" to match executable name
125125
EXECUTABLE=${EXECUTABLE%%-*} # remove any -* suffixe
126126
${EXECUTABLE} --version
127+
shell: bash
128+
129+
setup-pypy-multiple-versions:
130+
runs-on: ${{ matrix.os }}
131+
strategy:
132+
fail-fast: false
133+
matrix:
134+
os: [ubuntu-latest, windows-latest, macos-latest]
135+
steps:
136+
- uses: actions/checkout@v3
137+
- name: Setup PyPy and check latest
138+
uses: ./
139+
with:
140+
python-version: |
141+
pypy-3.7-v7.3.x
142+
pypy3.8
143+
check-latest: true
144+
- name: PyPy and Python version
145+
run: python --version
146+
147+
- name: Run simple code
148+
run: python -c 'import math; print(math.factorial(5))'
149+
150+
- name: Assert PyPy is running
151+
run: |
152+
import platform
153+
assert platform.python_implementation().lower() == "pypy"
154+
shell: python
155+
156+
- name: Assert expected binaries (or symlinks) are present
157+
run: |
158+
EXECUTABLE="pypy-3.7-v7.3.x"
159+
EXECUTABLE=${EXECUTABLE/-/} # remove the first '-' in "pypy-X.Y" -> "pypyX.Y" to match executable name
160+
EXECUTABLE=${EXECUTABLE%%-*} # remove any -* suffixe
161+
${EXECUTABLE} --version
162+
shell: bash
163+
- name: Assert expected binaries (or symlinks) are present
164+
run: |
165+
EXECUTABLE='pypy3.8'
166+
EXECUTABLE=${EXECUTABLE/pypy-/pypy} # remove the first '-' in "pypy-X.Y" -> "pypyX.Y" to match executable name
167+
EXECUTABLE=${EXECUTABLE%%-*} # remove any -* suffixe
168+
${EXECUTABLE} --version
127169
shell: bash

‎.github/workflows/test-python.yml

Copy file name to clipboardExpand all lines: .github/workflows/test-python.yml
+29-2Lines changed: 29 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -191,8 +191,35 @@ jobs:
191191
- name: Validate version
192192
run: |
193193
$pythonVersion = (python --version)
194-
if ("$pythonVersion" -NotMatch "${{ matrix.python }}"){
195-
Write-Host "The current version is $pythonVersion; expected version is ${{ matrix.python }}"
194+
if ("$pythonVersion" -NotMatch "${{ matrix.python-version }}"){
195+
Write-Host "The current version is $pythonVersion; expected version is ${{ matrix.python-version }}"
196+
exit 1
197+
}
198+
$pythonVersion
199+
shell: pwsh
200+
201+
setup-python-multiple-python-versions:
202+
runs-on: ${{ matrix.os }}
203+
strategy:
204+
fail-fast: false
205+
matrix:
206+
os: [ubuntu-latest, windows-latest, macos-latest]
207+
steps:
208+
- uses: actions/checkout@v3
209+
- name: Setup Python and check latest
210+
uses: ./
211+
with:
212+
python-version: |
213+
3.7
214+
3.8
215+
3.9
216+
3.10
217+
check-latest: true
218+
- name: Validate version
219+
run: |
220+
$pythonVersion = (python --version)
221+
if ("$pythonVersion" -NotMatch "3.10"){
222+
Write-Host "The current version is $pythonVersion; expected version is 3.10"
196223
exit 1
197224
}
198225
$pythonVersion

‎dist/setup/index.js

Copy file name to clipboardExpand all lines: dist/setup/index.js
+25-21Lines changed: 25 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -66867,31 +66867,31 @@ function cacheDependencies(cache, pythonVersion) {
6686766867
});
6686866868
}
6686966869
function resolveVersionInput() {
66870-
let version = core.getInput('python-version');
66870+
let versions = core.getMultilineInput('python-version');
6687166871
let versionFile = core.getInput('python-version-file');
66872-
if (version && versionFile) {
66872+
if (versions.length && versionFile) {
6687366873
core.warning('Both python-version and python-version-file inputs are specified, only python-version will be used.');
6687466874
}
66875-
if (version) {
66876-
return version;
66875+
if (versions.length) {
66876+
return versions;
6687766877
}
6687866878
if (versionFile) {
6687966879
if (!fs_1.default.existsSync(versionFile)) {
6688066880
throw new Error(`The specified python version file at: ${versionFile} doesn't exist.`);
6688166881
}
66882-
version = fs_1.default.readFileSync(versionFile, 'utf8');
66882+
const version = fs_1.default.readFileSync(versionFile, 'utf8');
6688366883
core.info(`Resolved ${versionFile} as ${version}`);
66884-
return version;
66884+
return [version];
6688566885
}
6688666886
utils_1.logWarning("Neither 'python-version' nor 'python-version-file' inputs were supplied. Attempting to find '.python-version' file.");
6688766887
versionFile = '.python-version';
6688866888
if (fs_1.default.existsSync(versionFile)) {
66889-
version = fs_1.default.readFileSync(versionFile, 'utf8');
66889+
const version = fs_1.default.readFileSync(versionFile, 'utf8');
6689066890
core.info(`Resolved ${versionFile} as ${version}`);
66891-
return version;
66891+
return [version];
6689266892
}
6689366893
utils_1.logWarning(`${versionFile} doesn't exist.`);
66894-
return version;
66894+
return versions;
6689566895
}
6689666896
function run() {
6689766897
var _a;
@@ -66904,22 +66904,26 @@ function run() {
6690466904
}
6690566905
core.debug(`Python is expected to be installed into ${process.env['RUNNER_TOOL_CACHE']}`);
6690666906
try {
66907-
const version = resolveVersionInput();
66907+
const versions = resolveVersionInput();
6690866908
const checkLatest = core.getBooleanInput('check-latest');
66909-
if (version) {
66910-
let pythonVersion;
66909+
if (versions.length) {
66910+
let pythonVersion = '';
6691166911
const arch = core.getInput('architecture') || os.arch();
6691266912
const updateEnvironment = core.getBooleanInput('update-environment');
66913-
if (isPyPyVersion(version)) {
66914-
const installed = yield finderPyPy.findPyPyVersion(version, arch, updateEnvironment, checkLatest);
66915-
pythonVersion = `${installed.resolvedPyPyVersion}-${installed.resolvedPythonVersion}`;
66916-
core.info(`Successfully set up PyPy ${installed.resolvedPyPyVersion} with Python (${installed.resolvedPythonVersion})`);
66917-
}
66918-
else {
66919-
const installed = yield finder.useCpythonVersion(version, arch, updateEnvironment, checkLatest);
66920-
pythonVersion = installed.version;
66921-
core.info(`Successfully set up ${installed.impl} (${pythonVersion})`);
66913+
core.startGroup('Installed versions');
66914+
for (const version of versions) {
66915+
if (isPyPyVersion(version)) {
66916+
const installed = yield finderPyPy.findPyPyVersion(version, arch, updateEnvironment, checkLatest);
66917+
pythonVersion = `${installed.resolvedPyPyVersion}-${installed.resolvedPythonVersion}`;
66918+
core.info(`Successfully set up PyPy ${installed.resolvedPyPyVersion} with Python (${installed.resolvedPythonVersion})`);
66919+
}
66920+
else {
66921+
const installed = yield finder.useCpythonVersion(version, arch, updateEnvironment, checkLatest);
66922+
pythonVersion = installed.version;
66923+
core.info(`Successfully set up ${installed.impl} (${pythonVersion})`);
66924+
}
6692266925
}
66926+
core.endGroup();
6692366927
const cache = core.getInput('cache');
6692466928
if (cache && utils_1.isCacheFeatureAvailable()) {
6692566929
yield cacheDependencies(cache, pythonVersion);

‎docs/advanced-usage.md

Copy file name to clipboardExpand all lines: docs/advanced-usage.md
+57Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
- [Using the python-version input](advanced-usage.md#using-the-python-version-input)
33
- [Specifying a Python version](advanced-usage.md#specifying-a-python-version)
44
- [Specifying a PyPy version](advanced-usage.md#specifying-a-pypy-version)
5+
- [Specifying multiple Python and PyPy versions](advanced-usage.md#specifying-multiple-python/pypy-version)
56
- [Matrix Testing](advanced-usage.md#matrix-testing)
67
- [Using the python-version-file input](advanced-usage.md#using-the-python-version-file-input)
78
- [Check latest version](advanced-usage.md#check-latest-version)
@@ -132,6 +133,62 @@ jobs:
132133
```
133134
More details on PyPy syntax can be found in the [Available versions of PyPy](#pypy) section.
134135

136+
### Specifying multiple Python/PyPy version
137+
The python-version input can get multiple python/pypy versions. The last specified version will be used as a default one.
138+
139+
Download and set up multiple Python versions:
140+
141+
```yaml
142+
jobs:
143+
build:
144+
runs-on: ubuntu-latest
145+
steps:
146+
- uses: actions/checkout@v3
147+
- uses: actions/setup-python@v4
148+
with:
149+
python-version: |
150+
3.8
151+
3.9
152+
3.10
153+
- run: python my_script.py
154+
```
155+
156+
Download and set up multiple PyPy versions:
157+
158+
```yaml
159+
jobs:
160+
build:
161+
runs-on: ubuntu-latest
162+
steps:
163+
- uses: actions/checkout@v3
164+
- uses: actions/setup-python@v4
165+
with:
166+
python-version: |
167+
pypy-3.7-v7.3.x
168+
pypy3.9-nightly
169+
pypy3.8
170+
- run: python my_script.py
171+
```
172+
173+
Download and set up multiple Python/PyPy versions:
174+
175+
```yaml
176+
jobs:
177+
build:
178+
runs-on: ubuntu-latest
179+
steps:
180+
- uses: actions/checkout@v3
181+
- uses: actions/setup-python@v4
182+
with:
183+
python-version: |
184+
3.8
185+
3.9
186+
pypy3.9-nightly
187+
pypy3.8
188+
3.10
189+
- run: python my_script.py
190+
```
191+
135192
### Matrix Testing
136193
137194
Using `setup-python` it's possible to use [matrix syntax](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstrategymatrix) to install several versions of Python or PyPy:

‎src/setup-python.ts

Copy file name to clipboardExpand all lines: src/setup-python.ts
+37-34Lines changed: 37 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -22,18 +22,18 @@ async function cacheDependencies(cache: string, pythonVersion: string) {
2222
await cacheDistributor.restoreCache();
2323
}
2424

25-
function resolveVersionInput(): string {
26-
let version = core.getInput('python-version');
25+
function resolveVersionInput() {
26+
let versions = core.getMultilineInput('python-version');
2727
let versionFile = core.getInput('python-version-file');
2828

29-
if (version && versionFile) {
29+
if (versions.length && versionFile) {
3030
core.warning(
3131
'Both python-version and python-version-file inputs are specified, only python-version will be used.'
3232
);
3333
}
3434

35-
if (version) {
36-
return version;
35+
if (versions.length) {
36+
return versions;
3737
}
3838

3939
if (versionFile) {
@@ -42,24 +42,24 @@ function resolveVersionInput(): string {
4242
`The specified python version file at: ${versionFile} doesn't exist.`
4343
);
4444
}
45-
version = fs.readFileSync(versionFile, 'utf8');
45+
const version = fs.readFileSync(versionFile, 'utf8');
4646
core.info(`Resolved ${versionFile} as ${version}`);
47-
return version;
47+
return [version];
4848
}
4949

5050
logWarning(
5151
"Neither 'python-version' nor 'python-version-file' inputs were supplied. Attempting to find '.python-version' file."
5252
);
5353
versionFile = '.python-version';
5454
if (fs.existsSync(versionFile)) {
55-
version = fs.readFileSync(versionFile, 'utf8');
55+
const version = fs.readFileSync(versionFile, 'utf8');
5656
core.info(`Resolved ${versionFile} as ${version}`);
57-
return version;
57+
return [version];
5858
}
5959

6060
logWarning(`${versionFile} doesn't exist.`);
6161

62-
return version;
62+
return versions;
6363
}
6464

6565
async function run() {
@@ -75,35 +75,38 @@ async function run() {
7575
`Python is expected to be installed into ${process.env['RUNNER_TOOL_CACHE']}`
7676
);
7777
try {
78-
const version = resolveVersionInput();
78+
const versions = resolveVersionInput();
7979
const checkLatest = core.getBooleanInput('check-latest');
8080

81-
if (version) {
82-
let pythonVersion: string;
81+
if (versions.length) {
82+
let pythonVersion = '';
8383
const arch: string = core.getInput('architecture') || os.arch();
8484
const updateEnvironment = core.getBooleanInput('update-environment');
85-
if (isPyPyVersion(version)) {
86-
const installed = await finderPyPy.findPyPyVersion(
87-
version,
88-
arch,
89-
updateEnvironment,
90-
checkLatest
91-
);
92-
pythonVersion = `${installed.resolvedPyPyVersion}-${installed.resolvedPythonVersion}`;
93-
core.info(
94-
`Successfully set up PyPy ${installed.resolvedPyPyVersion} with Python (${installed.resolvedPythonVersion})`
95-
);
96-
} else {
97-
const installed = await finder.useCpythonVersion(
98-
version,
99-
arch,
100-
updateEnvironment,
101-
checkLatest
102-
);
103-
pythonVersion = installed.version;
104-
core.info(`Successfully set up ${installed.impl} (${pythonVersion})`);
85+
core.startGroup('Installed versions');
86+
for (const version of versions) {
87+
if (isPyPyVersion(version)) {
88+
const installed = await finderPyPy.findPyPyVersion(
89+
version,
90+
arch,
91+
updateEnvironment,
92+
checkLatest
93+
);
94+
pythonVersion = `${installed.resolvedPyPyVersion}-${installed.resolvedPythonVersion}`;
95+
core.info(
96+
`Successfully set up PyPy ${installed.resolvedPyPyVersion} with Python (${installed.resolvedPythonVersion})`
97+
);
98+
} else {
99+
const installed = await finder.useCpythonVersion(
100+
version,
101+
arch,
102+
updateEnvironment,
103+
checkLatest
104+
);
105+
pythonVersion = installed.version;
106+
core.info(`Successfully set up ${installed.impl} (${pythonVersion})`);
107+
}
105108
}
106-
109+
core.endGroup();
107110
const cache = core.getInput('cache');
108111
if (cache && isCacheFeatureAvailable()) {
109112
await cacheDependencies(cache, pythonVersion);

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.