0

Interfaces are used as blueprints for a contract. And yet in TypeScript you have this odd syntax (essentially having a new() inside an interface). Is this some sort of factory?

interface IControllerDetails {
     controller : { new(...args:string[]): void ;};
}

tx for reading.

3 Answers 3

3

It means that the controller property of objects that conform to the interface have a constructor and the constructor can take any number of string parameters.

So you can write code like the following:

let controllerDetails: IControllerDetails = ...;

let controller = new controllerDetails.controller("any", "amount", "of string args");

The weird part is that when creating new instances of the controller property it returns void. So in the code shown, controller is of type void. I'm not sure why someone would want to do that unless just calling new controllerDetails.controller() did all that was necessary, but even still that's strange.

An example of a value that conforms to the interface would be something like this:

class Controller {
    constructor(...args: string[]) {
    }
}

let controllerDetails: IControllerDetails = {
    // you could inline a class here if you wanted by using a class expression
    controller: Controller
};

Edit: By "inline", I just meant you could write this if you wanted, which isn't commonly done:

let controllerDetails: IControllerDetails = {
    controller: class Controller {
        constructor(...args: string[]) {
        }
    }
};
Sign up to request clarification or add additional context in comments.

4 Comments

Thank you, what drove it home for me was the statement that "It means that the controller property of objects that conform to the interface have a constructor and the constructor can take any number of string parameters." TX again...
Can you please also show what you mean by "you could inline a class here if you wanted by using a class expression"
let controllerDetails: ISample = { controller: function(){ return class MyClass { constructor(...args:string[]) { } } }() };
@user2040670 no, that would be a function that returns a class controller: () => { new(...args: string[]): void; }. I updated the answer with an example. Saying that about using a class expression was just a sidenote... it's not common syntax.
3

To break this down:

interface IControllerDetails {
     controller : { new(...args:string[]): void ;};
}

Let's start here

interface IControllerDetails {

This declares a type called IControllerDetails

     controller : { new(...args:string[]): void ;};
     ~~~~~~~~~~

It has a property called controller

     controller : { new(...args:string[]): void ;};
                  ~                              ~

The type of the controller property is an object type with some members. There could have been more properties declared between the {}s, but there's only one here

     controller : { new(...args:string[]): void ;};
                    ~~~

The only member of the controller property is a construct signature. This means you can invoke the new operator on the controller property.

     controller : { new(...args:string[]): void ;};
                        ~~~           ~~

This constructor takes between zero and infinity arguments.

     controller : { new(...args:string[]): void ;};
                           ~~~~

The name of the parameter list is args, though this doesn't affect anything.

     controller : { new(...args:string[]): void ;};
                                ~~~~~~

All of the arguments have to be of type string

     controller : { new(...args:string[]): void ;};
                                           ~~~~

The constructor doesn't have to return anything. In practice, what they're saying here is that you can return an object of any kind (because it's safe to assign a function returning more to a function returning less).

1 Comment

Thank you, what drove it home for me was the statement that "It means that the controller property of objects that conform to the interface have a constructor and the constructor can take any number of string parameters." TX again...
0

basically, that syntax of someMember : { new(...args:string[]): IAnotherSample ;}; means the Class must have the same constructor signature that matches the interface contract. For anyone that needs the complete source here you go:

```

interface ISample {
    // someMember requires a class with a constructor that has matching signature and return type
    someMember : { new(...args:string[]): IAnotherSample ;};
}
interface IAnotherSample {
    someNum: number;
}
class MyClass implements IAnotherSample{
    public someNum:number;
    constructor(...args:string[]) {
    }
}

let sample: ISample = {
    someMember: MyClass
};

let sampleInstance = new sample.someMember('123');

```

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.