tcp.js 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. const debug = require('debug')('log4js:tcp');
  2. const net = require('net');
  3. function appender(config, layout) {
  4. let canWrite = false;
  5. const buffer = [];
  6. let socket;
  7. let shutdownAttempts = 3;
  8. let endMsg = '__LOG4JS__';
  9. function write(loggingEvent) {
  10. debug('Writing log event to socket');
  11. canWrite = socket.write(`${layout(loggingEvent)}${endMsg}`, 'utf8');
  12. }
  13. function emptyBuffer() {
  14. let evt;
  15. debug('emptying buffer');
  16. while ((evt = buffer.shift())) {
  17. write(evt);
  18. }
  19. }
  20. function createSocket() {
  21. debug(`appender creating socket to ${config.host || 'localhost'}:${config.port || 5000}`);
  22. endMsg = `${config.endMsg || '__LOG4JS__'}`;
  23. socket = net.createConnection(config.port || 5000, config.host || 'localhost');
  24. socket.on('connect', () => {
  25. debug('socket connected');
  26. emptyBuffer();
  27. canWrite = true;
  28. });
  29. socket.on('drain', () => {
  30. debug('drain event received, emptying buffer');
  31. canWrite = true;
  32. emptyBuffer();
  33. });
  34. socket.on('timeout', socket.end.bind(socket));
  35. socket.on('error', (e) => {
  36. debug('connection error', e);
  37. canWrite = false;
  38. emptyBuffer();
  39. });
  40. socket.on('close', createSocket);
  41. }
  42. createSocket();
  43. function log(loggingEvent) {
  44. if (canWrite) {
  45. write(loggingEvent);
  46. } else {
  47. debug('buffering log event because it cannot write at the moment');
  48. buffer.push(loggingEvent);
  49. }
  50. }
  51. log.shutdown = function (cb) {
  52. debug('shutdown called');
  53. if (buffer.length && shutdownAttempts) {
  54. debug('buffer has items, waiting 100ms to empty');
  55. shutdownAttempts -= 1;
  56. setTimeout(() => {
  57. log.shutdown(cb);
  58. }, 100);
  59. } else {
  60. socket.removeAllListeners('close');
  61. socket.end(cb);
  62. }
  63. };
  64. return log;
  65. }
  66. function configure(config, layouts) {
  67. debug(`configure with config = ${config}`);
  68. let layout = function (loggingEvent) {
  69. return loggingEvent.serialise();
  70. };
  71. if (config.layout) {
  72. layout = layouts.layout(config.layout.type, config.layout);
  73. }
  74. return appender(config, layout);
  75. }
  76. module.exports.configure = configure;