Effectively enhance constructor by incorporating decorators

Is it possible to properly extend a class constructor with decorators while maintaining the original class name and static attributes and methods?

Upon reading the handbook, there is a note that cautions about this scenario:

https://www.typescriptlang.org/docs/handbook/decorators.html#class-decorators

NOTE: If you choose to return a new constructor function, 
make sure to preserve the original prototype. 
The runtime logic for applying decorators does not handle this automatically.

One common issue when following the handbook's approach is losing the class name and static methods:

function my_decorator<T extends { new(...constr_args:any[]):any }>(constr_func:T){

    return class extends constr_func {
        constructor(...args: any[]){
            // DO STUFF
            super(...args);
            // DO STUFF
        }
    }

}

Answer №1

To transfer all the characteristics of the original class to the newly extended class, I must create an anonymous variable and assign the extended class to it.

After that, iterate through the descriptors of the original class and then return the variable.

function my_decorator<T extends {new (...constr_args:any[]):any}>(constr_func: T){

    const ExtClass = class extends constr_func {
        constructor(...args: any[]){
            // DO STUFF
            super(...args);
            // DO STUFF
        }
    }

    for(const property_name of Object.getOwnPropertyNames(constr_func)) {
        const descr = Object.getOwnPropertyDescriptor(constr_func, property_name)!;
        if(property_name != 'prototype')
            Object.defineProperty(ExtClass, property_name, descr);
    }

    return ExtClass;

}

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

react-i18next: issues with translating strings

I encountered a frustrating issue with the react-i18next library. Despite my efforts, I was unable to successfully translate the strings in my application. The relevant code looked like this: App.tsx: import i18n from 'i18next'; import { initR ...

AngularJS 2: Updating variable in parent component using Router

My current app.component looks like the following: import { Component, Input } from '@angular/core'; import {AuthTokenService} from './auth-token.service'; @Component({ selector: 'app-root', templateUrl: './app ...

Feeling lost with the concept of getcontext in js/ts and uncertain about how to navigate through it

Recently, I've been encountering undefined errors in my browser and can't seem to figure out how to resolve them. It seems that the usage of the keyword "this" in JavaScript and even TypeScript is causing quite a bit of confusion for me. Let&apo ...

Launching a Material UI Modal nested within a parent component

I have a table displaying various teams. Each row in the table has a menu option that, when clicked, should open either a modal or a dialog box. I want to keep the table, menu functionality, and modals as separate components for better organization. Here&a ...

Develop a fresh category inspired by the properties of objects

Let's tackle the challenge of constructing a new type in Typescript based on an descriptive object named schema, which contains all the requirements expressed within it. Here is my proposed solution: type ConfigParameter<IdType, ValueType> = Re ...

What is the recommended way to use the async pipe to consume a single Observable property in a view from an Angular2

Suppose I have a component with the following property: import { Component, OnInit } from 'angular2/core'; import { CarService } from 'someservice'; @Component({ selector: 'car-detail', templateUrl: './app/cars/ ...

Ways to specify a setter for a current object property in JavaScript

Looking to define a setter for an existing object property in JavaScript ES6? Currently, the value is directly assigned as true, but I'm interested in achieving the same using a setter. Here's a snippet of HTML: <form #Form="ngForm" novalida ...

Angular - Issue with Function Observable<number> in Development

Currently, I'm working on writing TypeScript code for a component. Within this TypeScript class, I have created a function that is meant to return a number representing the length of an array. My goal is to have this function work like an Observable. ...

Retrieving information from the Dog API using axios and storing the results in a fresh array

Currently, I am working on a NextJS app using Typescript. My issue lies in the functionality aspect of the application. I am utilizing the Dog API to retrieve all the breeds names and store them in a new array of arrays. Each sub-array contains the breed a ...

Incorporate an HTML span element with an onclick function bound in Angular framework

Is there a way to incorporate different icons by adding a span based on a flag, with an onclick event that triggers an internal function defined in the component ts? testfunc(){ console.log("it works") } flagToIcon(flag: boolean) { switch ( ...

There is an issue with the Next.js middleware: [Error: The edge runtime is not compatible with the Node.js 'crypto' module]

Struggling with a problem in next.js and typescript for the past 4 days. If anyone can provide some insight or help with a solution, it would be greatly appreciated. Thank you! -- This is my middleware.ts import jwt from "jsonwebtoken"; import { ...

What is the reason behind the warning about DOM element appearing when custom props are passed to a styled element in MUI?

Working on a project using mui v5 in React with Typescript. I am currently trying to style a div element but keep encountering this error message in the console: "Warning: React does not recognize the openFilterDrawer prop on a DOM element. If you in ...

What could be the reason for the crash caused by ngModel?

The usage of [(ngModel)] within a *ngFor-Loop is causing an endless loop and crashing the browser. This is how my HTML looks: <div class="container"> <div class="row" *ngFor="let item of controlSystemTargetViewModel.values; let index = i ...

Navigating the interface types between Angular, Firebase, and Typescript can be tricky, especially when working with the `firebase.firestore.FieldValue`

I am working on an interface that utilizes Firestore timestamps for date settings. export interface Album{ album_name: string, album_date: firebase.firestore.FieldValue; } Adding a new item functions perfectly: this.album ...

Checking the functionality of a feature with Jasmine framework in an Angular application

I am working on writing unit test cases and achieving code coverage for the code snippet below. Any advice on how to proceed? itemClick($event: any) { for (let obj of this.tocFiles) { let results = this.getchildren(obj, label); if (results) { conso ...

Discover the most effective method for identifying duplicate items within an array

I'm currently working with angular4 and facing a challenge of displaying a list containing only unique values. Whenever I access an API, it returns an array from which I have to filter out repeated data. The API will be accessed periodically, and the ...

Tips for Using Typescript Instance Fields to Prevent Undefined Values

After creating a few Typescript classes, I encountered an issue where I would get an undefined error when trying to use them after instantiating. I experimented with initializing my fields in the constructor, which resolved the problem, but I don't t ...

Combining portions of objects in Angular2

I want to combine two identical type observables in Angular2 and return an observable of the same type in a function. My goal is to: transform this setup: obs1.subscribe(obs => console.log(obs)) (where I receive): { count: 10, array: <some ...

Struggling with fetching the email value in .ts file from ngForm in Angular?

I'm trying to retrieve the form value in my .ts file, but I am only getting the password value and not the email. Here is the code snippet: <div class="wrapper"> <form autocomplete="off" class="form-signin" method="post" (ngSubmit)="lo ...

Sending real-time data from the tRPC stream API in OpenAI to the React client

I have been exploring ways to integrate the openai-node package into my Next.js application. Due to the lengthy generation times of OpenAI completions, I am interested in utilizing streaming, which is typically not supported within the package (refer to he ...