-
-
Notifications
You must be signed in to change notification settings - Fork 429
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
feat: Add Dockerize option to nuxt project #581
base: master
Are you sure you want to change the base?
Conversation
@@ -0,0 +1,25 @@ | |||
# Dockerfile | |||
FROM node:14-alpine |
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.
- I would suggest going with main (debian) image as default since some native deps cannot be compiled on alpine
- Also would be nice if we split build into two stages example https://github.com/nuxt/nuxt.js/blob/dev/examples/docker-build/Dockerfile#L22
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 alpine version is a very small version. I have been using this config for a long time and it can install packages well, the only problem is that it does not have git by default, which is when we use a package that instead of npm from use git, to solve this problem, I install git manually.
I have also seen some users have problems because the output size of the container with the image node itself is large.
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.
And in this case, if you know something better, I'll be happy for you to share so we can replace it.
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.
It's ok using alpine by default,. Maybe we can add a comment like # FROM node:14
to quickly switch? :)
Using single stage, ends up with final image with full dependencies in intermediate layers (including all devDependencies like webpack). (read more)
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.
alpine > *
also, at geospoc we use nginx to serve as it provides nice brotli support out-of-the-box,
this is a huge change on how deployment of nuxt apps work..
PS. this is the Dockerfile we use at GeoSpoc
# Create the container from the alpine linux image
FROM alpine:latest as stage0
# Add nodejs
RUN apk add --update --no-cache nodejs nodejs-npm
# Set the directory we want to run the next commands for
WORKDIR /frontend
# Copy package.json & package-lock.json
COPY package.json package.json
COPY package-lock.json package-lock.json
# Install the dependencies, can be commented out if you're running the same node version
RUN npm ci
# Copy our source code into the container
COPY . .
# run webpack and the build the project
RUN NODE_ENV=production npm run build
# copy the built app to our served directory
FROM nginx:alpine
# Copy frontend data to dir that'll host the static files
COPY --from=stage0 /frontend/dist /var/www/html
# Copy the respective nginx configuration files
COPY docker/app/nginx/nginx.conf /etc/nginx/nginx.conf
# Copy the wildcard certificates from certs to /etc/ssl
COPY docker/app/nginx/certs/* /etc/ssl/
# build-base will add gcc
RUN apk add --update --no-cache git bash curl make build-base pcre-dev zlib-dev \
&& mkdir ~/brotli && command="nginx -v" && nginxv=$( ${command} 2>&1 ) && nginxlocal=$(echo $nginxv | grep -o '[0-9.]*$') \
&& cd ~/brotli && curl -L "https://nginx.org/download/nginx-$(echo $nginxlocal).tar.gz" -o nginx.tar.gz && tar zxvf nginx.tar.gz && rm nginx.tar.gz \
&& git clone https://github.com/google/ngx_brotli.git && cd ngx_brotli && git submodule update --init \
&& cd ~/brotli/nginx-$(echo $nginxlocal) && ./configure --with-compat --add-dynamic-module=../ngx_brotli && make modules \
&& cp -r ./objs/*.so /usr/lib/nginx/modules/ \
&& rm -rf ~/brotli/ \
&& sed -i '1iload_module modules/ngx_http_brotli_filter_module.so; load_module modules/ngx_http_brotli_static_module.so;' /etc/nginx/nginx.conf
# Expose ports.
EXPOSE 80
EXPOSE 443
# start nginx and keep the process from backgrounding and the container from quitting
CMD ["nginx"]
staged builds for life!
@@ -112,5 +112,15 @@ module.exports = [ | |||
{ name: 'Semantic Pull Requests', value: 'semantic-pull-requests' } | |||
], | |||
default: [] | |||
}, | |||
{ | |||
name: 'devOps', |
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.
We may need to somehow enable it only for server target since for full static doesn't makes sense having this option
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 selection of this feature is optional and also due to the code structure, it is not possible to enable this feature based on the condition.
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.
There most certainly are use-cases for deploying full static sites as Dockerized, which except for using nginx itself include also scenarios like using a reverse proxy to expose private services inside a k8s cluster (and possibly whitelisting/blacklisting their endpoints) when the site consumes their API, or to go around CORS issues if the APIs cannot be accessed directly (though in some cases https://axios.nuxtjs.org/options/#proxy may be used for this, but it can't be used if we "already" use nginx anyway)
This seems to be officially suggested by Nuxt at https://nuxtjs.org/docs/2.x/deployment/nginx-proxy
However, note that nginx has some major issues when using it as a reverse proxy for other services; for example it doesn't support search
of /etc/resolv.conf
even if you apply a workaround https://serverfault.com/a/373306 to load the resolver IP, which is vital if you need for the domains to be cached temporarily rather than having the IP be resolved only at startup. There may be even a need for hacks like https://serverfault.com/a/909100 if you need to reload the file itself.
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.
PR pending because we should prefer multistage images.There might be many different approaches to build a docker image for nuxt apps. It would be probably better if we focus on documentation explaining how to deploy projects via docker and some common practices IMO
Of course, making a CI/CD for each project is time consuming and different for each project, and therefore requires a Docker image with a different structure, but in small projects having a code sample can be very helpful. |
2 years is a pretty long time, is there any plan to introduce a first iteration of the Docker image variant yet? I'd like to eventually integrate new improvements or workarounds, but it's difficult to open PRs if nothing has been merged yet. Can we get any information about what is currently being worked on? It would be great if we had a documentation for various use-cases, or even better, if the Dockerfile was self-documented with available next steps after providing users with multiple generation options. For example, dev mode or build vs. generate may differ (and so does SSR), and we need workarounds like
The pros and cons of specific implementations (e.g. base docker images and their versions) could be listed somewhere as a source of truth to make it easier to suggest changes once the dependent technologies further evolve, so that users aren't stuck with ad-hoc decisions in their projects if they prefer zero-configuration. Also related to Nuxt 3 docs: |
This PR adds Dockerfile and docker-compose.yml as devOps option 🐳