Reputation: 23
I created simple project in Django with docker. According to heroku's documentation about release phase with container registry (https://devcenter.heroku.com/articles/container-registry-and-runtime#release-phase) I created a new app with postgres addon. To deploy app with docker I executed following commands:
heroku container:push web
heroku container:push release
heroku container:release web release
But after last command my terminal is blocked and it looks like release phase actually run a container.
Releasing images web,release to teleagh... done
Running release command...
[2019-12-30 21:22:00 +0000] [17] [INFO] Starting gunicorn 19.9.0
[2019-12-30 21:22:00 +0000] [17] [INFO] Listening at: http://0.0.0.0:5519 (17)
[2019-12-30 21:22:00 +0000] [17] [INFO] Using worker: sync
[2019-12-30 21:22:00 +0000] [27] [INFO] Booting worker with pid: 27
My goal is tu run django migrations before release. I would really apreciate any help.
Procfile:
release: python manage.py migrate
Dockerfile:
FROM python:3.7-slim
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
ENV PORT=8000
WORKDIR /app
ADD requirements.txt .
RUN pip install -r requirements.txt
RUN apt-get update && apt-get install -y curl
ADD . ./
RUN python manage.py collectstatic --noinput
CMD gunicorn --bind 0.0.0.0:$PORT teleagh.wsgi
Upvotes: 1
Views: 831
Reputation: 14404
You can add a release phase to the heroku.yml
file.
ex.
build:
...
release:
command:
- rake db:migrate
run:
web: bundle exec puma -C config/puma.rb
Upvotes: 0
Reputation: 640
Procfile does not make effect when container deploy is used in heroku. If you want to set release phase command I can suggest two options that I have tested a lot:
1. Create dedicated Dockerfile for each phase with extensions matching the phase name.
Dockerfile.web
FROM python:3.7-slim
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
ENV PORT=8000
WORKDIR /app
ADD requirements.txt .
RUN pip install -r requirements.txt
RUN apt-get update && apt-get install -y curl
ADD . ./
RUN python manage.py collectstatic --noinput
CMD gunicorn --bind 0.0.0.0:$PORT teleagh.wsgi
Dockerfile.release
FROM python:3.7-slim
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
ENV PORT=8000
WORKDIR /app
ADD requirements.txt .
RUN pip install -r requirements.txt
RUN apt-get update && apt-get install -y curl
ADD . ./
RUN python manage.py collectstatic --noinput
CMD python manage.py migrate
The deploying process will be looking the same like yours with one exception — push command must have additional argument --recursive. Moreover it is possible to push all containers in one command:
heroku container:push web release --recursive
heroku container:release web release
2. Create a bash script to detect what phase is running in the container at the moment.
start.sh
#!/bin/bash
if [ -z "$SSH_CLIENT" ] && [ -n "$HEROKU_EXEC_URL" ];
then
source <(curl --fail --retry 3 -sSL "$HEROKU_EXEC_URL")
fi
if [[ "$DYNO" =~ ^release.* ]];
then
set -e
python3 manage.py migrate
else
exec gunicorn teleagh.wsgi -b 0.0.0.0:${PORT} --reload --access-logfile -
fi
Then the only Dockerfile will be looking like:
FROM python:3.7-slim
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
ENV PORT=8000
WORKDIR /app
ADD requirements.txt .
RUN pip install -r requirements.txt
RUN apt-get update && apt-get install -y curl
ADD . ./
RUN python manage.py collectstatic --noinput
CMD ./start.sh
Hope this will be helpful
Upvotes: 1