I use Bitbucket for source control and I absolutely love Bitbucket Pipelines.
I have been using Pipelines for a while to do automated testing of many of my Python projects utilizing tox.
However, the one piece that was missing was the Continuous Deployment to PyPI. I started by following the documentation
on Atlassian’s own site but found
it to not be complete. Couple that with some of the recent updates to Bitbucket Pipelines
I’ve decided to update with my own FAQ on how I do it!
The Recipe
Here is my bitbucket pipeline “recipe” for an example project:
image: python:3.6 # Default image for all steps
pipelines:
default:
- step:
name: Python 2 Tests
image: python:2.7
script:
- pip install -U tox
- tox -e py27
- step:
name: Python3 Tests
script:
- pip install -U tox
- tox -e py36
branches:
master:
- step:
name: Python 2 Tests
image: python:2.7
script:
- pip install -U tox
- tox -e py27
- step:
name: Python3 Tests
script:
- pip install -U tox
- tox -e py36
- step:
name: Deploy To PyPI
script:
- bash -e deploy.bash
This configuration allows tests of Python2 and Python3 on all branches including master. The only difference on master the additional step to actually do the deploy to PyPI. For my deploy script I first created some secure environment variables in my Bitbucket Repo configuration to store my PyPI Username/Password (I didn’t want to hard code these into the repo so that just anyone could see them). I then created the following script, based of the Atlassian example:
#!/bin/bash -e
cat <<EOF >> ~/.pypirc
[distutils]
index-servers=pypi
[pypi]
repository=https://upload.pypi.org/pypi
username=${PYPI_USERNAME}
password=${PYPI_PASSWORD}
EOF
python setup.py sdist upload;
rm ~/.pypirc;
And that is it! Now when I commit to any branch besides master my automated testing is run using both Python2 and Python3
and when I complete a release cut and merge to master the tests run as normal but then a the deploy.bash
script runs
and sends the updated code to PyPI.
I hope you find this useful in turning up CICD for Python projects using Bitbucket Pipelines!
P.S. You could have another step for any release* branch that automatically tests your upload to the PyPi dev site. I haven’t included those steps here but they should be easy enough to figure out!