简体   繁体   English

如何将JS错误从客户端记录到kibana?

[英]How to to log JS errors from a client into kibana?

I have web application backed end in NodeJS and logstash/elasticsearch/kibana to handle system logs like (access_error.log, messages.log etc) . 我在logstash/elasticsearch/kibanalogstash/elasticsearch/kibana有Web应用程序支持结束处理系统日志,如(access_error.log, messages.log etc)

Right now I need to record all JavaScript client side errors into kibana also. 现在我需要将所有JavaScript客户端错误记录到kibana中。 What is the best way to do this? 做这个的最好方式是什么?

EDIT: I have to add additional information to this question. 编辑:我必须在此问题中添加其他信息。 As @Jackie Xu provide partial solution to my problem and as follows from my comment: 由于@Jackie Xu为我的问题提供了部分解决方案,我的评论如下:

I'm most interested in realizing server-side error handling. 我最感兴趣的是实现服务器端错误处理。 I think it's not effective write each error into file. 我认为将每个错误写入文件是没有效果的。 I'm looking for best practices how to make it more performance. 我正在寻找如何使其更具性能的最佳实践。

I need to handle js error records on server-side more effective than just write into file. 我需要处理服务器端的js错误记录比写入文件更有效。 May you provide some scenarios how could I increase server-side logging performance? 您是否可以提供一些方案如何提高服务器端日志记录性能?

When you say client, I'm assuming here that you mean a logging client and not a web client . 当你说客户端时,我假设你指的是日志记录客户端而不是Web客户端

First, make it a habit to log your errors in a common format. 首先,养成以常见格式记录错误的习惯。 Logstash likes consistency, so if you're putting text and JSON in the same output log, you will run into issues. Logstash喜欢一致性,因此如果您将文本和JSON放在同一输出日志中,您将遇到问题。 Hint: log in JSON. 提示:登录JSON。 It's awesome and incredibly flexible. 它非常棒且非常灵活。

The overall process will go like this: 整个过程将如下所示:

  1. Error occurs in your app 您的应用中出现错误
  2. Log the error to file, socket, or over a network 将错误记录到文件,套接字或网络上
  3. Tell logstash how to get (input) that error (ie from file, listen over network, etc) 告诉logstash如何获取(输入)该错误(即从文件,通过网络监听等)
  4. Tell logstash to send (output) the error to Elasticsearch (which can be running on the same machine) 告诉logstash将错误发送(输出)到Elasticsearch(可以在同一台机器上运行)

In your app, try using the bunyan logger for node. 在您的应用中,尝试使用bunyan logger for node。 https://github.com/trentm/node-bunyan https://github.com/trentm/node-bunyan

node app index.js node app index.js

var bunyan = require('bunyan');
var log = bunyan.createLogger({
  name: 'myapp',
  streams: [{
    level: 'info',
    stream: process.stdout // log INFO and above to stdout
  }, {
    level: 'error',
    path: '/var/log/myapp-error.log' // log ERROR and above to a file
  }]
});

// Log stuff like this
log.info({status: 'started'}, 'foo bar message');

// Also, in express you can catch all errors like this
app.use(function(err, req, res, next) {
   log.error(err);
   res.send(500, 'An error occurred');
});

Then you need to configure logstash to read those JSON log files and send to Elasticsearch/Kibana. 然后,您需要配置logstash以读取这些JSON日志文件并发送到Elasticsearch / Kibana。 Make a file called myapp.conf and try the following: 创建一个名为myapp.conf的文件并尝试以下操作:

logstash config myapp.conf logstash config myapp.conf

# Input can read from many places, but here we're just reading the app error log
input {
    file {
        type => "my-app"
        path => [ "/var/log/myapp/*.log" ]
        codec => "json"
    }   
}

# Output can go many places, here we send to elasticsearch (pick one below)
output {

  elasticsearch {
    # Do this if elasticsearch is running somewhere else
    host => "your.elasticsearch.hostname"
    # Do this if elasticsearch is running on the same machine
    host => "localhost"
    # Do this if you want to run an embedded elastic search in logstash
    embedded => true   
  }

}

Then start/restart logstash as such: bin/logstash agent -f myapp.conf web 然后启动/重启logstash: bin/logstash agent -f myapp.conf web

Go to elasticsearch on http://your-elasticsearch-host:9292 to see the logs coming in. 转到http://your-elasticsearch-host:9292以查看进入的日志。

If I understand correctly, the problem you have is not about sending your logs back to the server (or if it was @Jackie-xu provided some hints), but rather about how to send them to elastiscsearch the most efficiently. 如果我理解正确,你遇到的问题不是将日志发送回服务器(或者@ Jackie-xu是否提供了一些提示),而是关于如何最有效地将它们发送到elastiscsearch。

Actually the vast majority of users of the classic stack Logstash/Elasticsearch/Kibana are used to having an application that logs into a file, then use Logstash's plugin for reading files to parse that file and send the result to ElasticSearch. 实际上,经典堆栈Logstash/Elasticsearch/Kibana的绝大多数用户习惯于将应用程序登录到文件中,然后使用Logstash的插件读取文件来解析该文件并将结果发送到ElasticSearch。 Since @methai gave a good explanation about it I won't go any further this way. 由于@methai给出了一个很好的解释,我不会再这样了。

But what I would like to bring on is that: 但我想带来的是:

You are not forced to used Logstash. 您不必被迫使用Logstash。
Actually Logstash's main role is to collect the logs, parse them to identify their structure and recurrent field, and finally output them in a JSON format so that they can be sent to ElasticSearch. 实际上,Logstash的主要作用是收集日志,解析它们以识别它们的结构和循环字段,最后以JSON格式输出它们,以便将它们发送到ElasticSearch。 But since you are already manipulating javascript on the client side, one can easily imagine that you would talk directly to the Elasticsearch server. 但由于您已经在客户端操作javascript,因此很容易想象您将直接与Elasticsearch服务器通信。 For example once you have caught a javascript exception, you could do the folowing: 例如,一旦你发现了一个javascript异常,你可以执行以下操作:

