Skip to content

Custom MoleculerJS logger for send log to ClickHouse

License

Notifications You must be signed in to change notification settings

1xtr/moleculer-ch-logger

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

44 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Moleculer logo

NPM version NPM Downloads

Moleculer logger for ClickHouse

This is a fork from native Datadog logger

Description

Easy to save logs to ClickHouse with moleculer

Install

$ npm install @1xtr/moleculer-ch-logger --save

Usage

const ClickHouseLogger = require('@1xtr/moleculer-ch-logger')

module.exports = {
    logger: new ClickHouseLogger({
      // put here your options
    })
}

Default options

const defaultOptions = {
  url: 'http://localhost',
  port: 8123,
  dbName: 'default',
  dbUser: 'default',
  dbPassword: '',
  dbTableName: 'logs',
  // use source like TAG
  source: process.env.MOL_NODE_NAME || 'moleculer',
  hostname: hostname(),
  objectPrinter: null,
  interval: 10 * 1000,
  timeZone: 'Europe/Istanbul',
  tableTTL: 'date + INTERVAL 1 DAY RECOMPRESS CODEC(ZSTD(3))',
  useBuffer: false,
}

Log table

const body = `CREATE TABLE IF NOT EXISTS ${this.opts.dbTableName} (
          timestamp DateTime64(3, '${this.opts.timeZone}') DEFAULT now(),
          requestID String,
          subdomain String,
          caller String,
          level String,
          message String,
          nodeID String,
          namespace String,
          service String,
          version String,
          source String,
          hostname String,
          date Date DEFAULT today())
      ENGINE = MergeTree()
      ORDER BY (toStartOfHour(timestamp), service, level, subdomain, requestID, timestamp)
      PRIMARY KEY (toStartOfHour(timestamp), service, level, subdomain, requestID)
      PARTITION BY (date, toStartOfDay(timestamp))
      TTL ${this.opts.tableTTL}
      SETTINGS index_granularity = 8192;`

Buffer

const body = `CREATE TABLE IF NOT EXISTS ${this.opts.dbTableName}_buffer
      as ${this.opts.dbTableName}
      ENGINE = Buffer('${this.opts.dbName}', '${this.opts.dbTableName}', 16, 10, 100, 1000, 10000, 10000, 100000);`

Logger mixin

That mixin I use for logging (Click for open)
const defaultContext = {
  requestID: '',
  meta: { customer: { subdomain: '' } },
}

module.exports = {
  name: 'logger',
  methods: {
    log(data, ctx = defaultContext) {
      this.sendLog(data, ctx, 'info')
    },
    error(title, error, ctx = defaultContext) {
      this.logger.error({
        title,
        subdomain: ctx.meta.customer ? ctx.meta.customer.subdomain : '',
        caller: ctx.caller || '',
        error,
        requestID: ctx.requestID || '',
      })
    },
    err(error, ctx = defaultContext) {
      this.logger.error({
        title: error.message,
        subdomain: ctx.meta.customer ? ctx.meta.customer.subdomain : '',
        caller: ctx.caller || '',
        error,
        requestID: ctx.requestID || '',
      })
    },
    warn(data, ctx = defaultContext) {
      this.sendLog(data, ctx, 'warn')
    },
    sendLog(data, ctx, logType) {
      if (!ctx.meta.customer) {
        ctx.meta.customer = { subdomain: '' }
      }

      if (typeof data === 'string') {
        return this.logger[logType]({
          requestID: ctx.requestID || '',
          subdomain: ctx.meta.customer.subdomain || '',
          caller: ctx.caller || '',
          title: data,
        })
      }

      if (typeof data !== 'object') {
        return this.logger[logType]({
          requestID: ctx.requestID || '',
          subdomain: ctx.meta.customer.subdomain || '',
          caller: ctx.caller || '',
          data,
        })
      }

      return this.logger[logType]({
        requestID: ctx.requestID || '',
        subdomain: ctx.meta.customer.subdomain || '',
        caller: ctx.caller || '',
        ...data,
      })
    },
  },
}

Documentation

For more details read docs

About

Custom MoleculerJS logger for send log to ClickHouse

Resources

License

Stars

Watchers

Forks

Packages

No packages published