Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
260 changes: 171 additions & 89 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
FROM ubuntu:16.04


FROM ubuntu:18.04

ENV PG_BRANCH=develop \
WEBWORK_URL=/webwork2 \
Expand All @@ -22,76 +20,142 @@ ENV PG_BRANCH=develop \
# Only /var/log/apache2 is handled by /etc/logrotate.d/apache2.
APACHE_LOG_DIR=/var/log/apache2 \
APP_ROOT=/opt/webwork \
DEBIAN_FRONTEND=noninteractive \
DEBCONF_NONINTERACTIVE_SEEN=true \
DEV=0

ENV WEBWORK_DB_DSN=DBI:mysql:${WEBWORK_DB_NAME}:${WEBWORK_DB_HOST}:${WEBWORK_DB_PORT} \
WEBWORK_ROOT=$APP_ROOT/webwork2 \
PG_ROOT=$APP_ROOT/pg \
PATH=$PATH:$APP_ROOT/webwork2/bin

# For ubuntu 18.04 add libemail-address-xs-perl
# For ubuntu 18.04 replace texlive-generic-recommended with texlive-plain-generic
# texlive-generic-recommended # For ubuntu 16.04 - contains path.sty
# texlive-plain-generic # For ubuntu 18.04 - contains path.sty



RUN apt-get update \
&& apt-get -y upgrade \

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would remove this, as from Dockerfile best practices (https://docs.docker.com/develop/develop-images/dockerfile_best-practices/)

Avoid RUN apt-get upgrade and dist-upgrade, as many of the “essential” packages from the parent images cannot upgrade inside an unprivileged container. If a package contained in the parent image is out-of-date, contact its maintainers. If you know there is a particular package, foo, that needs to be updated, use apt-get install -y foo to update automatically.

&& apt-get install -y --no-install-recommends --no-install-suggests \
apache2 \
curl \
dvipng \
gcc \
libapache2-request-perl \
libcrypt-ssleay-perl \
libdatetime-perl \
libdancer-perl \
libdancer-plugin-database-perl \
libdbd-mysql-perl \
libemail-address-perl \
libexception-class-perl \
libextutils-xsbuilder-perl \
libfile-find-rule-perl-perl \
libgd-perl \
libhtml-scrubber-perl \
libjson-perl \
liblocale-maketext-lexicon-perl \
libmail-sender-perl \
libmime-tools-perl \
libnet-ip-perl \
libnet-ldap-perl \
libnet-oauth-perl \
libossp-uuid-perl \
libpadwalker-perl \
libpath-class-perl \
libphp-serialization-perl \
libxml-simple-perl \
libsoap-lite-perl \
libsql-abstract-perl \
libstring-shellquote-perl \
libtemplate-perl \
libtext-csv-perl \
libtimedate-perl \
libuuid-tiny-perl \
libxml-parser-perl \
libxml-writer-perl \
libxmlrpc-lite-perl \
libapache2-reload-perl \
libxmlrpc-lite-perl \
libxml-simple-perl \
make \
netpbm \
preview-latex-style \
texlive \
texlive-latex-extra \
libc6-dev \
git \
mysql-client \
&& rm -fr /var/lib/apt/lists/*

# Warning - when I tried to include XML::Simple near the start of the first "cpanm install" line, there was an error:
# Building and testing XMLRPC-Lite-0.717 ... ! Installing XMLRPC::Lite failed. See /root/.cpanm/work/1551887935.125/build.log for details. Retry with --force to force install it.
# so it was put into a second "cpanm install" line.

RUN curl -Lk https://cpanmin.us | perl - App::cpanminus \
&& cpanm install XML::Parser::EasyTree Iterator Iterator::Util Pod::WSDL Array::Utils HTML::Template Mail::Sender Email::Sender::Simple Data::Dump Statistics::R::IO

##RUN cpanm install XML::Simple \
# && rm -fr ./cpanm /root/.cpanm /tmp/*
apache2 \
curl \
dvipng \
gcc \
libapache2-request-perl \
libcrypt-ssleay-perl \
libdatetime-perl \
libdancer-perl \
libdancer-plugin-database-perl \
libdbd-mysql-perl \
libemail-address-xs-perl \
libexception-class-perl \
libextutils-xsbuilder-perl \
libfile-find-rule-perl-perl \
libgd-perl \
libhtml-scrubber-perl \
libjson-perl \
liblocale-maketext-lexicon-perl \
libmail-sender-perl \
libmime-tools-perl \
libnet-ip-perl \
libnet-ldap-perl \
libnet-oauth-perl \
libossp-uuid-perl \
libpadwalker-perl \
libpath-class-perl \
libphp-serialization-perl \
libxml-simple-perl \
libsoap-lite-perl \
libsql-abstract-perl \
libstring-shellquote-perl \
libtemplate-perl \
libtext-csv-perl \
libtimedate-perl \
libuuid-tiny-perl \
libxml-parser-perl \
libxml-writer-perl \
libxmlrpc-lite-perl \
libapache2-reload-perl \
cpanminus \
libxml-parser-easytree-perl \
libiterator-perl \
libiterator-util-perl \
libpod-wsdl-perl \
libtest-xml-perl \
libmodule-build-perl \
libxml-semanticdiff-perl \
libxml-xpath-perl \
libpath-tiny-perl \
libarray-utils-perl \
libhtml-template-perl \
libtest-pod-perl \
libemail-sender-perl \
libmail-sender-perl \
libmodule-pluggable-perl \
libemail-date-format-perl \
libcapture-tiny-perl \
libthrowable-perl \
libdata-dump-perl \
libfile-sharedir-install-perl \
libclass-tiny-perl \
libtest-requires-perl \
libtest-mockobject-perl \
libtest-warn-perl \
libsub-uplevel-perl \
libtest-exception-perl \
libuniversal-can-perl \
libuniversal-isa-perl \
libtest-fatal-perl \
libjson-xs-perl \

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I find using system packages instead of cpan sometimes can be troublesome. Often times, system packages are not up-to-date. What packages people are using when doing webwork core development? I suggest we use the same packages for consistency and stability.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I hope most developers will now be working using the "current" Docker image + their local modifications, so standardizing on what is packed by our root OS image is convenient, for what is available. As I understand it, that is also how @mgage would like to see core system developers working.

If there are specific CPAN packages where a newer version are needed, we should use them and document it in the WW install instructions, as such issues are likely to effect people on some Linux distributions (ex. RHEL/CentOS) where changes to newer versions are very slow to happen.

I think @mgage and I ran into such an issue with the DBI or DBD on an older machine.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Having started out using cpan packages almost exclusively I have found system packages a bit quicker and sometimes easier. We have also run into problems where the system files are out of date. On the other hand we have run into several cpan modules that are unreliable to download and install (XML-simple
libxml-simple-perl \ libsoap-lite-perl \
were two examples where loading the CPAN modules were would sometimes work and sometimes not.
I haven't yet found a universal rule for preferring system install over cpan install.

make \
netpbm \
preview-latex-style \
texlive \
texlive-latex-extra \
texlive-plain-generic \
texlive-xetex \
texlive-latex-recommended \
texlive-lang-other \
texlive-lang-arabic \
libc6-dev \
git \
mysql-client \
tzdata \
apt-utils \
locales \
debconf-utils \
vim \
telnet \
mc \
file \
ssl-cert \
ca-certificates \
culmus \
fonts-linuxlibertine \
lmodern \

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would avoid to include the tools that are not necessary to run webwork, e.g. vim, telnet, etc. The goal is to build a smaller image that doesn't necessary include everything.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Point accepted. I found telnet helpful when there were issues with outgoing connections, and some reasonable editor is sometimes needed when working/debugging in the running container. However, they can be installed on the running container as needed.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I also found such tools very useful. Especially during development it is handy not to be in need to install them after every rebuild.

I did not catch up with all the discussions going on, but maybe one option could be to have two Dockerfiles, one mainly for production and one mainly for development. Of course this would require to maintain two Dockerfiles and probably some code duplication.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I just saw #972 (comment). I agree with @xcompass in that having a single Dockerfile / image for dev and ops would be desirable. @xcompass how is your development cycle? When you change parts of webwork2 or pg, do you do this on the host system and rebuild the container? If this is the recommended way, then I think we should try to assure that such kind of changes will result in short rebuild times.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In trying to understand how to speed up docker performance on the mac I have found that Docker allows for "cascading" files -- at least for docker-compose.yml.
You can have docker-compose.yml (for production) and docker-compose.dev.yml (for development) with the latter containing only the additions needed for development.
docker-compose -f docker-compose.yml -f docker-compose-dev.yml up create the development environment.

&& apt-get clean \
&& rm -fr /var/lib/apt/lists/* /tmp/*

# texlive-generic-recommended # For ubuntu 16.04 - contains path.sty
# texlive-plain-generic # For ubuntu 18.04 - contains path.sty

RUN echo 'America/New_York' > /etc/timezone \
Comment thread
taniwallach marked this conversation as resolved.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would use UTC for container timezone as it is best practises for ops. People often mount the /etc/timezone file from host to have container in sync with host.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry, I'm not a devops expert (yet). That makes lots of sense and will be done, and I will add a note somewhere in docker-compose.yml about maybe mounting the system file.

@xcompass - what do you recommend about the generation of locale files? I think the same logic regarding timezone means that the code to generate locales might best be moved to the very end of the Dockerfile or to the startup file.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense 😄

&& echo "tzdata tzdata/Areas select America\ntzdata tzdata/Zones/America select New_York\nlocales locales/locales_to_be_generated multiselect en_US.UTF-8 UTF-8\nlocales locales/default_environment_locale select en_US.UTF-8\ndebconf debconf/frontend select Noninteractive\nca-certificates ca-certificates/trust_new_crts select yes" > /tmp/preseed.txt \
&& cp -a /etc/locale.gen /etc/locale.gen.orig \
&& echo "en_US ISO-8859-1\nen_US.UTF-8 UTF-8" > /etc/locale.gen \
&& rm -f /etc/localtime /etc/timezone \
&& debconf-set-selections /tmp/preseed.txt \
&& dpkg-reconfigure -f noninteractive tzdata \
&& /usr/sbin/locale-gen

# Perl module installs - those not packaged for Ubuntu

RUN cpanm install Statistics::R::IO \
&& rm -fr ./cpanm /root/.cpanm /tmp/*

# XML::Parser::EasyTree Iterator Iterator::Util Pod::WSDL Array::Utils HTML::Template Mail::Sender Email::Sender::Simple Data::Dump

RUN mkdir -p $APP_ROOT/courses $APP_ROOT/libraries $APP_ROOT/webwork2

Expand All @@ -104,72 +168,90 @@ RUN mkdir -p $APP_ROOT/courses $APP_ROOT/libraries $APP_ROOT/webwork2
# && mv webwork2-${WEBWORK_BRANCH} $APP_ROOT/webwork2 \
# && rm -rf /tmp/${WEBWORK_BRANCH}.tar.gz /tmp/webwork2-${WEBWORK_BRANCH}

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does the container not include webwork source anymore? What if I'm an OPL developer and I have no interests in changing webwork core code. Or I just want to test webwork out. I still needs to download a copy of webwork source code outside container.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point. For any operational use it should be included, even if system developers don't need it.


# The next block installs PG from Git, using the branch set above as PG_BRANCH.
# and compiles color.c in the copy INSIDE the image.

RUN curl -fSL https://github.com/openwebwork/pg/archive/${PG_BRANCH}.tar.gz -o /tmp/${PG_BRANCH}.tar.gz \
&& tar xzf /tmp/${PG_BRANCH}.tar.gz \
&& mv pg-${PG_BRANCH} $APP_ROOT/pg \
&& rm /tmp/${PG_BRANCH}.tar.gz \
&& curl -fSL https://github.com/openwebwork/webwork-open-problem-library/archive/master.tar.gz -o /tmp/opl.tar.gz \
&& tar xzf /tmp/opl.tar.gz \
&& mv webwork-open-problem-library-master $APP_ROOT/libraries/webwork-open-problem-library \
&& rm /tmp/opl.tar.gz
&& cd $APP_ROOT/pg/lib/chromatic \
&& gcc color.c -o color

# The next block would install the OPL from Git. Disabled for developers who
# use an external OPL tree.

#RUN curl -fSL https://github.com/openwebwork/webwork-open-problem-library/archive/master.tar.gz -o /tmp/opl.tar.gz \
# && tar xzf /tmp/opl.tar.gz \
# && mv webwork-open-problem-library-master $APP_ROOT/libraries/webwork-open-problem-library \
# && rm /tmp/opl.tar.gz

# MathJax

RUN curl -fSL https://github.com/mathjax/MathJax/archive/master.tar.gz -o /tmp/mathjax.tar.gz \
&& tar xzf /tmp/mathjax.tar.gz \
&& mv MathJax-master $APP_ROOT/MathJax \
&& rm /tmp/mathjax.tar.gz
#&& rm /tmp/VERSION
#curl -fSL https://github.com/openwebwork/webwork2/archive/WeBWorK-${WEBWORK_VERSION}.tar.gz -o /tmp/WeBWorK-${WEBWORK_VERSION}.tar.gz \
#&& tar xzf /tmp/WeBWorK-${WEBWORK_VERSION}.tar.gz \
#&& mv webwork2-WeBWorK-${WEBWORK_VERSION} $APP_ROOT/webwork2 \
#&& rm /tmp/WeBWorK-${WEBWORK_VERSION}.tar.gz \


RUN echo "PATH=$PATH:$APP_ROOT/webwork2/bin" >> /root/.bashrc

COPY . $APP_ROOT/webwork2


# Move these lines into docker-entrypoint.sh so the bind mount of courses
# will be available
#RUN cd $APP_ROOT/webwork2/courses.dist \
# && cp *.lst $APP_ROOT/courses/ \
# && cp -R modelCourse $APP_ROOT/courses/

RUN cd $APP_ROOT/pg/lib/chromatic \
&& gcc color.c -o color
COPY docker-config/ssl/default-ssl.conf /etc/apache2/sites-available/default-ssl.conf

# setup apache
# if no SSL needed - comment out the line && a2enmod ssl && a2ensite default-ssl \

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would change it to if SSL is needed - uncomment the line && a2enmod ssl && a2ensite default-ssl

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please see the revised PR #980 which focuses on the Docker changes only. I tried to implement all the changes suggested.

RUN cd $APP_ROOT/webwork2/conf \
&& cp webwork.apache2.4-config.dist webwork.apache2.4-config \
&& cp $APP_ROOT/webwork2/conf/webwork.apache2.4-config /etc/apache2/conf-enabled/webwork.conf \
&& a2dismod mpm_event \
&& a2enmod mpm_prefork \
&& sed -i -e 's/Timeout 300/Timeout 1200/' /etc/apache2/apache2.conf \
&& sed -i -e 's/MaxRequestWorkers 150/MaxRequestWorkers 20/' \
-e 's/MaxConnectionsPerChild 0/MaxConnectionsPerChild 100/' \
/etc/apache2/mods-available/mpm_prefork.conf \
-e 's/MaxConnectionsPerChild 0/MaxConnectionsPerChild 100/' \
/etc/apache2/mods-available/mpm_prefork.conf \
&& cp $APP_ROOT/webwork2/htdocs/favicon.ico /var/www/html \
&& mkdir -p $APACHE_RUN_DIR $APACHE_LOCK_DIR $APACHE_LOG_DIR \
&& mkdir /etc/ssl/local \
&& a2enmod rewrite \
&& sed -i -e 's/^<Perl>$/\
PerlPassEnv WEBWORK_URL\n\
PerlPassEnv WEBWORK_ROOT_URL\n\
PerlPassEnv WEBWORK_DB_DSN\n\
PerlPassEnv WEBWORK_DB_USER\n\
PerlPassEnv WEBWORK_DB_PASSWORD\n\
PerlPassEnv WEBWORK_SMTP_SERVER\n\
PerlPassEnv WEBWORK_SMTP_SENDER\n\
PerlPassEnv WEBWORK_TIMEZONE\n\
\n<Perl>/' /etc/apache2/conf-enabled/webwork.conf

RUN cd $APP_ROOT/webwork2/ \
PerlPassEnv WEBWORK_URL\n\
PerlPassEnv WEBWORK_ROOT_URL\n\
PerlPassEnv WEBWORK_DB_DSN\n\
PerlPassEnv WEBWORK_DB_USER\n\
PerlPassEnv WEBWORK_DB_PASSWORD\n\
PerlPassEnv WEBWORK_SMTP_SERVER\n\
PerlPassEnv WEBWORK_SMTP_SENDER\n\
PerlPassEnv WEBWORK_TIMEZONE\n\
\n<Perl>/' /etc/apache2/conf-enabled/webwork.conf
#\
# && a2enmod ssl && a2ensite default-ssl
# The LAST line, and the "\" on the line above should be commented out if SSL is not needed

RUN mkdir $APP_ROOT/libraries/webwork-open-problem-library \
&& cd $APP_ROOT/webwork2/ \
&& chown www-data DATA ../courses htdocs/applets logs tmp $APP_ROOT/pg/lib/chromatic \
&& chmod -R u+w DATA ../courses htdocs/applets logs tmp $APP_ROOT/pg/lib/chromatic

COPY docker-entrypoint.sh /usr/local/bin/
COPY docker-config/docker-entrypoint.sh /usr/local/bin/

ENTRYPOINT ["docker-entrypoint.sh"]

EXPOSE 80

# Comment out the next line if SSL is not needed

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would change it to Uncomment the next line if SSL is needed

#EXPOSE 443

WORKDIR $APP_ROOT




Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why so many empty lines?

CMD ["apache2", "-DFOREGROUND"]
32 changes: 32 additions & 0 deletions conf/localOverrides.conf.dist
Original file line number Diff line number Diff line change
Expand Up @@ -512,4 +512,36 @@ $options{useOPLdefFiles}=1;
$permissionLevels{show_answer_group_info_checkbox} = "admin";

$permissionLevels{modify_tags} = "admin";

################################################################################

# Available Hardcopy themes (located in snippets) - adds four XeLaTeX themes
# using polyglossia for multilingual support and fontspec.

$hardcopyThemes = [ qw (
oneColumn
twoColumn
XeLaTeX-oneColumn
XeLaTeX-twoColumn
XeLaTeX-Hebrew-oneColumn
XeLaTeX-Hebrew-twoColumn
)];

# Hardcopy theme names (pretty names for themes)
$hardcopyThemeNames = {
oneColumn => 'pdfLaTeX - English - One Column',
twoColumn => 'pdfLaTeX - English - Two Columns',
XeLaTeX-oneColumn => 'XeLaTeX - English - one Column',
XeLaTeX-twoColumn => 'XeLaTeX - English - two Columns',
XeLaTeX-Hebrew-oneColumn => 'XeLaTeX - Hebrew/English - one Column',
XeLaTeX-Hebrew-twoColumn => 'XeLaTeX - Hebrew/English - two Columns',
};

# Change default Hardcopy theme - in order to use an XeLaTeX theme, we must set
# $externalPrograms{pdflatex} to use xelatex (here or in site.conf) !!!
#$hardcopyTheme = "XeLaTeX-twoColumn";
#$externalPrograms{pdflatex} ="/usr/bin/xelatex --shell-escape";

################################################################################

1; #final line of the file to reassure perl that it was read properly.
6 changes: 6 additions & 0 deletions conf/site.conf.dist
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,12 @@ $externalPrograms{git} = "/usr/bin/git";
# equation rendering/hardcopy utiltiies
####################################################
$externalPrograms{latex} ="/usr/bin/latex";

$externalPrograms{pdflatex} ="/usr/bin/pdflatex --shell-escape";
# Consider using xelatex instead of pdflatex for multilingual use, and
# use polyglossia and fontspec packages (which require xelatex or lualatex).
#$externalPrograms{pdflatex} ="/usr/bin/xelatex --shell-escape";

$externalPrograms{dvipng} ="/usr/bin/dvipng";

####################################################
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@

\vfill
\end{document}
Loading