Sammanfoga TypeScript-gränssnitt inuti moduler


Jag försöker slå ihop Matchers-gränssnittet från jasmine. Gränssnittet deklareras inom jasmine-namespace.

Jag har skapat en .d.ts-fil och lagt till följande:

declare namespace jasmine {
    interface Matchers {
        toBeSuccessful(): boolean;
    }
}

Detta fungerar, men om jag försöker lägga till en import-sats i .d.ts-filen fungerar det inte. toBeSuccessful-funktionen känns inte igen.

Jag försökte också att lägga till den här delen av koden i min implementering av funktionen och inte i d.ts-filen, men då är andra medlemmar i namespace inte tillgängliga längre, till exempel i den här koden:

class ToBeSuccessfulMatcher implements jasmine.CustomMatcher {
    compare<T>(actual: Result<T>): jasmine.CustomMatcherResult {
    }
}

Gränssnitten CustomMatcher och CustomMatcherResult är inte längre tillgängliga.

Vad missar jag?

Svar #1

Att lägga till import-satsen i deklarationsfilen förvandlar den .d.ts-filen till en modul, och "flyttar" alla deklarationer i filen till den modulens omfång.

Så namespace jasmine i din .d.ts-fil är inte längre i samma omfång som den "riktiga" namespace jasmine (troligtvis är den i globalt omfång), så din interface Matchers är också i ett annat omfång än den riktiga Matchers, och deklarationer från olika omfång slås inte ihop.

Lösningen, när du har import eller export på topnivå i din .d.ts-fil, är att använda uttrycklig global-scope där:

declare global {
    namespace jasmine {
        interface Matchers {
            toBeSuccessful(): boolean;
        }
    }
}

Som referens, se även "global förstärkning" i slutet av dokumentet om deklarationssammanfogning.

Också, när du lägger till Matchers-gränssnittet i din implementation, är det återigen i en annan scope än det riktiga Matchers och det döljer jasmine Matchers istället för att slå ihop med det.

Relaterade artiklar