I'm trying to type a UMD module (that I don't own so I can't change it) for the DefinitelyTyped project that has something like this (with actual functions of course):
function getModule() {
function fn1() {}
function fn2() {}
fn1.fn2 = fn2;
return fn1.fn1 = fn1;
}
if (typeof define === "function" && define.amd) {
define(getModule());
} else if (typeof module !== "undefined" && module.exports) {
module.exports = getModule();
} else {
this.moduleName = getModule();
}
Using the module-function.d.ts template, I have this so far:
export as namespace moduleName;
export = fn1;
declare function fn1(): void;
declare namespace fn1 {
function fn2(): void;
}
I then used dts-gen to generate a .d.ts file for me to try to find out how to declare the fn1
function again in the fn1
namespace and got this:
/** Declaration file generated by dts-gen */
export = moduleName;
declare function moduleName(): void;
declare namespace moduleName {
// Circular reference from moduleName
const fn1: any;
function fn2(): void;
}
However, when I tried combining the two in the following code I got the error 'fn1' is referenced directly or indirectly in its own type annotation.
.
export as namespace moduleName;
export = fn1;
declare function fn1(): void;
declare namespace fn1 {
function fn2(): void;
const fn1: any;
}
I don't want to do the following because then it wouldn't represent the fact that you can do require('moduleName').fn1.fn1.fn1.fn2
(or any number of fn1
s.
export = moduleName;
declare function moduleName(): void;
declare namespace moduleName {
function fn1(): void;
function fn2(): void;
}
How would I type this module?
You can use an interface to accurately represent the recursive type:
export = fn1;
declare const fn1: Fn1
interface Fn1 {
// The call signature of fn1
(): void
// The circular reference
fn1: Fn1
// Other functions
fn2: () => void
}