I have a container based on nodejs:14
that uses winston
for logging where, the destination is set as console for development and file for production. The container is itself launched with docker-compose up
where, the YAML file has a volumes
entry as ${HOST}/logs:${APP}/logs
for logs. The idea is to ship the logs from the host to archives, log visualization, log rotation, etc. I did read about Configure logging drivers - but, I am avoiding this because of this line.
These files are designed to be exclusively accessed by the Docker daemon. Interacting with these files with external tools may interfere with Docker’s logging system and result in unexpected behavior, and should be avoided.
With winston
, using File
for transport, I could only see the log file on the host but it is empty. This behavior is actually discussed at Winston not creating any output when running in a Docker container. The work around mentioned (towards the end) is to use Console
as the output and add a Dockerfile
entry for redirecting STDOUT
and STDERR
to appropriate files through symbolic links.
The symbolic links will probably depend on the base image. For example, in the issue above, the STDOUT
is referred to as /proc/1/fd/1
whereas, the documentation on View logs for a container or service refers the httpd
example where, the STDOUT
is referred to as /proc/self/fd/1
.
Therefore, the approach with symbolic links does not sound like a straight forward approach.
In fact, the last comment in that thread suggests that CMD
itself be set-up to direct STDOUT
and STDERR
to appropriate files through standard Linux commands. This sounds a better approach.
I have tried the second approach where winston
uses Console
approach but can’t get the files to be written even within the container. This is my Dockerfile
.
FROM node:14 as build
ARG APP_ROOT=/app
ARG APP_PORT=4000
WORKDIR /
RUN mkdir -p ${APP_ROOT}/logs && \
touch ${APP_ROOT}/logs/app.log && \
touch ${APP_ROOT}/logs/app.err
WORKDIR /app
COPY app .
COPY package.json .
COPY package-lock.json .
RUN npm i
EXPOSE ${APP_PORT}
CMD ["node", "index.js"]
FROM gcr.io/distroless/nodejs:14
ARG APP_ROOT=/app
ENV LOG_FILE=${APP_ROOT}/logs/app.log
ENV ERR_FILE=${APP_ROOT}/logs/app.err
COPY --from=build /app /app
COPY --from=build ${APP_ROOT} ${APP_ROOT}
WORKDIR /app
CMD ["index.js", "1>${LOG_FILE}", "2>${ERR_FILE}"]
How do I get log files generated on console, by winston
, to be written to files and read on host? Better yet, how do I get winston
to write to files directly?