var xhr = new XMLHttpRequest();
xhr.open("PUT", http://your-elasticsearch-host:9292, true);
var data = {
    lineNumber: lineNumber,
    message: message,
    url: url
}
xhr.send(JSON.stringify(data));

By doing this, you are directly talking from the client to the ElasticSearch Server. 通过这样做,您直接从客户端与ElasticSearch Server进行通信。 I can't imagine a simpler and faster way to do that (But note that this is just theory, I never tried myself, so reality could be more complex, especially if you want special fields like date timestamps to be generated ;)). 我无法想象一种更简单,更快速的方法(但请注意,这只是理论,我从未尝试过,所以现实可能更复杂,特别是如果你想要生成日期时间戳这样的特殊字段;))。 In a production context you will probably have security issues, probably a proxy server between the client and the ES server, but the principle is there. 在生产环境中,您可能会遇到安全问题,可能是客户端和ES服务器之间的代理服务器,但原则就在那里。

If you absolutely want to use Logstash you are not forced to use a file input 如果您绝对想要使用Logstash,则不必强制使用文件输入
If, for the purpose of harmonizing, doing the same as everyone, or for using advanced logstash parsing confifuration you want to stick to Logstash, you should take a look at all the alternative inputs to the basic file input. 如果为了协调,对每个人做同样的事情,或者为了使用高级logstash解析配置,你想坚持使用Logstash,你应该看看基本文件输入的所有替代输入。 For example I used to use a pipe myself, with a process in charge of collecting the logs and outputting these to the standard output. 例如,我过去常常使用管道,负责收集日志并将其输出到标准输出。 There is also the possibilty to read on an open tcp socket, and a lot more, you can even add your own. 在开放的tcp套接字上阅读也是可能的,还有更多,你甚至可以添加自己的。

You would have to catch all client side errors first (and send these to your server): 您必须首先捕获所有客户端错误(并将这些错误发送到您的服务器):

window.onerror = function (message, url, lineNumber) {

    // Send error to server for storage
    yourAjaxImplementation('http://domain.com/error-logger/', {
        lineNumber: lineNumber,
        message: message,
        url: url
    })

    // Allow default error handling, set to true to disable
    return false

}

Afterwards you can use NodeJS to write these error messages to a log. 之后,您可以使用NodeJS将这些错误消息写入日志。 Logstash can collect these, and then you can use Kibana to visualise. Logstash可以收集这些,然后您可以使用Kibana进行可视化。

Note that according to Mozilla window.onerror doesn't appear to work for every error. 请注意, 根据Mozilla window.onerror似乎不适用于每个错误。 You might want to switch to something like Sentry (if you don't want to pay, you can directly get the source from GitHub ). 你可能想切换到像Sentry这样的东西(如果你不想付钱,你可以直接从GitHub获取源代码)。

Logging errors trough the default built-in file logging allows your errors to be preserved and it also allows your kernel to optimize the writes for you. 通过默认的内置文件日志记录记录错误可以保留您的错误,并且还允许您的内核为您优化写入。

If you really think that it is not fast enough (you get that many errors?) you could just put them into redis. 如果你真的认为它不够快(你得到那么多错误?)你可以把它们放到redis中。

Logstash has a redis pub/sub input so you can store the errors in redis and logstash will pull them out and store them in your case in elasticsearch. Logstash有一个redis pub / sub输入,因此您可以将错误存储在redis中,logstash会将它们拉出来并将它们存储在elasticsearch中。

I'm presuming logstash/es are on another server, otherwise there really is no point doing this, es has to store the data on disc also, and it is not nearly as efficient as writing a logfile. 我假设logstash / es在另一台服务器上,否则实际上没有必要这样做,es也必须将数据存储在光盘上,并且它的效率不如编写日志文件。

With whatever solution you go with, youll want to store the data, eg. 无论您使用何种解决方案,您都希望存储数据,例如。 writing it to disc. 把它写到光盘上。 Append-only to a single (log) file is highly efficient, and when preserving data the only way you can handle more is to shard it across multiple discs/nodes. 仅附加到单个(日志)文件是非常有效的,并且在保留数据时,您可以处理更多的唯一方法是在多个光盘/节点上对其进行分片。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 GraphQL 如何在 node.js 中将服务器错误与客户端错误(最好使用 TryCatch 块)分开? - GraphQL How to seperate Server errors from Client errors (ideally using TryCatch blocks) in node.js? 控制台不记录内容脚本中的 js 错误 - Console doesn't log js errors from content script 如何在Heroku上记录错误 - How to log errors on Heroku 如何从Amazon AWS JavaScript SDK捕获/记录所有错误? - How to capture/log all errors from Amazon AWS JavaScript SDK? 如何记录客户端Angular应用程序中发生的所有可能的控制台错误? - How to log all possible console errors occurring in Angular application on a client's side? 如何从Electron的控制台中自动记录警告和错误? - How can I automatically log warnings and errors from the console in Electron? Node.js:log忽略错误 - Node.js: log ignored errors 如何将错误记录到 Firebase Cloud Functions 日志? - How to log errors to Firebase Cloud Functions Log? 如何从 DynamoDB for Elasticsearch/Kibana 格式化时间戳? - How to format a timestamp from DynamoDB for Elasticsearch/Kibana? 如何使用JavaScriptCore将错误记录到XCode? - How to log errors to XCode with JavaScriptCore?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM