Reputation: 7250
I have read that they do the same thing when on the top level? However, in my case:
This works fine:
export class First{}
export class Second{}
but following gives error:
class First{}
class Second{}
module.exports = exports = {First,Second}
Error: File 'filepath.ts' is not a module.
Upvotes: 1
Views: 5105
Reputation: 151531
[Pay close attention to the difference between the singular export
and the plural exports
in what follows. They are not interchangeable.]
Both export ...
and export =
are treated as export statements by TypeScript. (Yes, even the 2nd one, which looks like a plain assignment, is in fact treated as an export statement.)
module.exports = exports =
is a pair of assignments that has no special meaning as far as the TypeScript compiler is concerned. It is a way to export symbols in CommonJS modules.
Both can be used to export symbols (with some workarounds required in the 2nd case to pacify the compiler), but I recommend using the TypeScript export
statements over the CommonJS assignments.
export ...
and export =
are treated as export statements by TypeScript. When us use this, the compiler knows you want to export some symbols from your file. If you try to import in another TypeScript module a file using this, everything is fine, because your use of export ...
or export =
in the first file tells TypeScript "this is a module", and you've clearly indicated to TypeScript what you want to export.
The code module.exports = exports = ...
is treated as two assignments, and has no special meaning beyond this. For the TypeScript compiler, it's the same as foo.bar = bar = ...
. In both cases, TypeScript will perform type checking on the code but it won't treat it as specifically exporting anything. So if you import a file that uses this, you will get the error you saw: Error: File '...' is not a module.
Since your file does not contain any import
or export
statements, TypeScript does not treat the file as a module.
While you can concoct workarounds to use module.exports = exports = ...
to export symbols, I don't recommend using module.exports = exports = ...
in TypeScript code. This is a CommonJS way of exporting symbols. AMD modules can also in theory support it, but the TypeScript compiler does not make module
visible by default when it emits AMD modules. So whatever concoction you'd use to make it work with CommonJS will require more concocting for AMD. And other module formats that exist now or will be developed in the future may not be able to handle it at all. I'd replace it with:
class First{}
class Second{}
export = {First,Second}
When you are using CommonJS, the compiler emits this for the last line:
module.exports = { First: First, Second: Second };
If you set the compiler to emit AMD modules, it will just return { First: First, Second: Second }
from the module factory. And will emit something appropriate for other module formats it supports.
In the rare case where I'd need to use a local reference to the object I'm exporting, I'd modify my export to do this:
const ex = { First, Second };
export = ex;
Then ex
can be used locally in the module in the same way exports
can be used locally in the CommonJS idiom.
Upvotes: 2