Error detected due to Typescript linting when using Morgan and logger.stream together in the

When attempting to attach Morgan log to Winston using a logger Stream feature, an error arises. The error message states:

Argument of type '"combined"' is not assignable to parameter of type 'FormatFn'.

Below is the initialization code for Winston:

import * as appRoot from 'app-root-path';
import * as winston from 'winston';
import { Logger } from 'winston';
import * as fs from 'fs';
import * as stream from 'stream';

const dirLogs = `${appRoot}/logs`;

// Call during initialization, thread can be blocked
if (!fs.existsSync(dirLogs)) {
  fs.mkdirSync(dirLogs);
}
// Custom settings for each transport (file, console)
const options = {
  file: {
    level: 'info',
    filename: `${dirLogs}/app.log`,
    handleExceptions: true,
    json: true,
    maxsize: 5242880, // 5MB
    maxFiles: 5,
    colorize: false,
  },
  console: {
    level: 'debug',
    handleExceptions: true,
    json: false,
    colorize: true,
  },
};

// Focus on core requirement
// Logger should send logs to a logger service
const logger = new Logger({
  level: 'info',
  transports: [
    new winston.transports.File(options.file),
    new winston.transports.Console(options.console),
  ],
  exitOnError: false, // do not exit on handled exceptions
});

// To avoid lint errors, utilizes stream.Duplex
logger.stream = (options?: any) => new stream.Duplex({
  write: function (message: string, encoding: any) {
      logger.info(message.trim());
  }
});

export default logger;

The code snippet where Morgan is used:

// ... All imports
import logger from './logger/index';

// ... Later in the code
this.expressApp.use(morgan('combined', { stream: logger.stream }));

The cause of this error remains unclear :/

Answer №1

After delving deep into the code and TypeScript files, I gained a better understanding of what needed to be done.

I made changes to my logger.stream declaration as follows:

// To avoid another lint error, I switched to using stream.Duplex
logger.stream = (options?: any) => new stream.Duplex({
  write: function (message: string, encoding: any) {
      logger.info(message.trim());
  }
});

Instead, I updated it to:

// Ensure you import this
import { Options } from 'morgan';

// The revised code snippet
export const morganOption: Options = {
  stream: {
    write: function (message: string) {
        logger.info(message.trim());
    },
  },
};

Then I imported the morganOptions and set it to morgan:

// My imports
import { logger, morganOption } from './logger/index';

// ... Later in the code
this.expressApp.use(morgan('combined', morganOption));

Hopefully, this explanation proves helpful to others :)

Answer №2

Set up the Winston node package using node package manager

To start logging, create a logger.ts file and add the code snippet below:

import { createLogger, format, transports } from 'winston';
const { label, combine, timestamp , prettyPrint } = format;
const logger = createLogger({
 format: combine(
 timestamp(),
 prettyPrint(),
 ),
 transports: [
 new transports.Console(),
 new transports.File({ filename: './error.log' , level: 'error' }),
 new transports.File({ filename: './info.log' , level: 'info' }),
 ],
 exitOnError: false,
});
export default loggerStep 

For more information, check out the link provided here

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

How do I implement branch code using TypeScript types in Svelte?

Looking for a solution similar to the one mentioned in Typescript: How to branch based on type, but tailored for Svelte. Despite implementing run-time type guards as suggested, Svelte continues to throw errors. I am dealing with an array called collectabl ...

Tips for sorting through and minimizing data based on the most recent date

