我只是想在typescript接口中声明一个静态属性?我没有找到任何关于这方面的资料。

interface myInterface {
  static Name:string;
}

这可能吗?


当前回答

如果您正在寻找定义一个静态类(即。所有的方法/属性都是静态的),你可以这样做:

interface MyStaticClassInterface {
  foo():string;
}

var myStaticClass:MyStaticClassInterface = {
  foo() {
    return 'bar';
  }
};

在这种情况下,静态“类”实际上只是一个普通的-ol'-js-object,它实现了MyStaticClassInterface的所有方法

其他回答

在TypeScript中,你不能在接口上定义静态属性。

假设您想要更改Date对象,而不是尝试添加到Date的定义中,您可以包装它,或者简单地创建富Date类来完成Date没有完成的工作。

class RichDate {
    public static MinValue = new Date();
}

因为Date是TypeScript中的一个接口,你不能使用extends关键字将它扩展为一个类,这有点遗憾,因为如果Date是一个类,这将是一个很好的解决方案。

如果你想扩展Date对象以在原型上提供MinValue属性,你可以:

interface Date {
    MinValue: Date;
}

Date.prototype.MinValue = new Date(0);

使用:

var x = new Date();
console.log(x.MinValue);

如果你想让它在没有实例的情况下可用,你也可以…但这有点繁琐。

interface DateStatic extends Date {
    MinValue: Date;
}

Date['MinValue'] = new Date(0);

使用:

var x: DateStatic = <any>Date; // We aren't using an instance
console.log(x.MinValue);

其他解决方案似乎偏离了正确的路径,我发现我的场景在Typescript文档中有覆盖,我在下面解释:

interface AppPackageCheck<T> {
  new (packageExists: boolean): T
  checkIfPackageExists(): boolean;
}

class WebApp {
    public static checkIfPackageExists(): boolean {
        return false;
    }

    constructor(public packageExists: boolean) {}
}

class BackendApp {
    constructor(public packageExists: boolean) {}
}

function createApp<T>(type: AppPackageCheck<T>): T {
    const packageExists = type.checkIfPackageExists();
    return new type(packageExists)
}

let web = createApp(WebApp);

// compiler failure here, missing checkIfPackageExists
let backend = createApp(BackendApp); 

我的解决方案对于添加额外静态构造函数的用例非常有效。我已经测试过了,它通过了所有的测试。如果有人发现有问题,请告诉我。

我做了一个泛型类型,它接受接口和静态接口。

它适用于具体类和抽象类。

我使用条件类型来设计它,这样所有的错误都可以传播 到实现接口的类,而不是接口本身。

注意:错误传播允许vscode快速修复(实现所有方法)。唯一的缺点是你必须自己应用static关键字,因为没有快速修复这个错误的方法。

的接口:

type Class<T = any> = new (...args: any[]) => T;
type AbstractClass<T = any> = abstract new (...args: any[]) => T;

type Interface<C extends Class<InstanceType<C>> | AbstractClass<InstanceType<C>>, SI, I = {}> = 
    C extends Class<InstanceType<C>> 
    // ConcreteClass
    ? InstanceType<C> extends I 
        ? C extends (SI & Class<InstanceType<C>>)
            ? (InstanceType<C> & I)
            : (SI & Class<InstanceType<C>>) // Indicate StaticInterface Error
        : I // Indicate Interface Error
    // AbstractClass
    : InstanceType<C> extends I 
        ? C extends (SI & AbstractClass<InstanceType<C>>)
            ? (InstanceType<C> & I)
            : (SI & AbstractClass<InstanceType<C>>) // Indicate StaticInterface Error
        : I // Indicate Interface Error

用法:

interface MyInterface {
    instanceMethod(): number;
}

interface MyStaticInterface {
    staticMethod(): number;
}
 
class MyClass implements Interface<typeof MyClass, MyStaticInterface, MyInterface> {
    static staticMethod(): number {
        return 50;
    }

    instanceMethod(): number {
        return 100;
    }

    static otherStatic() {
        return "HELLO"
    }

    otherInstance() {
        return "GOODBYE"
    }
}

abstract class MyClass1 implements Interface<typeof MyClass1, MyStaticInterface, MyInterface> {
    static staticMethod(): number {
        return 50;
    }


    instanceMethod(): number {
        return 20;
    }

    static otherStatic() {
        return "HELLO"
    }

    otherInstance() {
        return "GOODBYE"
    }

    abstract abstractMethod() : number;

}

这里有一个相当简单的方法:

interface MyClass {
    new (): MyClassInstance;
    staticMethod(): string;
}

interface MyClassInstance {
    instanceMethod(): string;
}

const Class: MyClass = class {
    static staticMethod() {
        return "This is a static method";
    }
    instanceMethod() {
        return "This is an instance method";
    }
}

Class.staticMethod();

// Has type MyClassInstance
const instance = new Class();
instance.instanceMethod();

请注意,这并不允许您像通常那样让类扩展接口,但对于许多情况来说,这已经足够好了。

你可以正常定义接口:

interface MyInterface {
    Name:string;
}

但你不能这么做

class MyClass implements MyInterface {
    static Name:string; // typescript won't care about this field
    Name:string;         // and demand this one instead
}

为了表示一个类应该遵循这个接口来获取它的静态属性,你需要一点技巧:

var MyClass: MyInterface;
MyClass = class {
    static Name:string; // if the class doesn't have that field it won't compile
}

你甚至可以保留类名,TypeScript(2.0)不会介意:

var MyClass: MyInterface;
MyClass = class MyClass {
    static Name:string; // if the class doesn't have that field it won't compile
}

如果你想静态地继承许多接口,你必须首先将它们合并到一个新的接口中:

interface NameInterface {
    Name:string;
}
interface AddressInterface {
    Address:string;
}
interface NameAndAddressInterface extends NameInterface, AddressInterface { }
var MyClass: NameAndAddressInterface;
MyClass = class MyClass {
    static Name:string; // if the class doesn't have that static field code won't compile
    static Address:string; // if the class doesn't have that static field code won't compile
}

或者如果你不想命名合并接口,你可以这样做:

interface NameInterface {
    Name:string;
}
interface AddressInterface {
    Address:string;
}
var MyClass: NameInterface & AddressInterface;
MyClass = class MyClass {
    static Name:string; // if the class doesn't have that static field code won't compile
    static Address:string; // if the class doesn't have that static field code won't compile
}

工作示例