The Nest Scheduler - Cron decorator may encounter missing dependencies when used in conjunction with another decorator by applying multiple decorators

In my current project, I am developing a custom cron decorator that not only schedules tasks but also logs the name of the task when it is executed. To accomplish this, I have merged the default nestjs scheduling Cron decorator with a unique LogTask decorator in the code snippet below:

//cron-with-log.decorator.ts

const CronWithLog = (
  taskName: string,
  cronTime: string | Date,
  options?: CronOptions,
) => {
  return applyDecorators(LogTask(taskName), Cron(cronTime, options));
};

export default CronWithLog;



//log-task.decorator.ts

const LogTask = (taskName) => {
  return (target: any, propertyKey: string, descriptor: PropertyDescriptor) => {
    const targetFunc = descriptor.value;
    const logger = new Logger('Scheduler');
    descriptor.value = (...args: any[]) => {
      logger.log(`Executing Task: ${taskName}`);
      targetFunc.apply(this, args);
    };
    return descriptor;
  };
};

export default LogTask;

Now, let me show you how I implement this solution:


@Injectable()
export class Task {
  constructor(
    private readonly taskService: TaskService,
  ) {}

  @CronWithLog('Example Task', '* * * * * *')
  async run() {
    console.log(taskService.get(1))
  }
}

The logging functionality works perfectly as intended:

[Nest] 98   - 02/12/2021, 7:36:07 AM   [Scheduler] Executing Task: Example Task

However, I encountered an issue where the TaskService dependency is not being initialized, causing the task to fail. Upon further investigation, changing the order of decorators within the applyDecorators function from

applyDecorators(LogTask(taskName), Cron(cronTime, options))
to
applyDecorators(Cron(cronTime, options), LogTask(taskName))
resulted in both the logging and task execution failing altogether. Interestingly, running the job using the default Cron decorator works without any issues.

Is there something crucial that I am overlooking to ensure proper initialization of dependencies within my LogTask function?

Answer №1

The issue arose from the arrow function implementation in this snippet:

descriptor.value = (...args: any[]) => {
      logger.log(`Task Executed: ${taskName}`);
      targetFunc.apply(this, args);
    };

When using the arrow function, the reference of this pointed to the decorator itself instead of the class instance. Substituting it with function (...args: any[]) {...} will ensure that this refers to the class instance where the decorator is applied, providing access to all initialized dependencies.

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

Angular 2 integration for Oauth 2 popup authorization

I am in the process of updating an existing Angular application to utilize Angular 2. One challenge I am facing is opening an OAuth flow in a new pop-up window and then using window.postMessage to send a signal back to the Angular 2 app once the OAuth proc ...

Choose does not showcase the updated value

My form contains a form control for currency selection Each currency object has the properties {id: string; symbol: string}; Upon initialization, the currency select component loops through an array of currencies; After meeting a specific condition, I need ...

Running a Redux Thunk action from within a TypeScript environment, beyond the confines of a React component

