如何使用远程配置 运行 Docker 和 node.js
How to run Docker and node.js with remote configurations
我想为开源应用程序提供一个简单易用的 Docker 容器,该应用程序将配置文件的 URL 作为参数并使用该文件。
Docker文件非常简单:
FROM phusion/baseimage
# Use baseimage-docker's init system.
CMD ["/sbin/my_init"]
RUN curl -sL https://deb.nodesource.com/setup_4.x | sudo -E bash -
RUN apt-get update
RUN apt-get install -y nodejs git
ADD . /src
RUN cd /src; npm install; npm update
ENV NODE_ENV production
CMD ["/usr/bin/node", "/src/gitevents.js"]
我发现无法在容器运行时添加文件(使用 ADD 或 ENTRYPOINT),所以我试图在 node.js:
中解决这个问题
docker run -e "CONFIG_URL=https://gist.githubusercontent.com/PatrickHeneise/c97ba221495df0cd9a3b/raw/fda1b8cd53874735349c6310a6643e6fc589a404/gitevents_config.js" gitevents
这会将 CONFIG_URL
设置为我可以在节点中使用的环境变量。但是,我需要下载一个文件,它是异步的,这在当前设置中不起作用。
if (process.env.NODE_ENV === 'production') {
var exists = fs.accessSync(path.join(__dirname, 'common', 'production.js'), fs.R_OK);
if (exists) {
config = require('./production');
} else {
// https download, but then `config` is undefined when running the app the first time.
}
}
node.js 中没有同步下载,有什么解决办法的建议吗?
我很想 Docker 使用 ADD
或 CMD
进行 curl 下载,但我不确定它是如何工作的?
我设法重写了我的配置脚本以异步工作,在我看来仍然不是最好的解决方案。
var config = {};
var https = require('https');
var fs = require('fs');
var path = require('path');
config.load = function(fn) {
if (process.env.NODE_ENV === 'production') {
fs.access(path.join(__dirname, 'production.js'), fs.R_OK, function(error, exists) {
if (exists) {
config = require('./production');
} else {
var file = fs.createWriteStream(path.join(__dirname, 'production.js'));
var url = process.env.CONFIG_URL;
if (!url) {
process.exit(-1);
} else {
https.get(url, function(response) {
response.pipe(file);
file.on('finish', function() {
file.close(function() {
return fn(require('./production'));
});
});
});
}
}
});
} else if (process.env.NODE_ENV === 'test') {
return fn(require('./test'));
} else {
return fn(require('./development'));
}
};
module.exports = exports = config;
ENTRYPOINT
和环境变量的组合怎么样?您可以将 Dockerfile 中的 ENTRYPOINT
设置为 shell 脚本,该脚本将下载环境变量中指定的配置文件,然后启动应用程序。
由于入口点脚本将接收 CMD
中的任何内容作为参数,因此应用程序启动步骤可以通过类似
的方式完成
# Execute CMD.
eval "$@"
另一件事是考虑您的 "config file" 不是文件而只是文本,并在 运行 时将内容传递给容器。
CONFIG="$(curl -sL https://gist.githubusercontent.com/PatrickHeneise/c97ba221495df0cd9a3b/raw/fda1b8cd53874735349c6310a6643e6fc589a404/gitevents_config.js)"
docker 运行 -e "CONFIG_URL=${CONFIG}" gitevents
我想为开源应用程序提供一个简单易用的 Docker 容器,该应用程序将配置文件的 URL 作为参数并使用该文件。
Docker文件非常简单:
FROM phusion/baseimage
# Use baseimage-docker's init system.
CMD ["/sbin/my_init"]
RUN curl -sL https://deb.nodesource.com/setup_4.x | sudo -E bash -
RUN apt-get update
RUN apt-get install -y nodejs git
ADD . /src
RUN cd /src; npm install; npm update
ENV NODE_ENV production
CMD ["/usr/bin/node", "/src/gitevents.js"]
我发现无法在容器运行时添加文件(使用 ADD 或 ENTRYPOINT),所以我试图在 node.js:
中解决这个问题docker run -e "CONFIG_URL=https://gist.githubusercontent.com/PatrickHeneise/c97ba221495df0cd9a3b/raw/fda1b8cd53874735349c6310a6643e6fc589a404/gitevents_config.js" gitevents
这会将 CONFIG_URL
设置为我可以在节点中使用的环境变量。但是,我需要下载一个文件,它是异步的,这在当前设置中不起作用。
if (process.env.NODE_ENV === 'production') {
var exists = fs.accessSync(path.join(__dirname, 'common', 'production.js'), fs.R_OK);
if (exists) {
config = require('./production');
} else {
// https download, but then `config` is undefined when running the app the first time.
}
}
node.js 中没有同步下载,有什么解决办法的建议吗?
我很想 Docker 使用 ADD
或 CMD
进行 curl 下载,但我不确定它是如何工作的?
我设法重写了我的配置脚本以异步工作,在我看来仍然不是最好的解决方案。
var config = {};
var https = require('https');
var fs = require('fs');
var path = require('path');
config.load = function(fn) {
if (process.env.NODE_ENV === 'production') {
fs.access(path.join(__dirname, 'production.js'), fs.R_OK, function(error, exists) {
if (exists) {
config = require('./production');
} else {
var file = fs.createWriteStream(path.join(__dirname, 'production.js'));
var url = process.env.CONFIG_URL;
if (!url) {
process.exit(-1);
} else {
https.get(url, function(response) {
response.pipe(file);
file.on('finish', function() {
file.close(function() {
return fn(require('./production'));
});
});
});
}
}
});
} else if (process.env.NODE_ENV === 'test') {
return fn(require('./test'));
} else {
return fn(require('./development'));
}
};
module.exports = exports = config;
ENTRYPOINT
和环境变量的组合怎么样?您可以将 Dockerfile 中的 ENTRYPOINT
设置为 shell 脚本,该脚本将下载环境变量中指定的配置文件,然后启动应用程序。
由于入口点脚本将接收 CMD
中的任何内容作为参数,因此应用程序启动步骤可以通过类似
# Execute CMD.
eval "$@"
另一件事是考虑您的 "config file" 不是文件而只是文本,并在 运行 时将内容传递给容器。
CONFIG="$(curl -sL https://gist.githubusercontent.com/PatrickHeneise/c97ba221495df0cd9a3b/raw/fda1b8cd53874735349c6310a6643e6fc589a404/gitevents_config.js)"
docker 运行 -e "CONFIG_URL=${CONFIG}" gitevents