diff --git a/.github/workflows/pnl-ci-docs.yml b/.github/workflows/pnl-ci-docs.yml index ed27167e5d5..fab0009323f 100644 --- a/.github/workflows/pnl-ci-docs.yml +++ b/.github/workflows/pnl-ci-docs.yml @@ -128,10 +128,11 @@ jobs: python-version: [3.7] os: [ubuntu-latest] + runs-on: ${{ matrix.os }} permissions: contents: write - runs-on: ${{ matrix.os }} needs: [docs-build] + environment: github-pages if: github.event_name == 'push' && (github.ref == 'refs/heads/master' || github.ref == 'refs/heads/devel' || diff --git a/.github/workflows/prepare-release.yml b/.github/workflows/prepare-release.yml deleted file mode 100644 index 0b2d5b48a55..00000000000 --- a/.github/workflows/prepare-release.yml +++ /dev/null @@ -1,69 +0,0 @@ -name: Prepare PNL release - -on: - push: - tags: - - 'v*' - -jobs: - prepare-release: - runs-on: ubuntu-latest - steps: - - - name: Checkout sources - uses: actions/checkout@v2.4.0 - with: - fetch-depth: 1 - - - name: Check if on master - id: on_master - uses: ./.github/actions/on-branch - with: - branch: master - - - name: Check for existing release with the reference tag - uses: actions/github-script@v5 - id: exist_check - with: - script: | - tag = context.ref.split('/').pop() - console.log('running on:' + context.ref); - console.log('Looking for release for tag:' + tag); - try { - release_if_exists = await github.repos.getReleaseByTag({ - owner: context.repo.owner, - repo: context.repo.repo, - tag: tag - }); - console.log('Release found at: ' + release_if_exists.data.html_url); - core.setOutput('exists', 'yes') - } catch (err) { - if (err.status == 404) { - console.log('Release not found.'); - core.setOutput('exists', 'no') - } else { - throw err; - } - } - - - name: Create Release - uses: actions/github-script@v5 - if: steps.on_master.outputs.on-branch == 'master' && steps.exist_check.outputs.exists == 'no' - with: - # We need custom token since the default one doesn't trigger actions - github-token: ${{ secrets.CREATE_RELEASE_TOKEN }} - script: | - if (core.getInput('github-token') == 'no-token') { - core.warning('No token to create a release!'); - return 0; - } - - tag = context.ref.split('/').pop() - return await github.repos.createRelease({ - owner: context.repo.owner, - repo: context.repo.repo, - tag_name: tag, - prerelease: true, - name: 'Release ' + tag, - body: 'New features and fixed bugs' - }); diff --git a/.github/workflows/test-release.yml b/.github/workflows/test-release.yml index 0edea71031b..52acdb856cc 100644 --- a/.github/workflows/test-release.yml +++ b/.github/workflows/test-release.yml @@ -1,8 +1,9 @@ -name: Test PNL pre-release +name: Test and publish PNL release on: - release: - types: [published] + push: + tags: + - 'v*' jobs: create-python-dist: @@ -11,31 +12,23 @@ jobs: matrix: # Python version in matrix for easier reference python-version: [3.8] - if: ${{ github.event.release.prerelease == true }} + environment: test-pypi outputs: sdist: ${{ steps.create_dist.outputs.sdist }} wheel: ${{ steps.create_dist.outputs.wheel }} steps: + - name: Checkout sources + uses: actions/checkout@v2.4.0 + - name: Set up Python ${{ matrix.python-version }} uses: actions/setup-python@v2.2.2 with: python-version: ${{ matrix.python-version }} - - name: Get release tarball - id: get_release - shell: bash - run: | - wget ${{ github.event.release.tarball_url }} -O psyneulink.tar.gz - export RELEASE_DIR=$(tar -tzf psyneulink.tar.gz | head -n1) - echo ::set-output name=release_dir::$RELEASE_DIR - tar -xzvf psyneulink.tar.gz - - - name: Create Python Dist files id: create_dist shell: bash run: | - cd ${{ steps.get_release.outputs.release_dir }} # We don't care about the python version used. pip install setuptools wheel python setup.py sdist @@ -48,8 +41,8 @@ jobs: uses: actions/upload-artifact@v2.2.4 with: name: Python-dist-files + path: dist/ retention-days: 1 - path: ${{ steps.get_release.outputs.release_dir }}/dist - name: Upload dist files to test PyPI shell: bash @@ -57,9 +50,9 @@ jobs: # Include implicit dependency on setuptools{,-rust} and preinstall wheel pip install setuptools setuptools-rust wheel pip install twine - # This expects TWINE_USERNAME, TWINE_PASSWORD, and TWINE_REPOSITORY + # This expects TWINE_USERNAME, TWINE_PASSWORD, and TWINE_REPOSITORY_URL # environment variables - # It's not possibel to condition steps on env or secrets, + # It's not possible to condition steps on env or secrets, # We need an explicit check here if [ -n "$TWINE_USERNAME" -a -n "$TWINE_PASSWORD" ]; then twine upload dist/* @@ -69,7 +62,7 @@ jobs: env: TWINE_USERNAME: ${{ secrets.TWINE_TEST_USERNAME }} TWINE_PASSWORD: ${{ secrets.TWINE_TEST_PASSWORD }} - TWINE_REPOSITORY: ${{ secrets.TWINE_TEST_REPOSITORY }} + TWINE_REPOSITORY_URL: ${{ secrets.TWINE_TEST_REPOSITORY_URL }} test-release: @@ -82,19 +75,8 @@ jobs: runs-on: ${{ matrix.os }} needs: [create-python-dist] - if: ${{ github.event.release.prerelease == true }} steps: - - - name: Get release tarball - id: get_release - shell: bash - run: | - curl -L --retry 5 ${{ github.event.release.tarball_url }} --output psyneulink.tar.gz - export RELEASE_DIR=$(tar -tzf psyneulink.tar.gz | head -n1) - echo ::set-output name=release_dir::$RELEASE_DIR - tar -xzvf psyneulink.tar.gz - - name: Download dist files uses: actions/download-artifact@v2 with: @@ -107,7 +89,7 @@ jobs: python-version: ${{ matrix.python-version }} # The installation _could_ reuse the 'install-pnl' action, - # but we intentionally avoid workarounds in there. + # but actions deploys workarounds that we want to avoid here. - name: MacOS dependencies run: HOMEBREW_NO_AUTO_UPDATE=1 brew install graphviz if: startsWith(runner.os, 'macOS') @@ -130,27 +112,32 @@ jobs: if: matrix.dist == 'sdist' run: pip install dist/${{ needs.create-python-dist.outputs.sdist }}[dev] + - name: Get tests from the repository + uses: actions/checkout@v2.4.0 + - name: Run tests + shell: bash # run only tests/. We don't care about codestyle/docstyle at this point timeout-minutes: 80 run: | - # Enter the PNL directory otherwise docstyle won't pick up the configuration - cd ${{ steps.get_release.outputs.release_dir }} - pytest --junit-xml=tests_out.xml --verbosity=0 -n auto --maxprocesses=2 tests + # remove sources to prevent conflict with the isntalled package + rm -r -f psyneulink/ docs/ bin/ Matlab/ + # run tests + pytest --junit-xml=tests_out.xml --verbosity=0 -n auto tests - name: Upload test results uses: actions/upload-artifact@v2.2.4 with: name: test-results-${{ matrix.os }}-${{ matrix.python-version }} - path: ${{ steps.get_release.outputs.release_dir }}/tests_out.xml + path: tests_out.xml retention-days: 30 if: success() || failure() - publish-release: + publish-pypi: runs-on: ubuntu-latest needs: [create-python-dist, test-release] - if: ${{ github.event.release.prerelease == true }} + environment: pypi steps: - name: Download dist files @@ -165,9 +152,9 @@ jobs: # Include implicit dependency on setuptools{,-rust} and preinstall wheel pip3 install --user setuptools setuptools-rust wheel pip3 install --user twine - # This expects TWINE_USERNAME, TWINE_PASSWORD, and TWINE_REPOSITORY + # This expects TWINE_USERNAME, TWINE_PASSWORD, and TWINE_REPOSITORY_URL # environment variables - # It's not possibel to condition steps on env or secrets, + # It's not possible to condition steps on env or secrets, # We need an explicit check here if [ -n "$TWINE_USERNAME" -a -n "$TWINE_PASSWORD" ]; then twine upload dist/* @@ -177,14 +164,55 @@ jobs: env: TWINE_USERNAME: ${{ secrets.TWINE_USERNAME }} TWINE_PASSWORD: ${{ secrets.TWINE_PASSWORD }} - TWINE_REPOSITORY: ${{ secrets.TWINE_REPOSITORY }} + TWINE_REPOSITORY_URL: ${{ secrets.TWINE_REPOSITORY_URL }} + + publish-github: + runs-on: ubuntu-latest + needs: [create-python-dist, test-release] + environment: gh-release + permissions: + contents: write + + steps: + - name: Download dist files + uses: actions/download-artifact@v2 + with: + name: Python-dist-files + path: dist/ - name: Upload dist files to release uses: actions/github-script@v5 with: script: | const fs = require('fs') + tag = context.ref.split('/').pop() + console.log('running on:' + context.ref); + console.log('Looking for release for tag:' + tag); + + var release + try { + release = await github.rest.repos.getReleaseByTag({ + owner: context.repo.owner, + repo: context.repo.repo, + tag: tag + }); + console.log('Release found at: ' + release.data.html_url); // ' + } catch (err) { + if (err.status == 404) { + console.log('Release not found, creating a new one'); + release = await github.rest.repos.createRelease({ + owner: context.repo.owner, + repo: context.repo.repo, + tag_name: tag, + name: 'Release ' + tag, + body: 'New features and fixed bugs' + }); + } else { + throw err; + } + } + console.log('Using release upload url: ' + release['data']['upload_url']); // Determine content-length for header to upload asset for (asset of ['${{ needs.create-python-dist.outputs.wheel }}', '${{ needs.create-python-dist.outputs.sdist }}']) { const file_path = 'dist/' + asset; @@ -196,18 +224,10 @@ jobs: const headers = { 'content-type': 'application/zip', 'content-length': file_size(file_path) }; // Upload a release asset - const uploadAssetResponse = await github.repos.uploadReleaseAsset({ - url: '${{ github.event.release.upload_url }}', + const uploadAssetResponse = await github.rest.repos.uploadReleaseAsset({ + url: release.data.upload_url, headers, name: asset, file: fs.readFileSync(file_path) }); } - - // Bump to full release - const uploadAssetResponse = await github.repos.updateRelease({ - owner: context.repo.owner, - repo: context.repo.repo, - release_id: ${{ github.event.release.id }}, - prerelease: false - });