info = { start: 1, data: [ { name: 'Maria', date: '2020-02-15 }, { name: 'Paula', date: '2020-06-10 }, { name: 'Eva', date: '2020-12-05 }, { name: 'Sophia', date ...

Utilizing JSON data from Jade in local JavaScript: A comprehensive guide

Attempting to utilize a JSON object (the entire object, not just a portion) from Node via Jade in my local myScript.js. Here is what my Jade file looks like: span(class="glyphicon glyphicon-pencil" onclick="confirm(\"#{myJSON.taskid}\", \" ...

The Express.io platform is having trouble loading the JavaScript file

Currently, I have an operational Express.io server up and running. However, I am encountering issues with the proper loading of my Javascript files. Here is a snippet from my Jade file: html head h1 Test index body script(src="/so ...

The material UI style is not being implemented properly in the final production or build

While applying styles to the ListItemButton component from MUI by targeting the specific class .css-10hburv-MuiTypography-root, it works fine in development but not in production. I have tried various methods, including directly applying the styles on th ...

Steps for creating a click event for text within an Ag-Grid cell

Is there a way to open a component when the user clicks on the text of a specific cell, like the Name column in this case? I've tried various Ag-Grid methods but couldn't find any that allow for a cell text click event. I know there is a method f ...

Angular's array filter functionality allows you to narrow down an

I am working with an Array and aiming to filter it based on multiple criteria: primasSalud = [ { nombre: 'one', internacional: true, nacional: false, nacionalSinReembolso: false, nacionalClinicasAcotadas: false ...

The resolution of Angular 8 resolver remains unresolved

I tried using console.log in both the constructor and ngOnInit() of Resolver but for some reason, they are not being logged. resolve:{serverResolver:ServerResolverDynamicDataService}}, console.log("ServerResolverDynamicDataService constructor"); console ...

Tips for finding the displayRows paragraph within the MUI table pagination, nestled between the preceding and succeeding page buttons

Incorporating a Material-UI table pagination component into my React application, I am striving to position the text that indicates the current range of rows between the two action buttons (previous and next). <TablePagination ...

Find the variance between today's date and a selected date, then initiate the timer based on this variance

I have a grid containing data. I utilize the loadGrid() function to preload data or conditions before the grid finishes loading. When the active state is set to 1, my intention is to initiate a timer by calculating the difference between the current date ...

What methods are available to pass a variable value between two components in Angular 2?

I've been experimenting with Angular2 and recently created a component called appmenu using angular cli. The code in appmenu.html looks like this: <ul> <li (click)="menuitem1()">Menu Item 1</li> <li>Menu Item 2</li> ...

Improving the Performance of MongoDB Queries in Node.js

I am currently working on optimizing a MongoDB query in my Node.js application to improve performance. Here is the query I am trying to enhance: var ReceiveEmailHistoryData1 = await ReceiveEmailHistory.find({ IsDeleted: false, ClientID: ClientID, ...

What is the best way to switch to a different screen in a React Native application?

I've recently dived into the world of React Native and embarked on a new project. The initial screen that greets users upon launching the app is the "welcome screen," complete with a prominent 'continue' button. Ideally, clicking this button ...

Whenever I attempt to bring in AngularFireModule, an error promptly appears

I am experiencing some errors when trying to import AngularFireModule and initialize the app with environment.firebaseConfig. I have tried to solve the problem but without success. Can anyone provide guidance on what steps I should take? @NgModule({ decl ...

Encountering a hiccup as I attempt to set up a new user through Express NodeJs with Passport integration

I'm encountering an issue while attempting to set up a registration page for users. After trying to make a POST request to save the user in the database, I am getting an error that states TypeError: req.checkBody is not a function. I have also used np ...

ERROR: The variable countryCallingCode has not been defined

I encountered an error when attempting to assign a value to my property countryCallingCode, which does not exist in the first option. this.allData.customerFacingPhone.countryCallingCode = newItem.countryCallingCode The error message I received was: ERROR ...

Implement the TypeScript handleChange function for input fields and dropdown menus

Currently, I am in the process of developing a form using TypeScript and Material-UI components. My objective is to create a change handler function that can be utilized for both select and textfield changes. Below are my state and functions: const [re ...

What are the reasons for deprecating bindToController in Typescript?

When I am creating an AngularJS directive using TypeScript, I typically use the bindToController property to bind parameters to the controller for easy access. export class MyDirective implements IDirective { controller = MyController; controllerA ...

Combining Rollup, Typescript, and converting images to base64 during the loading process

Having trouble preloading an image with Rollup. None of the solutions that should work seem to be effective, and I can't figure out why. Has anyone successfully managed to make this work? Here is my configuration in rollup.config.js: import image fr ...

"Sometimes the findByIdAndUpdate function may be successful, while other times it may

Having trouble updating two documents in mongoose? Getting a mysterious error message: UnhandledPromiseRejectionWarning: TypeError: Cannot read property '_id' of undefined? It's frustrating when it sometimes works and sometimes doesn't. ...