Maybe this is just how TypeScript works, but I'm having trouble testing a pure function when it's in a file with other code — that other code only works in a browser environment so TypeScript compilation fails.

Here's what I mean:

template.ts:

// HtmlUtility uses jQuery+plugins, also window and document globals and really
// can only run in browser, currently only in a real environment of our app
import { HtmlUtility } from './htmlUtility.ts'
import { version } from './package.json'

export class Template {
    // This also can only run in a browser because of dependency on HtmlUtility
    constructor() {
        this.url = addVersionToUrl(window.location.href, version);
        HtmlUtility.someFunction(this.url);
    }
}

// This is a pure function so importing it shouldn't have any side effects. In
// Reality this code is more compilcated but it's still without dependencies.
export function addVersionToUrl(_url: string, _version: string) {
    return `${_url}?v=${_version}`;
}

template.test.ts:

import { addVersionToUrl } from './template'

// I'm using Mocha but I don't think it changes anything
describe('Template', function() {
    describe('addVersionToUrl', function() {
        it('adds version to url', function() {
            equal(addVersionToUrl('/test', '1'), '/test?v=1');
        })
    })
})

However, when trying to run this test, it first compiles the entire template.ts with all its dependencies, including code that only runs in browser and requires jQuery to exist as a global. That compilation fails due to missing window and then missing jQuery even when using jsdom with jsdom-global/register. It just doesn't seem reasonable that importing a pure function also requires all the other unrelated code to work, even simply considering compilation/testing speed.

I could see that this is simply due to the way TypeScript works, that it needs to compile the entire file (imports and all) first before it's able to provide the exact function I'm requiring. But is that really the case? Or is this something that I can work/configure my way around?

0 Answers