Building a library in TS to be called by TS and JS code and wondering how people hide internal methods and fields. Java has package visibility to handle this. Lacking that in TS, I see two options:
Define interfaces to only expose certain members. But this involves duplicating the definitions and extra code to cast arguments from interface to implementation types.
Put an @private doc comment on the internal members. Possibly exclude such from generated docs.
Note: the private qualifier is NOT a solution, as it only allows code from the same class access. I am talking about the need to access fields from other classes in the same library, but preventing access from clients of the library. That is what Java's package access does.
Since TypeScript 3.1, you can use the stripInternal
compiler option. When generating declaration files, this stops declarations being generated for code that has the @internal
JSDoc annotation.
This compiler option can be enabled in the tsconfig.json
file:
{
"compilerOptions" : {
...
"stripInternal": true
}
}
For example, the following declarations will be suppressed:
//Class will not be visible
/** @internal */
export class MyHelperClass {
}
export class MyPublicClass {
//Method will not be visible
/** @internal */
helperMethod() {}
}
// Binding will not be visible
/** @internal */
export const MyValue = 5;
However, this will have no effect on code that sees the *.ts
source files, such as your own code.
If you distribute your package as a mix of *.js
and *.d.ts
files, like most NPM packages, this will effectively hide the member from code outside your package. But if you distribute the code as *.ts
files, it won’t help you.
private
modifier keyword. Note that in the end everything in JavaScript is quite public because of the prototyped based language. There are also no actual namespaces. So maybe you should not worry too much. Good documentation always helps.
As a sidenote it might be interesting to know that there are great other transpilers like TypeScript. Haxe for example solves this problem a bit more elegant because of their more OOP oriented language design, where you can grant and request access using metadata on top of the access modifiers. You might find this more convenient coming from Java. Still, in the end everything will be public because of JavaScript.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With