Dave
Dave

Reputation: 19090

How do I install GDAL in a Python Docker environment?

I'm using Python 3.7 and Django 3.0. I want to install this requirement

GDAL==2.4.2

in my Django Docker environment. Below is my Docker file ...

FROM python:3.7-slim
  
RUN apt-get update && apt-get install

RUN apt-get install -y libmariadb-dev-compat libmariadb-dev
RUN apt-get update \
    && apt-get install -y --no-install-recommends gcc \
    && rm -rf /var/lib/apt/lists/*
RUN apt-get update &&\
    apt-get install -y binutils libproj-dev gdal-bin
RUN export CPLUS_INCLUDE_PATH=/usr/include/gdal
RUN export C_INCLUDE_PATH=/usr/include/gdal


RUN python -m pip install --upgrade pip

WORKDIR /app/

COPY requirements.txt requirements.txt
RUN python -m pip install -r requirements.txt

ENTRYPOINT ["bash", "/app/entrypoint.sh"]

but when building my container, the build dies with the following error ...

Collecting GDAL==2.4.2
  Downloading GDAL-2.4.2.tar.gz (564 kB)
    ERROR: Command errored out with exit status 1:
     command: /usr/local/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/pip-install-ofz0fkgb/GDAL/setup.py'"'"'; __file__='"'"'/tmp/pip-install-ofz0fkgb/GDAL/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' egg_info --egg-base /tmp/pip-pip-egg-info-imfatnrk
         cwd: /tmp/pip-install-ofz0fkgb/GDAL/
    Complete output (73 lines):
    WARNING: numpy not available!  Array support will not be enabled
    running egg_info
    creating /tmp/pip-pip-egg-info-imfatnrk/GDAL.egg-info
    writing /tmp/pip-pip-egg-info-imfatnrk/GDAL.egg-info/PKG-INFO
    writing dependency_links to /tmp/pip-pip-egg-info-imfatnrk/GDAL.egg-info/dependency_links.txt
    writing top-level names to /tmp/pip-pip-egg-info-imfatnrk/GDAL.egg-info/top_level.txt
    writing manifest file '/tmp/pip-pip-egg-info-imfatnrk/GDAL.egg-info/SOURCES.txt'
    Traceback (most recent call last):
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 151, in fetch_config
        p = subprocess.Popen([command, args], stdout=subprocess.PIPE)
      File "/usr/local/lib/python3.7/subprocess.py", line 800, in __init__
        restore_signals, start_new_session)
      File "/usr/local/lib/python3.7/subprocess.py", line 1551, in _execute_child
        raise child_exception_type(errno_num, err_msg, err_filename)
    FileNotFoundError: [Errno 2] No such file or directory: '../../apps/gdal-config': '../../apps/gdal-config'
    
    During handling of the above exception, another exception occurred:
    
    Traceback (most recent call last):
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 237, in get_gdal_config
        return fetch_config(option, gdal_config=self.gdal_config)
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 154, in fetch_config
        raise gdal_config_error(e)
    __main__.gdal_config_error: [Errno 2] No such file or directory: '../../apps/gdal-config': '../../apps/gdal-config'
    
    During handling of the above exception, another exception occurred:
    
    Traceback (most recent call last):
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 151, in fetch_config
        p = subprocess.Popen([command, args], stdout=subprocess.PIPE)
      File "/usr/local/lib/python3.7/subprocess.py", line 800, in __init__
        restore_signals, start_new_session)
      File "/usr/local/lib/python3.7/subprocess.py", line 1551, in _execute_child
        raise child_exception_type(errno_num, err_msg, err_filename)
    FileNotFoundError: [Errno 2] No such file or directory: 'gdal-config': 'gdal-config'
    
    During handling of the above exception, another exception occurred:
    
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 431, in <module>
        setup(**setup_kwargs)
      File "/usr/local/lib/python3.7/site-packages/setuptools/__init__.py", line 144, in setup
        return distutils.core.setup(**attrs)
      File "/usr/local/lib/python3.7/distutils/core.py", line 148, in setup
        dist.run_commands()
      File "/usr/local/lib/python3.7/distutils/dist.py", line 966, in run_commands
        self.run_command(cmd)
      File "/usr/local/lib/python3.7/distutils/dist.py", line 985, in run_command
        cmd_obj.run()
      File "/usr/local/lib/python3.7/site-packages/setuptools/command/egg_info.py", line 297, in run
        self.find_sources()
      File "/usr/local/lib/python3.7/site-packages/setuptools/command/egg_info.py", line 304, in find_sources
        mm.run()
      File "/usr/local/lib/python3.7/site-packages/setuptools/command/egg_info.py", line 535, in run
        self.add_defaults()
      File "/usr/local/lib/python3.7/site-packages/setuptools/command/egg_info.py", line 571, in add_defaults
        sdist.add_defaults(self)
      File "/usr/local/lib/python3.7/distutils/command/sdist.py", line 228, in add_defaults
        self._add_defaults_ext()
      File "/usr/local/lib/python3.7/distutils/command/sdist.py", line 311, in _add_defaults_ext
        build_ext = self.get_finalized_command('build_ext')
      File "/usr/local/lib/python3.7/distutils/cmd.py", line 299, in get_finalized_command
        cmd_obj.ensure_finalized()
      File "/usr/local/lib/python3.7/distutils/cmd.py", line 107, in ensure_finalized
        self.finalize_options()
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 287, in finalize_options
        self.gdaldir = self.get_gdal_config('prefix')
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 243, in get_gdal_config
        return fetch_config(option)
      File "/tmp/pip-install-ofz0fkgb/GDAL/setup.py", line 154, in fetch_config
        raise gdal_config_error(e)
    __main__.gdal_config_error: [Errno 2] No such file or directory: 'gdal-config': 'gdal-config'
    ----------------------------------------
ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.
ERROR: Service 'web' failed to build: The command '/bin/sh -c python -m pip install -r requirements.txt' returned a non-zero code: 1

How do I install the GDAL library in a Python Docker environment?

Upvotes: 3

Views: 3909

Answers (1)

smrf
smrf

Reputation: 361

Here is a docker file you can use, I used this in one of my project and it is working, however, change the other section of the file based on your preferences and project.

ARG PYTHON_VERSION=3.9-slim-bullseye



# define an alias for the specfic python version used in this file.
FROM python:${PYTHON_VERSION} as python

# Python build stage
FROM python as python-build-stage

ARG BUILD_ENVIRONMENT=production

# Install apt packages
RUN apt-get update && apt-get install --no-install-recommends -y \
  # dependencies for building Python packages
  build-essential \
  # psycopg2 dependencies
  libpq-dev
# RUN apk add gcc musl-dev python3-dev libffi-dev openssl-dev cargo
RUN apt-get update && \
    apt-get -y install gcc mono-mcs && \
    rm -rf /var/lib/apt/lists/*
# Requirements are installed here to ensure they will be cached.
COPY ./requirements .

# Create Python Dependency and Sub-Dependency Wheels.
RUN pip wheel --wheel-dir /usr/src/app/wheels  \
  -r ${BUILD_ENVIRONMENT}.txt


# Python 'run' stage
FROM python as python-run-stage

ARG BUILD_ENVIRONMENT=production
ARG APP_HOME=/app

ENV PYTHONUNBUFFERED 1
ENV PYTHONDONTWRITEBYTECODE 1
ENV BUILD_ENV ${BUILD_ENVIRONMENT}

WORKDIR ${APP_HOME}

RUN addgroup --system django \
    && adduser --system --ingroup django django


# Install required system dependencies
RUN apt-get update && apt-get install --no-install-recommends -y \
  # psycopg2 dependencies
  libpq-dev \
  # Translations dependencies
  gettext \
  && apt-get install gdal-bin -y \
  # cleaning up unused files
  && apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false \
  && rm -rf /var/lib/apt/lists/*

# All absolute dir copies ignore workdir instruction. All relative dir copies are wrt to the workdir instruction
# copy python dependency wheels from python-build-stage
COPY --from=python-build-stage /usr/src/app/wheels  /wheels/

# use wheels to install python dependencies
RUN pip install --no-cache-dir --no-index --find-links=/wheels/ /wheels/* \
  && rm -rf /wheels/


COPY --chown=django:django ./compose/production/django/entrypoint /entrypoint
RUN sed -i 's/\r$//g' /entrypoint
RUN chmod +x /entrypoint


COPY --chown=django:django ./compose/production/django/start /start
RUN sed -i 's/\r$//g' /start
RUN chmod +x /start
COPY --chown=django:django ./compose/production/django/celery/worker/start /start-celeryworker
RUN sed -i 's/\r$//g' /start-celeryworker
RUN chmod +x /start-celeryworker


COPY --chown=django:django ./compose/production/django/celery/beat/start /start-celerybeat
RUN sed -i 's/\r$//g' /start-celerybeat
RUN chmod +x /start-celerybeat


COPY ./compose/production/django/celery/flower/start /start-flower
RUN sed -i 's/\r$//g' /start-flower
RUN chmod +x /start-flower


# copy application code to WORKDIR
COPY --chown=django:django . ${APP_HOME}

# make django owner of the WORKDIR directory as well.
RUN chown django:django ${APP_HOME}

USER django

ENTRYPOINT ["/entrypoint"]

Upvotes: 2

Related Questions