-
Notifications
You must be signed in to change notification settings - Fork 946
Solution #1008
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Solution #1008
Changes from 1 commit
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,4 @@ | ||
| .venv | ||
| Dockerfile | ||
| .idea | ||
| docker-compose.yaml |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,23 @@ | ||
| FROM python:3.11.6-alpine3.18 | ||
|
|
||
| LABEL maintainer="rarturus" | ||
|
|
||
| ENV PYTHONUNBUFFERED 1 | ||
|
|
||
| WORKDIR /app | ||
|
|
||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The management command has a typo: use the attribute name |
||
| COPY requirements.txt . | ||
| RUN pip install --no-cache-dir -r requirements.txt | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Installing Python packages on Alpine often requires system build dependencies (gcc, musl-dev, postgresql-dev, libffi-dev, openssl-dev, build-base, etc.) if your requirements include packages like There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Critical: you must install OS build dependencies before running pip install so native DB drivers (like psycopg2) can be built. Add a RUN step such as: |
||
|
|
||
| COPY . . | ||
| RUN mkdir -p /files/media | ||
|
|
||
| RUN adduser \ | ||
| --disabled-password \ | ||
| --no-create-home \ | ||
| my_user | ||
|
Comment on lines
+17
to
+20
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The |
||
|
|
||
| RUN chown -R my_user /files/media | ||
| RUN chmod -R 755 /files/media | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Permissions: you create |
||
|
|
||
| USER my_user | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Setting |
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,19 @@ | ||
| import time | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Minor/informational: the migration header says it was generated by Django 6.0.4 while project settings indicate Django 4.x. This version mismatch is unusual and may indicate the migration was generated with a different Django version. Verify migrations and Django version compatibility. |
||
| from django.core.management.base import BaseCommand | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Critical: You are ignoring the Dockerfile in .dockerignore. Docker will not send the Dockerfile into the build context if it's listed here, which prevents building the app image. Remove this line so the Dockerfile is included in the build context. |
||
| from django.db import connections | ||
| from django.db.utils import OperationalError | ||
|
|
||
|
|
||
| class Command(BaseCommand): | ||
| help1 = "Wait for database to be available" | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The management command sets |
||
|
|
||
| def handle(self, *args, **options): | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. If your requirements include packages like There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Before running
This ensures packages like |
||
| self.stdout.write("Waiting for database...") | ||
| while True: | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. COPY . . is fine for image build, but if you later mount the project directory as a volume in docker-compose (bind mount), it will overwrite the image contents at runtime and make the image less independent/thin. Reconsider the bind mount in compose if your goal is to make the service independent of the local machine, or document that mounting is for development only. |
||
| try: | ||
| connections["default"].cursor() | ||
| break | ||
| except OperationalError: | ||
| self.stdout.write("Database unavailable, waiting 1 second...") | ||
| time.sleep(1) | ||
|
Comment on lines
+13
to
+16
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The adduser command used here appears to use Debian-style flags (e.g. --disabled-password, --no-create-home). On Alpine-based images the adduser implementation and flags are different and this RUN may fail during image build. Either use an Alpine-compatible user creation (e.g.
Comment on lines
+13
to
+16
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You create a user with |
||
| self.stdout.write(self.style.SUCCESS("Database available!")) | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,41 @@ | ||
| # Generated by Django 6.0.4 on 2026-04-16 22:41 | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. If |
||
|
|
||
| import django.db.models.deletion | ||
| from django.conf import settings | ||
| from django.db import migrations, models | ||
|
|
||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You currently ignore |
||
|
|
||
| class Migration(migrations.Migration): | ||
|
|
||
| dependencies = [ | ||
| ('cinema', '0001_initial'), | ||
| migrations.swappable_dependency(settings.AUTH_USER_MODEL), | ||
| ] | ||
|
|
||
| operations = [ | ||
| migrations.AlterField( | ||
| model_name='movie', | ||
| name='actors', | ||
| field=models.ManyToManyField(blank=True, related_name='movies', to='cinema.actor'), | ||
| ), | ||
| migrations.AlterField( | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You create the |
||
| model_name='movie', | ||
| name='genres', | ||
| field=models.ManyToManyField(blank=True, related_name='movies', to='cinema.genre'), | ||
| ), | ||
| migrations.AlterField( | ||
| model_name='moviesession', | ||
| name='cinema_hall', | ||
| field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='movie_sessions', to='cinema.cinemahall'), | ||
| ), | ||
| migrations.AlterField( | ||
| model_name='moviesession', | ||
| name='movie', | ||
| field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='movie_sessions', to='cinema.movie'), | ||
| ), | ||
| migrations.AlterField( | ||
| model_name='order', | ||
| name='user', | ||
| field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='orders', to=settings.AUTH_USER_MODEL), | ||
| ), | ||
| ] | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -9,6 +9,7 @@ | |
| For the full list of settings and their values, see | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The app service runs Django on 0.0.0.0:8000 but there is no |
||
| https://docs.djangoproject.com/en/4.0/ref/settings/ | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Critical: the Dockerfile runs |
||
| """ | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You bind-mount the project directory into the container ( |
||
| import os | ||
| from datetime import timedelta | ||
| from pathlib import Path | ||
|
|
||
|
|
@@ -86,12 +87,15 @@ | |
|
|
||
| DATABASES = { | ||
| "default": { | ||
| "ENGINE": "django.db.backends.sqlite3", | ||
| "NAME": BASE_DIR / "db.sqlite3", | ||
| "ENGINE": os.environ.get("SQL_ENGINE", "django.db.backends.sqlite3"), | ||
| "NAME": os.environ.get("SQL_DATABASE", BASE_DIR / "db.sqlite3"), | ||
|
Comment on lines
+90
to
+91
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The database ENGINE and NAME default to SQLite if environment variables are not provided. Ensure your |
||
| "USER": os.environ.get("SQL_USER", "user"), | ||
| "PASSWORD": os.environ.get("SQL_PASSWORD", "password"), | ||
| "HOST": os.environ.get("SQL_HOST", "localhost"), | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Default HOST is |
||
| "PORT": os.environ.get("SQL_PORT", "5432"), | ||
| } | ||
| } | ||
|
|
||
|
|
||
| # Password validation | ||
| # https://docs.djangoproject.com/en/4.0/ref/settings/#auth-password-validators | ||
|
|
||
|
|
@@ -134,7 +138,8 @@ | |
| STATIC_URL = "static/" | ||
|
|
||
| MEDIA_URL = "/media/" | ||
| MEDIA_ROOT = BASE_DIR / "media" | ||
| MEDIA_ROOT = "files/media" | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. MEDIA_ROOT is set to a relative path |
||
|
|
||
|
|
||
| # Default primary key field type | ||
| # https://docs.djangoproject.com/en/4.0/ref/settings/#default-auto-field | ||
|
|
@@ -167,7 +172,7 @@ | |
| } | ||
|
|
||
| SIMPLE_JWT = { | ||
| "ACCESS_TOKEN_LIFETIME": timedelta(minutes=5), | ||
| "ACCESS_TOKEN_LIFETIME": timedelta(days=1), | ||
| "REFRESH_TOKEN_LIFETIME": timedelta(days=1), | ||
| "ROTATE_REFRESH_TOKENS": False, | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,33 @@ | ||
| services: | ||
| cinema: | ||
| build: | ||
| context: . | ||
| env_file: | ||
| - .env | ||
| command: > | ||
| sh -c "python manage.py wait_for_db && python manage.py migrate && | ||
| python manage.py runserver 0.0.0.0:8000" | ||
| volumes: | ||
| - ./:/app | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The |
||
| - media_data:/files/media | ||
| depends_on: | ||
| - db | ||
|
|
||
| db: | ||
| image: postgres:16.0-alpine3.17 | ||
| environment: | ||
| POSTGRES_USER: "rarturus" | ||
| POSTGRES_PASSWORD: "password" | ||
| POSTGRES_DB: "db" | ||
| restart: always | ||
| ports: | ||
| - "5432:5432" | ||
| env_file: | ||
| - .env | ||
| volumes: | ||
| - db_data:$PG_DATA | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The DB volume mapping uses |
||
|
|
||
|
|
||
| volumes: | ||
| db_data: | ||
| media_data: | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -8,3 +8,5 @@ djangorestframework | |
| djangorestframework-simplejwt | ||
| drf-spectacular | ||
| Pillow | ||
| psycopg==3.3.3 | ||
| psycopg-binary==3.3.3 | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The .dockerignore is very minimal. Add common ignores such as
.env,__pycache__/,*.pyc,.pytest_cache/and optionallymediaif you don't want to copy uploaded files into the image. Also you currently ignoreDockerfile(line 2) which is unnecessary; while not always fatal it is unusual and may hide files needed in the build context. Finally, you listdocker-compose.yamlbut the task expectsdocker-compose.yml— consider including both names to be safe.