Currently, I am in the process of converting a React Native app into TypeScript. Unfortunately, I have encountered an issue with dispatching thunk actions outside of the store. Below is how my store is configured: store/index.ts import { createStore, app ...

A Vue component library devoid of bundled dependencies or the need for compiling SCSS files

My current challenge involves the task of finding a way to publish our team's component library. These components are intended to be used by various internal applications within our organization. I have specific requirements: The library must be acc ...

What is the best way to retrieve the URL query parameters in a Node.js environment?

How can I retrieve URL query parameters in Node.js using TypeScript? Below is my attempted code: /** * My Server app */ import * as Http from "http"; import * as url from "url"; import { HttpServer } from "./HttpServer"; import { TaxCalculator } from ". ...

Having Trouble Showing Loading Component on Next.js v13

Having some issues with setting up a loading component in my Next.js v13 project. I followed the documentation by creating a file called loading.tsx in the src directory, but it's not appearing on the page as expected. I've also included a functi ...

Add an asterisk before each line of comment when working in a TypeScript file using the VS Code IDE

Within my VS Code workspace, I am using the Typescript language and would like to format my comments across multiple lines with a specific style (look out for the star character) /** *@desc any text * any text */ However, when I attempt to write a comm ...

Attempting to connect to "http://localhost:4242/webhook" was unsuccessful due to a connection refusal when trying to dial tcp 127.0.0.1:4242

In my next.js 13 project, I am integrating stripe with TypeScript and configuring the app router. To create a stripe event in my local machine, I ran stripe listen --forward-to localhost:4242/webhook, but now I am encountered with the error message stripe ...

TS1057: It is required that an async function or method has a return type that can be awaited

There was a recent Github issue reported on March 28th regarding async arrow functions generating faulty code when targeting ES5, resulting in the error message: TS1057: An async function or method must have a valid awaitable return type You can find t ...

Tips for disentangling code from types in Typescript

Instead of intertwining code and types like the example below: const compar8 : boolean | error = (action: string, n: number) => { switch(action) { case 'greater': return n > 8; case 'less': ...

Sharing information between different components in React can be done using props, context, or a

When attempting to edit by clicking, the parent information is taken instead of creating a new VI. I was able to achieve this with angular dialog but I am unsure how to do it with components. This is done using dialog: <div class="dropdown-menu-item" ...

Utilizing Class Types in Generics with TypeScript

Struggling to implement a factory method based on the example from the documentation on Using Class Types in Generics, but hitting roadblocks. Here's a simplified version of what I'm attempting: class Animal { legCount = 4; constructor( ...

In <R>, what does R represent when it is wrapped around an observer of type Observer<R>? Would it result in a Subscription, Function, or void?

The Angularfire2 project is in the process of adding a storage feature through a work-in-progress branch. This implementation includes two new files - an Observable class and a Factory function. Observable class export class FirebaseUploadTaskObservable& ...

Upon executing the `npm start` command, the application experiences a crash

When I tried following the steps of the Angular quickstart guide, I encountered some errors after running "npm start". Here are the errors displayed: node_modules/@angular/common/src/directives/ng_class.d.ts(46,34): error TS2304: Cannot find name 'Se ...

My PHP script scheduled to run through a cron job keeps getting stuck. I'm unsure what's causing the issue, so I would

Background Info: I had a seemingly straightforward task: sending an XML file containing stock and price data to an FTP location every hour. To accomplish this, I planned to use a PHP script with a cron job. The data was sourced from an existing Magento s ...

Discovering the generic type from an optional parameter within a constructor

Looking to implement an optional parameter within a constructor, where the type is automatically determined based on the property's type. However, when no argument is provided, TypeScript defaults to the type "unknown" rather than inferring it as "und ...

The import component path in Angular 4/TypeScript is not being recognized, even though it appears to be valid and functional

I'm currently working on building a router component using Angular and TypeScript. Check out my project structure below: https://i.stack.imgur.com/h2Y9k.png Let's delve into the landingPageComponent. From the image, you can see that the path ...

Improving the process of class initialization in Angular 4 using TypeScript

Is there a more efficient method to initialize an inner class within an outer class in Angular 4? Suppose we have an outer class named ProductsModel that includes ProductsListModel. We need to send the ProductId string array as part of a server-side reque ...

I'm looking to find the Angular version of "event.target.value" - can you help me out?

https://stackblitz.com/edit/angular-ivy-s2ujmr?file=src/app/pages/home/home.component.html I am currently working on getting the dropdown menu to function properly for filtering the flags displayed below it. My initial thought was to replicate the search ...

Getting the PlayerId after a user subscribes in OneSignal with Ionic2

Currently working on an app with Ionic2 and facing a challenge with retrieving the player id after a user subscribes in order to store it in my database. Any suggestions on how I can retrieve the unique player id of OneSignal users post-subscription? ...