tst-reflect icon indicating copy to clipboard operation
tst-reflect copied to clipboard

Runtime class generic parameters

Open Hookyns opened this issue 3 years ago • 7 comments

Support class generic parameters same ways the method generic parameters.

class Foo<TGenericClassType>
{
    doSomething() {
        getType<TGenericClassType>();
    }
}

Hookyns avatar Feb 14 '22 02:02 Hookyns

Hey, First of all, thanks for making this amazing package, really appreciate the effort.

Can you please guide me on how and where to add the support for generics, I am trying to build a utility function that can return default values for an interface, and this package is the only thing that can make it happen as far as I know.

interface ISampleInterface {
  name: string;
  age: number;
  alive: boolean;
  wishlist: string[];
  somethingOptional?: number;
  nestedObj: {
    hello: string;
    bye: number;
    hi: string[];
  };
}

// preferred way
const sampleObj: ISampleInterface = getDefaultValues<ISampleInterface>();

// available for now
const sample: ISampleInterface = getDefaultValues<ISampleInterface>(getType<ISampleInterface>());

//output
{
  name: '',
  age: 0,
  alive: false,
  wishlist: [],
  complexObj: { hello: '', bye: 0, helloBye: [] }
}

"getDefaultValues" just read the types with getType<T>() and construct the obj with default values

Thanks!

AbdulRafaySiddiqui avatar Apr 14 '22 16:04 AbdulRafaySiddiqui

Hi @AbdulRafaySiddiqui, TY.

Something like this? https://stackblitz.com/edit/tst-reflect-example-get-default-values?file=index.ts

Hookyns avatar Apr 14 '22 20:04 Hookyns

oh great, I was doing the same thing, but with arrow function and it was giving this error ReferenceError: __genericParams__ is not defined, strange :/ I thought it was some limitation of the package, but changed to normal function just like yours and now it works :)

Thanks, @Hookyns

AbdulRafaySiddiqui avatar Apr 14 '22 21:04 AbdulRafaySiddiqui

Implemented in the Next version.

Hookyns avatar Aug 28 '22 13:08 Hookyns

It works fine for getType<Foo<T>>(), but fails from inside class like in your first message:

class Foo<T>
{
    doSomething() {
        const type: Type = getType<T>()
        console.log(type)
    }
}
const temp = new Foo<string>()
temp.doSomething()

with ReferenceError: __genericParams__ is not defined

Igorjan94 avatar Aug 29 '22 17:08 Igorjan94

@Igorjan94 Yes, it is not implemented in the current version 0.x, but it is implemented in the new rewriten version of this package (I call it The Next version), which is not public yet. It'll be v1.0 version.

Example you posted will work, such as:

class Foo<T>
{
	constructor(bar: T, ...rest: any[]) {
		getType<T>();
	}

	doSomething<U>() {
		getType<T>();
		getType<U>();
	}
}

// new,
new Foo<string>("bar").doSomething();

// or Reflect.construct<T>(Function, args: any[], newTarget: Function),
Reflect.construct<Foo<string>>(Foo, ["some", "args"]).doSomething();

// or Reflect.constructGeneric(Function, typeArgs: Type[], args: any[], newTarget: Function),
Reflect.constructGeneric(Foo, [getType<string>()], ["some", "args"]).doSomething();

// or this too.
function baz<T>(Ctor: Function, ...args: any[]) {
	Reflect.constructGeneric(Ctor, [getType<T>()], args).doSomething();
}

baz<string>(Foo, "some", "args");

Hookyns avatar Aug 29 '22 18:08 Hookyns

Ah, sorry, I thought it's available now, haven't thought that it's private version. Can't wait to test it out!

Igorjan94 avatar Aug 29 '22 20:08 Igorjan94