2016-10-20 5 views
2

У меня есть машинопись файл config.ts, который будет работать с узлом:Могу ли я использовать функцию разрешения пользовательского модуля (например, «proxyquire») вместо require() с помощью TypeScript?

import myDependency = require('my-dependency');  

export = { 
    doSomething =() => { 
     ... 
    } 
} 

В другом файле машинопись, я могу import этот файл с полной безопасностью типа:

import config = require('./config'); 
config.doSomething(); 
config.doSomethingElse(); // compiler error, this method doesn't exist 

Теперь я хочу модульное тестирование этот скрипт. Чтобы издеваться над зависимостями, которые этот скрипт require() s, я использую proxyquire, который позволяет мне предоставлять значения, которые мой скрипт получит, когда он совершает вызовы require(). Вот что мой тест может выглядеть следующим образом:

import proxyquire = require('proxyquire'); 
const config = proxyquire('./config', { 
    'my-dependency': {} // this mocked object will be provided when config.ts asks for `my-dependency` 
}); 

expect(config.doSomething()).to.do.something(); 

Это работает отлично, за исключением того, что моя config переменного типа any, потому что я использую proxyquire() вместо require(). TypeScript должен предоставить специальную обработку функции require(), чтобы позволить ей выполнять разрешение модуля. Есть ли способ сказать компилятору TypeScript, что proxyquire() также должен выполнять разрешение модуля, аналогично require()?

Я мог бы переписать config.ts как класс или использовать его интерфейс. Затем я смог бы явно ввести переменные в свои тесты, импортировав определение класса/интерфейса. Но разрешение proxyquire() неявно вводить вещи для меня было бы намного проще.

ответ

0

Существует обходной путь - вы можете получить тип config.ts модуля путем импорта фактического модуля и использования typeof в типе броска:

import proxyquire = require('proxyquire'); 

import configType = require('./config'); 

const config = <typeof configType> proxyquire('./config', { 
    'my-dependency': {} // this mocked object will be provided when config.ts asks for `my-dependency` 
}); 

config.doSomething(); 

// config.noSuchMethod(); // does not compile 

Это не идеально, потому что вы должны импортировать тот же модуль в вашем тест дважды - реальный, просто чтобы получить тип и «проксимированный», чтобы фактически использовать в своих тестах, и вы должны быть осторожны, чтобы не смешивать их. Но это довольно просто по сравнению с задачей реализации другого варианта разрешения модуля для машинописного текста. Кроме того, когда configType используется таким образом - только для ввода текста - его импорт даже не появится в сгенерированном коде javacsript.

 Смежные вопросы

  • Нет связанных вопросов^_^