Мы пытаемся перенести наши Java-приложения с текущих платформ Elastic Beanstalk JDK 8 на новые, на которых работает Corretto 11 в Amazon Linux 2. Приложение работает хорошо, но способ обработки журналов изменился. Выходные данные веб-процесса теперь хранятся в /var/log/web.stdout.log
и каждая строка имеет префикс с меткой времени и именем процесса, то есть:
May 20 17:00:00 ip-10-48-41-129 web: {"timestamp":"2020-05-20T17:00:00.035Z","message":"...","logger":"...","thread":"MessageBroker-2","level":"INFO"}
Как избавиться от приставки? Эти журналы передаются в CloudWatch, и мы выводим их на стандартный вывод в формате JSON, чтобы позже можно было запросить их с помощью Logs Insights. Но с префиксом Insights не «видит» JSON и просто рассматривает всю строку как текстовый blob.
Я не могу найти на AWS никакой документации по этому поводу. Практически вся документация Elastic Beanstalk относится к первой версии Amazon Linux.
Я нашел решение, которое работает достаточно хорошо, поэтому отправлю его здесь для потомков. Если кто-то может предложить лучший вариант, пожалуйста.
Elastic Beanstalk в Amazon Linux 2 использует rsyslog
для обработки и вывода логов. Есть файл на /opt/elasticbeanstalk/config/private/rsyslog.conf
что во время развертывания копируется в /etc/rsyslog.d/web.conf
и это тот, который направляет весь вывод из web
приложение к /var/log/web.stdout.log
.
В файле нет настраиваемого шаблона. Он полагается на rsyslog
шаблон по умолчанию с префиксом любого %msg%
с отметкой времени и $programname
(который web
в таком случае).
Я попытался заменить этот файл через .ebextensions
config, но это не сработало, потому что Elastic Beanstalk, похоже, перезаписывает этот файл после .ebextensions
запустить. Итак, я добавил дополнительный крюк платформы который удаляет файл, сохраняя добавленный мной пользовательский.
Вот .ebextensions/logs.config
файл:
files:
"/etc/rsyslog.d/web-files.conf":
mode: "000644"
owner: root
group: root
content: |
template(name="WebTemplate" type="string" string="%msg%\n")
if $programname == 'web' then {
*.=warning;*.=err;*.=crit;*.=alert;*.=emerg; /var/log/web.stderr.log;WebTemplate
*.=info;*.=notice /var/log/web.stdout.log;WebTemplate
}
commands:
remove-.bak-rsyslog:
command: rm -f *.bak
cwd: /etc/rsyslog.d
и .platform/hooks/predeploy/remove-default-rsyslog-conf.sh
(убедись, что ты chmod +x
вот этот):
#!/bin/sh
rm /etc/rsyslog.d/web.conf
systemctl restart rsyslog.service
Я собираюсь изложить здесь свое решение, хотя это немного другая проблема, чем op - это примерно та же идея и, надеюсь, ответит на некоторые другие вопросы комментаторов о nodejs.
Это для Amazon Linux 2 под управлением Node.js 12.x
ПроблемаЖурналы stdout: nodejs смешаны с журналами nginx в разделе "web" и плохо отформатированы.
Ранее в Amazon Linux 1 под управлением Nodejs эти журналы разделялись на /var/log/nodejs/nodejs.log
и /var/log/nginx/access.log
. Объединение их с префиксом IP-адреса просто превращает их в полный беспорядок.
Я следил за предложенными решениями и немного их модифицировал.
Я не уверен, хотят ли они, чтобы вы редактировали этот файл, как указал другой комментатор, поскольку i является частным. Если вам это не нравится, я бы порекомендовал писать в свои собственные файлы журнала, а не в стандартный вывод. Так у вас будет больше контроля.
files:
"/opt/elasticbeanstalk/config/private/rsyslog.conf" :
mode: "000755"
owner: root
group: root
content: |
template(name="WebTemplate" type="string" string="%msg%\n")
if $programname == 'web' and $msg startswith '#033[' then {
*.=warning;*.=err;*.=crit;*.=alert;*.=emerg; /var/log/web.stderr.log
*.=info;*.=notice /var/log/web.stderr.log;
} else if( $programname == 'web') then /var/log/node/nodejs.log;WebTemplate
files:
"/opt/elasticbeanstalk/config/private/logtasks/bundle/node.conf" :
mode: "000755"
owner: root
group: root
content: |
/var/log/node/nodejs.log
files:
"/opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.d/node.json" :
mode: "000755"
owner: root
group: root
content: |
{
"logs": {
"logs_collected": {
"files": {
"collect_list": [
{
"file_path": "/var/log/node/nodejs.log",
"log_group_name": "/aws/elasticbeanstalk/[environment_name]/var/log/node/nodejs.log",
"log_stream_name": "{instance_id}"
}
]
}
}
}
}
commands:
append_and_restart:
command: /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent-ctl -a append-config -m ec2 -c file:/opt/aws/amazon-cloudwatch-agent/etc/node.json -s