Simple yet powerful Odoo image for Docker maintained by Elico Corporation.
- Usage
- Security
- Data persistency
- Host user mapping
- Odoo configuration file
- Additional Odoo modules
- Run a bash script at startup
- How to extend this image
- Roadmap
- Bug Tracker
- Credits
Usage^
In order to use this image, a recent version of Docker must be installed on the host. For more information about Docker Engine, see the official documentation.
Run the image^
Running this image without specifying any command will display this help message:
$ docker run elicocorp/odoo:10.0
To display the user manual, run the image with the command man
. Redirecting
stdout
to less
is highly recommended:
$ docker run elicocorp/odoo:10.0 man | less
To start Odoo, run the image with the command start
:
$ docker run elicocorp/odoo:10.0 start
The easiest way to use this image is to run it along with a PostgreSQL
image. By default, Odoo is configured to connect with a PostgreSQL host named
db
.
Note: The PostgreSQL image of Elico Corp can be used as well.
Compose example^
Below is an example of a simple docker-compose.yml
to use this image. For
more information about Compose, see the official documentation.
version: '3.3'
services:
postgres:
image: postgres:9.5
environment:
- POSTGRES_USER=odoo
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
environment:
- ODOO_DB_USER=odoo
Once this file is created, simply move to the corresponding folder and run the following command to start Odoo:
$ docker-compose up
Note 1: With this configuration, Odoo will be accessible at the following URL only from the local host: http://127.0.0.1:8069
It is possible to publish it following one of these options:
- map a reverse-proxy to
127.0.0.1:8069
- remove the
127.0.0.1:
prefix in order to publish the port8069
outside the local host
Note 2: With this configuration:
- Odoo is running without master password
odoo
PostgreSQL user is a superuser who doesn't require any password
See Security section for more info.
Note 3: With this configuration, all the data will be lost once the containers are stopped.
See Data persistency section for more info.
Security^
In order to improve the security, it is recommended to:
- set a master password for Odoo using
ODOO_ADMIN_PASSWD
- start PostgreSQL with a different superuser (e.g.
postgres
) - give the superuser a password using
POSTGRES_PASSWORD
- create a separate PostgreSQL user for Odoo (e.g.
odoo
) with his own password and specify it usingODOO_DB_PASSWORD
Note: Run below SQL queries with PostgreSQL superuser to create the odoo
user:
CREATE user odoo WITH password 'strong_pg_odoo_password';
ALTER user odoo WITH createdb;
The docker-compose.yml
should look like:
version: '3.3'
services:
postgres:
image: postgres:9.5
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=strong_pg_superuser_password
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
environment:
- ODOO_ADMIN_PASSWD=strong_odoo_master_password
- ODOO_DB_USER=odoo
- ODOO_DB_PASSWORD=strong_pg_odoo_password
Note: If Odoo is behind a reverse proxy, it is also suggested to change the port published by the container (though this port is actually not opened to the outside). For instance:
ports:
- 127.0.0.1:12345:8069
Data persistency^
As soon as the containers are removed, all the modifications (e.g. database, attachments, etc.) will be lost. There are 2 main volumes that must be made persistent in order to preserve the data:
- the PostgreSQL database in
/var/lib/postgresql/data
- the Odoo filestore in
/opt/odoo/data/filestore
Optionally, it is also possible to map the Odoo sessions folder in
/opt/odoo/data/sessions
In the following example, these volumes are mapped under the folder volumes
which is in the same folder as the docker-compose.yml
. This command will
create the corresponding folders:
mkdir -p ./volumes/{postgres,odoo/filestore,odoo/sessions}
The docker-compose.yml
should look like:
version: '3.3'
services:
postgres:
image: postgres:9.5
volumes:
- ./volumes/postgres:/var/lib/postgresql/data
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=strong_pg_superuser_password
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
volumes:
- ./volumes/odoo/filestore:/opt/odoo/data/filestore
- ./volumes/odoo/sessions:/opt/odoo/data/sessions
environment:
- ODOO_ADMIN_PASSWD=strong_odoo_master_password
- ODOO_DB_USER=odoo
- ODOO_DB_PASSWORD=strong_pg_odoo_password
Note: With this configuration, all the data created in the volumes will belong to the user whose UID matches the user running inside the container.
See Host user mapping section for more info.
Host user mapping^
Default host user mapping in Docker^
Each Docker image defines its own users. Users only exist inside the running container.
For instance:
- in
elicocorp/odoo
image, the default user that will run the Odoo process isodoo
with UID1000
- in
postgres
image, the default user that will run the PostgreSQL process ispostgres
with UID999
Whenever those users are used inside the container, Docker will actually use the corresponding user on the host running Docker. The mapping is made on the UID, not on the user name.
If the user elico
with UID 1000
exists on the host, when running the Odoo
image with the default user, the Odoo process executed by the odoo
user
inside the container will actually be executed by the host user elico
.
Note: The users don't have to actually exist on the host for the container to use them. Anonymous users with the corresponding UID will be created automatically.
If the with UID 999
doesn't exist on the host, when running the PostgreSQL
image with the default user, the PostgreSQL process executed by the postgres
user inside the container will actually be executed by the anonymous host user
with UID 999
.
Host user mapping and volumes^
When the user inside the container owns files that belong to a volume, the corresponding files in the folder mapped to the volume on the host will actually belong to the corresponding user on the host.
Following the previous example:
- in the Odoo container, the files created by the
odoo
user in the folder/opt/odoo/data/filestore
will be stored on the host in the folder./volumes/odoo/filestore
and belong to the host userelico
- in the PostgreSQL container, the files created by the
postgres
user in the folder/var/lib/postgresql/data
will be stored on the host in the folder./volumes/postgres
and belong to the anonymous host user with UID999
Impact^
When having root
privileges on the host, the default host user mapping
behavior is usually not a big issue. The main impact is that the files mapped
with a volume might belong to users that don't have anything to do with the
corresponding Docker services.
In the previous example:
- the host user
elico
will be able to read the content of the Odoo filestore - the anonymous host user with UID
999
will be able to read the PostgreSQL database files
It is possible to avoid this by creating host users with the corresponding UIDs in order to control which host user owns the files in a volume.
However, a user with limited system privileges (e.g. no sudo
) will have a
bigger issue. The typical use case is a user with limited system privileges
that maps a volume inside his home folder. He would expect to own all the files
under his home folder, which won't be the case.
Following the previous example, if the host user seb
with UID 1001
starts
the image from his home folder:
- the files in
./volumes/odoo/filestore
will belong to the host userelico
- the files in
./volumes/postgres
will belong to the anonymous host user with UID999
The host user seb
will not be able to access those files even though they are
located under his own home folder. This can lead to very annoying situations
where a user would require the system administrator to help him delete files
under his own home folder.
Solution^
Each Docker image has its own way to deal with host user mapping:
- for PostgreSQL, see the official documentation (section "Arbitrary --user Notes")
- for this image, use the environment variable
TARGET_UID
as described below
First, the host user needs to find out his UID:
$ echo $UID
Then, simply assign this UID to the environment variable TARGET_UID
.
After starting the Docker containers, all the files created in the volumes will belong to the corresponding host user.
The docker-compose.yml
should look like:
version: '3.3'
services:
postgres:
image: postgres:9.5
volumes:
- ./volumes/postgres:/var/lib/postgresql/data
- /etc/passwd:/etc/passwd:ro
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=strong_pg_superuser_password
user: 1001:1001
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
volumes:
- ./volumes/odoo/filestore:/opt/odoo/data/filestore
- ./volumes/odoo/sessions:/opt/odoo/data/sessions
environment:
- TARGET_UID=1001
- ODOO_ADMIN_PASSWD=strong_odoo_master_password
- ODOO_DB_USER=odoo
- ODOO_DB_PASSWORD=strong_pg_odoo_password
Note: For a more dynamic UID mapping, you can use Compose
variable substitution. Simply export the environment variable UID
before starting the container and replace the UID
with $UID
in the
docker-compose.yml
.
Odoo configuration file^
The configuration file is generated automatically at startup. Any available
Odoo parameter can be provided as an environment variable, prefixed by ODOO_
.
Note: As a convention, it is preferrable to use only big caps but this is not mandatory. The parameters will be converted to small caps in the configuration file.
In the previous docker-compose.yml
examples, the following Odoo parameters
have already been defined:
admin_passwd
: environment variableODOO_ADMIN_PASSWD
db_user
: environment variableODOO_DB_USER
db_password
: environment variableODOO_DB_PASSWORD
For a complete list of Odoo parameters, see the documentation.
It is also possible to use a custom Odoo configuration file. The most common ways are:
ADD
the configuration file in/opt/odoo/etc/odoo.conf
using aDockerfile
- Map the
/opt/odoo/etc/odoo.conf
using a volume
Additional Odoo modules^
This image allows to load additional Odoo modules through the volume
/opt/odoo/additional_addons
. When adding modules manually in that folder, the
Odoo parameter addons_path
must be defined accordingly:
addons_path = /opt/odoo/additional_addons,/opt/odoo/sources/odoo/addons
Note: The previous configuration assumes that all the modules are at the
root of the folder /opt/odoo/additional_addons
. Depending on the folder
structure, the parameter might need to be adapted.
Automatically fetch Git repositories^
This image is able to automatically fetch (e.g. git clone
) a Git
repository containing a set of modules. It is based on the
cross repository dependency management system introduced by
the OCA.
Basically, this image is able to recursively fetch Git repositories in the
/opt/odoo/additional_addons
volume. Once all the repositories have been
fetched, the addons_path
parameter will be generated automatically.
The cross repository dependency is based on the
oca_dependencies.txt
syntax.
Note: This image integrates a Git repositories cache system. If some of the
repositories already exist in the volume (e.g. when restarting the container),
the container will pull (e.g. git pull
) them instead of cloning them, which
allows for much faster boot.
The easiest way to clone a Git repository is to set the environment variable
ADDONS_REPO
with the URL of the repository.
For instance, in order to fetch the OCA Project Git repository,
as well as all the Git repositories it depends on, you can use the following
docker-compose.yml
:
version: '3.3'
services:
postgres:
image: postgres:9.5
volumes:
- ./volumes/postgres:/var/lib/postgresql/data
- /etc/passwd:/etc/passwd:ro
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=strong_pg_superuser_password
user: 1001:1001
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
volumes:
- ./volumes/odoo/addons:/opt/odoo/additional_addons
- ./volumes/odoo/filestore:/opt/odoo/data/filestore
- ./volumes/odoo/sessions:/opt/odoo/data/sessions
environment:
- ADDONS_REPO=https://github.com/OCA/project.git
- TARGET_UID=1001
- ODOO_ADMIN_PASSWD=strong_odoo_master_password
- ODOO_DB_USER=odoo
- ODOO_DB_PASSWORD=strong_pg_odoo_password
Note: After the repositories have been fetched, it might not be required to
pull them every time the container is restarted. In that case, simply set the
environment variable FETCH_OCA_DEPENDENCIES
to False
(default value is
True
) in order to boot much faster, e.g.:
environment:
- FETCH_OCA_DEPENDENCIES=False
Fetch multiple independent repositories^
It might be necessary to fetch more than one Git repository (and the
repositories it depends on). In that case, instead of using the ADDONS_REPO
environment variable, simply create one oca_dependencies.txt
file and put it
at the root of the /opt/odoo/additional_addons
volume.
For instance, if you want to fetch the
OCA account payment modules repository along with the
OCA project repository, put the following oca_dependencies.txt
in the
/opt/odoo/additional_addons
volume:
# list the OCA project dependencies, one per line
# add a github url if you need a forked version
project https://github.com/OCA/project.git
account-payment https://github.com/OCA/account-payment.git
Fetch private GitHub repositories^
This image is able to pull multiple private GitHub repositories when provided a valid SSH key that has read access to these repositories. The URL for GitHub SSH authentication is available under the "Clone with SSH" option.
Simply put the SSH private key whose name must be id_rsa
in the volume
/opt/odoo/ssh
. Since Odoo doesn't need to write in that volume, you can use
the ro
option to mount a read-only volume.
The docker-compose.yml
should look like:
version: '3.3'
services:
postgres:
image: postgres:9.5
volumes:
- ./volumes/postgres:/var/lib/postgresql/data
- /etc/passwd:/etc/passwd:ro
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=strong_pg_superuser_password
user: 1001:1001
odoo:
image: elicocorp/odoo:10.0
command: start
ports:
- 127.0.0.1:8069:8069
links:
- postgres:db
volumes:
- ./volumes/odoo/addons:/opt/odoo/additional_addons
- ./volumes/odoo/filestore:/opt/odoo/data/filestore
- ./volumes/odoo/sessions:/opt/odoo/data/sessions
- ./volumes/odoo/ssh:/opt/odoo/ssh:ro
environment:
- [email protected]:Elico-Corp/odoo-private-addons.git
- TARGET_UID=1001
- ODOO_ADMIN_PASSWD=strong_odoo_master_password
- ODOO_DB_USER=odoo
- ODOO_DB_PASSWORD=strong_pg_odoo_password
Note: If the host user has a valid SSH key under the .ssh
folder of his
home folder, he can map his .ssh
folder instead, e.g.:
volumes:
- ~/.ssh:/opt/odoo/ssh:ro
Run a bash script at startup^
In some cases, it might be useful to run some commands in the container before
starting Odoo. After the Odoo target user has been created, the container will
execute a bash script with the container user root
.
The script is located at /opt/scripts/startup.sh
and can be mapped with a
volume or added via a Dockerfile
.
How to extend this image^
This image comes with all the dependencies required to run the standard version of Odoo. However, some additionnal modules might require an extra setup.
While the startup script is a way to achieve this, the changes it operates in the OS of the container are not persistent. Such setup would be performed every time the container is restarted, which could induce long delay in the boot process.
In order to make those changes persistent, simply create a child Docker image by extending this image.
The below example shows how to install the dependencies captcha
and
simplecrypt
for the Odoo v8 module website_captcha_nogoogle
.
This is how the Dockerfile
would look like:
FROM elicocorp/odoo:8.0
MAINTAINER Elico Corp <[email protected]>
RUN pip install --upgrade cffi
RUN pip install captcha simple-crypt recaptcha-client
RUN pip install --upgrade pillow
Save it as ./build/odoo/Dockerfile
. Then, in docker-compose.yml
, replace
the image
instruction with a build
instruction, e.g.:
odoo:
build: ./build/odoo
When starting the container with docker-compose up
, Docker will first build
the image. In order to re-build the odoo
image, use:
$ docker-compose build odoo
Note: Extend an image is an extremely versatile feature of Docker. The only limit is your imagination! For instance, check out the Elico Corp Odoo Docker image localized for China.
Roadmap^
- Use the code of
maintainer-quality-tools
to pull theoca_dependencies.txt
Bug Tracker^
Bugs are tracked on GitHub Issues. In case of trouble, please check there if your issue has already been reported. If you spotted it first, help us smash it by providing detailed and welcomed feedback.
Credits^
Contributors^
- Sebastien Maillard [email protected]
- Eric Caudal [email protected]
- Noah Wang [email protected]
- Augustin Cisterne-Kaas [email protected]
Maintainer^
This project is maintained by Elico Corporation.
Elico Corp is an innovative actor in China, Hong-Kong and Singapore servicing well known international companies and as well as local mid-sized businesses. Since 2010, our seasoned Sino-European consultants have been providing full range Odoo services:
- Business consultancy for Gap analysis, BPM, operational work-flows review.
- Ready-to-use ERP packages aimed at starting businesses.
- Odoo implementation for manufacturing, international trading, service industry and e-commerce.
- Connectors and integration with 3rd party software (Magento, Taobao, Coswin, Joomla, Prestashop, Tradevine etc...).
- Odoo Support services such as developments, training, maintenance and hosting.
Our headquarters are located in Shanghai with branch in Singapore servicing customers from all over Asia Pacific.
Contact information: Sales [email protected]