From f148af2bf0b549c9f358ed5b798cd79a94f6bbfe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o?= <theo@le-filament.com> Date: Thu, 27 Oct 2022 16:09:10 +0200 Subject: [PATCH] [ADD] image from scratch --- .gitlab-ci.yml | 6 +- 16.0-alpine.Dockerfile | 71 ------------- 16.0-scratch.Dockerfile | 220 ++++++++++++++++++++++++++++++++++++++++ entrypoint-scratch.sh | 87 ++++++++++++++++ 4 files changed, 310 insertions(+), 74 deletions(-) delete mode 100644 16.0-alpine.Dockerfile create mode 100644 16.0-scratch.Dockerfile create mode 100755 entrypoint-scratch.sh diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index e99942c..769ce96 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -66,7 +66,7 @@ docker-build-16.0: - docker push "$CI_REGISTRY_IMAGE:16.0" only: - '16.0' -docker-build-16.0-alpine: +docker-build-16.0-scratch: image: docker:20.10.17 stage: build services: @@ -74,8 +74,8 @@ docker-build-16.0-alpine: before_script: - docker login -u "$CI_REGISTRY_USER" -p "$CI_REGISTRY_PASSWORD" $CI_REGISTRY script: - - docker build --pull -f 16.0-alpine.Dockerfile -t "$CI_REGISTRY_IMAGE:16.0-alpine" + - docker build --pull -f 16.0-scratch.Dockerfile -t "$CI_REGISTRY_IMAGE:16.0-scratch" . - - docker push "$CI_REGISTRY_IMAGE:16.0-alpine" + - docker push "$CI_REGISTRY_IMAGE:16.0-scratch" only: - '16.0' diff --git a/16.0-alpine.Dockerfile b/16.0-alpine.Dockerfile deleted file mode 100644 index 55d4504..0000000 --- a/16.0-alpine.Dockerfile +++ /dev/null @@ -1,71 +0,0 @@ -FROM surnet/alpine-wkhtmltopdf:3.16.0-0.12.6-small as wkhtmltopdf - -FROM python:3.10-alpine AS builder -RUN set -x; \ - apk add --no-cache python3-dev libffi-dev gcc musl-dev make postgresql-dev openldap-dev cyrus-sasl-dev jpeg-dev zlib-dev libsass-dev g++ &&\ - pip install wheel &&\ - echo 'INPUT ( libldap.so )' > /usr/lib/libldap_r.so &&\ - pip wheel --wheel-dir=/svc/wheels -r https://raw.githubusercontent.com/odoo/odoo/master/requirements.txt &&\ - pip wheel --wheel-dir=/svc/wheels phonenumbers simplejson openupgradelib PyYAML - - -FROM python:3.10-alpine AS final -ENV LANG=C.UTF-8 \ - LC_ALL=C.UTF-8 \ - PGDATABASE=odoo - -RUN set -x; \ - apk add --no-cache \ - bash \ - fontconfig \ - freetype \ - git \ - libjpeg-turbo \ - libsass \ - libstdc++ \ - libx11 \ - libxrender \ - postgresql-client - -# Copy wkhtmltopdf files from docker-wkhtmltopdf image -COPY --from=wkhtmltopdf /bin/wkhtmltopdf /bin/wkhtmltopdf - -COPY --from=builder /svc /svc -RUN pip3 install --no-index --find-links=/svc/wheels -r https://raw.githubusercontent.com/odoo/odoo/master/requirements.txt &&\ - pip3 install --no-index --find-links=/svc/wheels phonenumbers simplejson openupgradelib PyYAML - -# Add Git Known Hosts -COPY ./ssh_known_git_hosts /root/.ssh/known_hosts - -# Install Odoo and remove not French translations and .git directory to limit amount of data used by container -RUN set -x; \ - adduser -h /opt/odoo -D odoo &&\ - /bin/bash -c "mkdir -p /opt/odoo/{etc,odoo,additional_addons,private_addons,data,private}" &&\ - git clone -b 16.0 --depth 1 https://github.com/OCA/OCB.git /opt/odoo/odoo &&\ - rm -rf /opt/odoo/odoo/.git &&\ - find /opt/odoo/odoo/addons/*/i18n/ /opt/odoo/odoo/odoo/addons/base/i18n/ -type f -not -name 'fr.po' -delete &&\ - chown -R odoo:odoo /opt/odoo - -# Copy entrypoint script and Odoo configuration file -COPY ./entrypoint.sh / -COPY ./odoo.conf /opt/odoo/etc/odoo.conf -RUN chown odoo:odoo /opt/odoo/etc/odoo.conf - -# Mount /opt/odoo/data to allow restoring filestore -VOLUME ["/opt/odoo/data/"] - -# Expose Odoo services -EXPOSE 8069 - -# Set default user when running the container -USER odoo - -# Start -ENTRYPOINT ["/entrypoint.sh"] -CMD ["odoo"] - -# Metadata -LABEL org.label-schema.schema-version="16.0" \ - org.label-schema.vendor=LeFilament \ - org.label-schema.license=Apache-2.0 \ - org.label-schema.vcs-url="https://sources.le-filament.com/lefilament/odoo_docker" diff --git a/16.0-scratch.Dockerfile b/16.0-scratch.Dockerfile new file mode 100644 index 0000000..46e59a9 --- /dev/null +++ b/16.0-scratch.Dockerfile @@ -0,0 +1,220 @@ +FROM surnet/alpine-wkhtmltopdf:3.16.0-0.12.6-small as wkhtmltopdf + + +FROM alpine as build + +# Initial setup of new root. +RUN apk update \ + && mkdir --parents \ + /newroot/etc \ + /newroot/bin \ + /newroot/usr/bin \ + && cp -a --parents \ + /bin/busybox \ + /lib/ld-musl* \ + /newroot/ \ + && /bin/busybox --install -s /newroot/bin/ \ + && /bin/busybox --install -s /newroot/usr/bin/ \ + && echo 'root:x:0:0:::' > /newroot/etc/passwd \ + && echo 'root:x:0:' > /newroot/etc/group + +# Add depedencies +RUN apk add --no-cache \ + file \ + freetype-dev \ + g++ \ + gcc \ + git \ + jpeg-dev \ + libev-dev \ + libffi-dev \ + libx11-dev \ + libxrender-dev \ + fontconfig-dev \ + make \ + musl-dev \ + openldap-dev \ + postgresql-dev \ + py3-pip \ + python3 \ + python3-dev \ + zlib-dev + +# Add Odoo. +RUN git clone -b 16.0 --depth 1 https://github.com/OCA/OCB.git /newroot/opt/odoo/odoo \ + && rm -rf /newroot/opt/odoo/odoo/.git \ + && find /newroot/opt/odoo/odoo/addons/*/i18n/ /newroot/opt/odoo/odoo/odoo/addons/base/i18n/ -type f -not -name 'fr.po' -delete + +## Add Git known hosts. +#COPY ./ssh_known_git_hosts /root/.ssh/known_hosts +# +## Install Odoo OCA and Le Filament default dependencies. +#RUN mkdir -p \ +# /tmp/oca-repos/ \ +# /newroot/opt/odoo/additional_addons \ +# /newroot/opt/odoo/private_addons \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/account-financial-reporting.git \ +# /tmp/oca-repos/account-financial-reporting \ +# && mv /tmp/oca-repos/account-financial-reporting/account_tax_balance \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/account-financial-tools.git \ +# /tmp/oca-repos/account-financial-tools \ +# && mv /tmp/oca-repos/account-financial-tools/account_lock_date_update \ +# /tmp/oca-repos/account-financial-tools/account_move_name_sequence \ +# /tmp/oca-repos/account-financial-tools/account_reconcile_show_boolean \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/account-invoicing.git \ +# /tmp/oca-repos/account-invoicing \ +# && mv /tmp/oca-repos/account-invoicing/sale_timesheet_invoice_description \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/account-reconcile.git \ +# /tmp/oca-repos/account-reconcile \ +# && mv /tmp/oca-repos/account-reconcile/account_reconciliation_widget \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/bank-statement-import.git \ +# /tmp/oca-repos/bank-statement-import \ +# && mv /tmp/oca-repos/bank-statement-import/account_statement_import \ +# /tmp/oca-repos/bank-statement-import/account_statement_import_ofx \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/crm.git \ +# /tmp/oca-repos/crm \ +# && mv /tmp/oca-repos/crm/crm_stage_probability \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/partner-contact.git \ +# /tmp/oca-repos/partner-contact \ +# && mv /tmp/oca-repos/partner-contact/partner_disable_gravatar \ +# /tmp/oca-repos/partner-contact/partner_firstname \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/project.git \ +# /tmp/oca-repos/project \ +# && mv /tmp/oca-repos/project/project_category \ +# /tmp/oca-repos/project/project_status \ +# /tmp/oca-repos/project/project_task_default_stage \ +# /tmp/oca-repos/project/project_template \ +# /tmp/oca-repos/project/project_timeline \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/server-auth.git \ +# /tmp/oca-repos/server-auth \ +# && mv /tmp/oca-repos/server-auth/password_security \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/server-brand.git \ +# /tmp/oca-repos/server-brand \ +# && mv /tmp/oca-repos/server-brand/disable_odoo_online \ +# /tmp/oca-repos/server-brand/remove_odoo_enterprise \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/server-tools.git \ +# /tmp/oca-repos/server-tools \ +# && mv /tmp/oca-repos/server-tools/base_search_fuzzy \ +# /tmp/oca-repos/server-tools/module_change_auto_install \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/server-ux.git \ +# /tmp/oca-repos/server-ux \ +# && mv /tmp/oca-repos/server-ux/base_technical_features \ +# /tmp/oca-repos/server-ux/date_range \ +# /tmp/oca-repos/server-ux/mass_editing \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/social.git \ +# /tmp/oca-repos/social \ +# && mv /tmp/oca-repos/social/base_search_mail_content \ +# /tmp/oca-repos/social/mail_debrand \ +# /tmp/oca-repos/social/mail_tracking \ +# /newroot/opt/odoo/additional_addons/ \ +# && git clone -b 16.0 --depth 1 \ +# https://github.com/OCA/web.git \ +# /tmp/oca-repos/web \ +# && mv /tmp/oca-repos/web/web_environment_ribbon \ +# /tmp/oca-repos/web/web_responsive \ +# /tmp/oca-repos/web/web_no_bubble \ +# /tmp/oca-repos/web/web_timeline \ +# /newroot/opt/odoo/additional_addons/ \ +# && rm -rf /tmp/oca-repos/ \ +# && find /newroot/opt/odoo/additional_addons/*/i18n/ -type f -not -name 'fr.po' -delete \ +# && git clone -b 16.0 --depth 1 \ +# https://sources.le-filament.com/lefilament/remove_login_links.git \ +# /newroot/opt/odoo/private_addons/remove_login_links \ +# && git clone -b 16.0 --depth 1 \ +# https://sources.le-filament.com/lefilament/lefilament_release_agent.git \ +# /newroot/opt/odoo/private_addons/lefilament_release_agent + +# Fix a ldap library bug. +RUN echo -n "INPUT ( libldap.so )" > /usr/lib/libldap_r.so + +# Install Python requirements. +RUN pip install --requirement /newroot/opt/odoo/odoo/requirements.txt + +# Only copy libraries of needed binaries to new root. +RUN ls \ + /lib/libz.so* \ + /usr/bin/python3* \ + /usr/lib/libexpat.so* \ + /usr/lib/libfontconfig.so* \ + /usr/lib/libfreetype.so* \ + /usr/lib/libjpeg.so* \ + /usr/lib/libpq.so* \ + /usr/lib/libpython3.so* \ + /usr/lib/python3.10/lib-dynload/*.so \ + /usr/lib/python3.10/site-packages/*.so \ + /usr/lib/libX11.so* \ + /usr/lib/libXrender.so* \ + > to_copy \ + && xargs -a to_copy -I R ldd R \ + | tr -s '[:blank:]' '\n' \ + | grep '^/' \ + | sed 's/://' \ + | sort -u \ + | xargs cp -aL --parents -t /newroot/ \ + && xargs -a to_copy cp -a --parents -t /newroot/ + +# Copy Python libraries. +RUN cp -a --parents \ + /usr/lib/python3.10/ \ + /newroot + +COPY --from=wkhtmltopdf /bin/wkhtmltopdf /newroot/bin/wkhtmltopdf +COPY ./entrypoint-scratch.sh /newroot/entrypoint.sh + +# Add odoo user. +RUN echo 'odoo:x:1:1:::' >> /newroot/etc/passwd \ + && echo 'odoo:x:1:' >> /newroot/etc/group \ + && chown -R 1:1 /newroot/opt/odoo/ \ + && chmod 555 /newroot/entrypoint.sh \ + && mkdir /newroot/tmp \ + && chmod 1777 /newroot/tmp + + +# Final image. +FROM scratch + +COPY --from=build /newroot / + +# Mount /opt/odoo/data to allow restoring filestore. +VOLUME ["/opt/odoo/data/"] + +# Expose Odoo services. +EXPOSE 8069 + +# Set default user when running the container. +USER odoo + +# Start +ENTRYPOINT ["/entrypoint.sh"] +CMD ["odoo"] + +# Metadata +LABEL org.label-schema.schema-version="16.0" \ + org.label-schema.vendor=LeFilament \ + org.label-schema.license=Apache-2.0 \ + org.label-schema.vcs-url="https://sources.le-filament.com/lefilament/odoo_docker" diff --git a/entrypoint-scratch.sh b/entrypoint-scratch.sh new file mode 100755 index 0000000..d11e0b4 --- /dev/null +++ b/entrypoint-scratch.sh @@ -0,0 +1,87 @@ +#!/bin/sh + +# set the postgres database host, port, user and password according to the environment +# and pass them as arguments to the odoo process if not present in the config file +: ${HOST:=${DB_PORT_5432_TCP_ADDR:='db'}} +: ${PORT:=${DB_PORT_5432_TCP_PORT:=5432}} +: ${USER:=${DB_ENV_POSTGRES_USER:=${POSTGRES_USER:='odoo'}}} +: ${PASSWORD:=${DB_ENV_POSTGRES_PASSWORD:=${POSTGRES_PASSWORD:='odoo'}}} + +check_config() { + param="$1" + value="$2" + if ! grep -q -E "^\s*\b${param}\b\s*=" /opt/odoo/etc/odoo.conf ; then + DB_ARGS="${DB_ARGS} --${param} ${value}" + fi; +} + +unaccent_db() { + /usr/bin/python3 -c "import psycopg2 + +try: + conn = psycopg2.connect(database='postgres', user='${USER}', password='${PASSWORD}', host='${HOST}', port='${PORT}') +except: + print('err: init: fail to connect to database') + exit(11) + +cur = conn.cursor() +try: + cur.execute(\"SELECT datname FROM pg_database WHERE datname='${PGDATABASE}'\") +except: + print('err: init: fail to execute request') + cur.close() + conn.close() + exit(12) + +if not cur.fetchall(): + cur.close() + conn.close() + exit(1) + +try: + cur.execute('CREATE EXTENSION IF NOT EXISTS unaccent') +except: + print('err: init: fail to execute request') + cur.close() + conn.close() + exit(13) + +conn.commit() +cur.close() +conn.close() +exit(0)" + + return $? +} + +DB_ARGS='' +check_config "db_host" "$HOST" +check_config "db_port" "$PORT" +check_config "db_user" "$USER" +check_config "db_password" "$PASSWORD" + +unaccent_db +return_code=$? +[ "$return_code" -gt 10 ] && exit 1 +if [ "$return_code" == 1 ]; then + echo "info: init: database $PGDATABASE does not exist" + DB_ARGS="${DB_ARGS} --load-language fr_FR" +fi + +case "$1" in + -- | odoo) + shift + if [[ "$1" == "scaffold" ]] ; then + exec /opt/odoo/odoo/odoo-bin -c /opt/odoo/etc/odoo.conf "$@" + else + exec /opt/odoo/odoo/odoo-bin -c /opt/odoo/etc/odoo.conf "$@" ${DB_ARGS} + fi + ;; + -*) + exec /opt/odoo/odoo/odoo-bin -c /opt/odoo/etc/odoo.conf "$@" ${DB_ARGS} + ;; + *) + exec "$@" +esac + +exit 1 -- GitLab