45

Errorホスト オブジェクトをカスタムUploadErrorクラスに拡張したいと考えています。次の例は、コンパイル時に失敗します。

class UploadError extends Error {
    constructor(message: string, private code: number) {
        super(message);
    }

    getCode(): number {
        return this.code;
    }
}

TypeScript コンパイラを実行するとtsc、次のエラーが発生します。

UploadError.ts(1,0): A export class may only extend other classes, Error is an interface.

Errorインターフェイスとして定義されているようです。誰かが実装の名前を知っていれば、私はとても幸せになります:-)

更新:私は現在これをハックするために採用しているように、プロトタイプの継承ではなく、Typescripts の継承を使用したいと考えています。

function UploadError (message: string, code: number) {
    this.message = message;
    this.code = code;
}

UploadError.prototype = new Error();

UploadError.prototype.constructor = UploadError;

UploadError.prototype.getCode = (): number => {
    return this.code;
}
4

11 に答える 11

10

アップデート

TypeScript 1.6 はネイティブ型を拡張する機能をもたらしているので、これが着地したときに使用できるはずです

class UploadError extends Error {
    //... calls to super and all that jazz
}

元の回答

superTypeScript でエラー インターフェイスを実装できますが、継承を使用していないため、アクセスできません。

class UploadError implements Error {
    public name = "CustomError";

    constructor (public message: string, private code: number){

    }
}

throw new UploadError ("Something went wrong!", 123);
于 2012-10-16T22:49:23.433 に答える
10

次のアプローチが機能することがわかりました。

declare class ErrorClass implements Error {
    public name: string;
    public message: string;
    constructor(message?: string);
}
var ErrorClass = Error;

class MyError extends ErrorClass {
    public name = "MyError";
    constructor (public message?: string) {
        super(message);
    }
}

生成されたスクリプトは次のようになります。

var ErrorClass = Error;
var MyError = (function (_super) {
    __extends(MyError, _super);
    function MyError(message) {
        _super.call(this, message);
        this.message = message;
        this.name = "MyError";
    }
    return MyError;
})(ErrorClass);
于 2012-11-16T03:58:14.860 に答える
5

これにより、Errorクラス バージョン 1.6 を拡張できるようになりました。プル リクエストのクラス extends 句で式を許可する https://github.com/Microsoft/TypeScript/pull/3516と issue組み込み型を拡張できない https://github.com/Microsoft/TypeScript/issues/1168を参照してください。

tscもう文句を言うことはありませんが、エディター/IDE は更新されるまで文句を言うことに注意してください。

于 2015-06-24T22:50:20.703 に答える
1

TypeScript 1.8 を使用していますが、これは以前のバージョンでも機能する可能性があります。

class MyError extends Error {

  static name: string;

  constructor(public message?: string, public extra?: number) {
    super(message);
    Error.captureStackTrace(this, MyError);
    this.name = (this as any).constructor.name; // OR (<any>this).constructor.name;
  }

};

nodeを使用するには、タイピングをインストールする必要があることに注意してくださいError.captureStackTrace

于 2016-07-30T05:04:18.223 に答える
1

私は答えが受け入れられたことを知っており、ソリューションは間違いなく印象的ですが、例外のためだけにプロジェクトにその量のコードを入れたくありません.

TypeScript が何らかの形で言語レベルで適切な例外を取得するまでは、Error を拡張するのは非常に面倒なので、現在は次の非常に単純なソリューションを使用しています。

class MyError {
    constructor(error: Error) {
        error.name = this['constructor'].name;
        error['type'] = this; // for type-checking in exception-handlers

        return error;
    }
}

throw new MyError(new Error('aw snap!'));

さて、私のエラー タイプは実際にはクラスです。それらを拡張することができます。未処理のエラーがスローされたときに、コンソールに正しいクラス名が表示されます。しかし、私の Error オブジェクトはこれらのクラスのインスタンスではありません。コンストラクタはMyError のインスタンスを返しません。渡した Error インスタンスに独自の名前を適用するだけです。

これは、エラーをスローした時点ではなく、構築した時点でスタック トレースを生成するエラーの問題に対する簡単な回避策も提供します。これは、コンストラクター シグネチャにより、「実際の」エラー インスタンスの構築が強制されるためです。 .

例外ハンドラで例外のタイプを確認する必要がある場合は、['type']プロパティを取得して次のように比較しinstanceofます。

try {
    // something throws new MyError(new Error('aw snap!'))
} catch (error) {
    console.log(error['type'] instanceof MyError); // => true
}

理想的ではありませんが、シンプルで機能します。

MyError を拡張する場合、return super(...)TypeScript によって生成されるデフォルトのコンストラクターは return ステートメントを使用するコンストラクターを想定していないため、毎回コンストラクターを実装して を追加する必要があることに注意してください。ただし、それらは許可されます。

于 2013-11-06T15:28:53.083 に答える
0

プロトタイプを使用して、関数と属性を追加できます。

interface Error {
   code: number;
   getCode(): number;
}   

Error.prototype.code = 1;

Error.prototype.getCode = function () {
    return this.code;
}  
var myError = new Error();
console.log("Code: " + myError.getCode());

で実行するとnode.js、次の出力が生成されます。

Code: 1

エラーは次のように定義されlib.d.tsています。

interface Error {
    name: string;
    message: string;
}

declare var Error: {
    new (message?: string): Error;
    (message?: string): Error;
    prototype: Error;
}

それ以外には、拡張する独自のインターフェースを定義する明白な解決策しかありませんError

interface MyErrorInterface extends Error {       
    code: number;       
    getCode(): number;    
}       
class MyError implements MyErrorInterface {      
    code : number;      
    name : string;      
    message : string;
    constructor(code: number, name? : string, message? : string) {
        this.code = code;
        this.name = name;
        this.message = message;
    }   
    getCode(): number {
        return this.code;
    }   
}   

var myError = new MyError(1);
console.log("Code: " + myError.getCode());
于 2012-10-16T13:13:50.797 に答える