DEV Community

idleman
idleman

Posted on

The problem with TypeScript and its practices

Most of you probably believe TypeScript is best practices these days. It has some advantages, but also disadvantages. Here are some myths and problems with it.

Myth 1: It is typed and safe.

TypeScript is either typed nor safe. Being a typed language means the compiler 100% know the type every single value, the binary representation of the value in memory and how to access it. The typescript transpiler/compiler cannot and does not know this information. The dynamic nature of JavaScript/ECMAScript prevent it. What TypeScript actually do is try to figure that information out or let you specify it, but it has no way to actually knowing.

const value: number = randomInt();
//  value can be anything, really!
Enter fullscreen mode Exit fullscreen mode

Myth 2: It create less bugs

Contradictory what many people say, TypeScript do not create less bugs compared to applications written in JavaScript. It's not my opinion, its research. The research study checked the 15% most popular applications on github. The study in a nutshell says the following:

  • The use of "any" has a positive impact on bug resolution time.
  • TypeScript code contains equal or more bugs than JavaScript code.
  • Its take longer time to fix bugs in projects that is written in TypeScript.

So you should definitely not feel bad if you use "any" or a loose mode in TypeScript.

It is also important to understand that, even if you may find TypeScript code more readable, does it not mean it actually is more readable. Readable code is by definition simple to change and understand, so if it takes longer to fix various bugs in a programming language than in another, is it a sign something is wrong in your understanding what readable code actually is.

PS. I know it exists other studies that say the opposite, but as noted in the research paper as well, those studies are either focus only on a few projects or library code. This is different than what most of us do in our daily life. Most of us code applications, not libraries.

Myth 3: Scalability

How well your application scale regarding code-complexity have nothing to do whatever you code in JavaScript or TypeScript. It is just adversating from Microsoft or a TypeScript lover if someone tell you that. To be honest, types is the least important language feature and even calling it a feature is controversial. Even research papers in 1970s noted it.

Have you heard of loose coupling? It is most of the time the factor that will decide regarding your application will scale or not. It comes in many favors and some people use different words, but the meaning is more or less the same: The less the programmer need to know, the better.

Myth 4: Future proof

TypeScript is not in any way future proof. In every places you can run TypeScript today, do you actually run JavaScript. There is a proposal to add some type-annotations to the language, but if you read all issues and even meeting notes is it clear:

  • Annotations will just be treated as comments. You cannot trust it the type in any way.
  • Most TypeScript code will never work because it uses TypeScript-specific features.
  • It does not offer any technical benefits.
  • Many people are against the proposal, some of those people are inside the committee itself.

Do you remember HTTP 2 push? Chrome deprecated the support because too few websites used it. So even if it got standardized (that is a huge "if"), would browsers probably not add support for it anyway:

  • It does not offer any technical benefits, more the opposite (more bytes => slow website).
  • Almost every website use bundlers and and those who does not will almost certain use TypeScript specific features that is not supported anyway.

Problem 1: Encourage named exports

Almost every module should export only one thing. There is very few exceptions to this, for example configuration files or a file containing multiple constants. And if you export only one thing, the default export is the obvious candidate. The argument TypeScript lovers usually say is it ease refactoring but it is technically impossible.

If you use default exports do you hide the identifier/name of the thing you export. It is by definition better because it remove a dependency, you do not need to know what name of some thing has within a file, only the interface of the thing the file exports. It's great. It means less coupling and less "need to know". Its honor SOLID principles and is great software design. It also encourage the developer to give great names for imported modules and each file has different contexts, so it make clear sense different names/identifiers may be used depending on context.

The issue is of course and it is the main reason why some developers prefer named exports, it force the developer to give each package a name when you import it, so different files may use different names:

File 1

import Foo from 'somewhere';
Enter fullscreen mode Exit fullscreen mode

File 2

import Bar from 'somewhere';
Enter fullscreen mode Exit fullscreen mode

The consequence is that if you use some "refactoring" tools, will it be harder to rename the "default export", especially on a project-wide basis. Both file 1 & 2 will probably still use the names Foo and Bar even after a automatic refactoring for example. And it is great because there is hopefully a good reason why those names were used in the first place. Some people forget that.

Problem 2: Do not support import by .ts extension

ECMAScript/JavaScript import modules by import/dependency specifiers and every plattform I know will convert the dependency specifier to some path or an url it can fetch. If the direct location cannot easily be defined, must the platform perform some kind of traversal (visit many files before it "knowns"). This process is slow, but remarkable slow if it is done over a network. This can be fixed if the developer provide more specific dependency specifiers, for example adding the file-extension. But there is a problem:
TypeScript do not support if you add the .ts extension. It does not rename dependency specifiers. Its extremely weird actually:

  • The TypeScript team do 100% know TypeScript is not supported natively anywhere in the world. So you cannot evaluate a file containing TypeScript code. It must first be converted to JavaScript.
  • The TypeScript team 100% know the ".ts" extension is their own file-extension and it is extremely likely if someone want to import a ".ts" file from a TypeScript file, is the file very likely a TypeScript file.
  • The TypeScript transpiler itself will re-write all code, have almost in every case access to all dependencies and will create ".js" files by default.

There is no excuse for not supporting it.

Problem 3: Encourage bloat

The TypeScript community encourage developers to some really bad habits that make code bases bloated. Examples:

Over-use strict mode.

Strict mode do not produce less bugs nor it is more readable. Sure, you may believe so, but science says it's not. You should absolutely use "any" if it makes the code shorter and easy to read, yet there is an insane belief its bad. Its not!

Overuse of unions types

If your function has multiple declarations, use multiple functions. There is a reason why parseFloat and parseInt is different functions instead of just "parseNumber".

Overuse of types

You should not care about the type a specific value has, but the interface the value has. Instead of doing:

function getName(user: User): string {
    return user.name;
}
Enter fullscreen mode Exit fullscreen mode

should you prefer:

const getName = ({ name = '' } = {}) => name;

getName()  // OK
getName(123)  // OK
getName(true)  // OK
getName(undefined)  // OK
getName(Symbol('test')) // OK
getName(null) // TypeError, but this is the only case
Enter fullscreen mode Exit fullscreen mode

The same applies if you work with generic and variadic arguments:

const add = (...args) => args.reduce(((s, v) => s + v), args.shift());
Enter fullscreen mode Exit fullscreen mode

The code style is called defensive coding and it is scientifically proven to be the best method among programming languages in general together with tests to actually decrease the number of bugs and create more robust software. It a very important skill to learn. And yes TypeScript will detect if you call "getName" with something else than an object. If it does not, check your tsconfig.

Disclaimer

I know there is a lot of people in the TypeScript community that is so insecure in their programming skill so they take any critic against the programming language personal. Please do not. I don´t want to force you stop using TypeScript. Use what every programming you want. I just want to spread some facts that I know are unpopular, but yet undeniable true.

Latest comments (13)

Collapse
 
brense profile image
Rense Bakker

The research you linked doesnt appear to conclude what you are concluding from it.

Our Findings therefore indicate that using TypeScript and adhering to its type safety has benefits, but not the straightforward advantage of directly reducing bugs.

This is true. Type safety does not directly reduce bugs. It just catches some bugs at compiletime instead of runtime. A lot of the repos they tested use other testing strategies to catch runtime bugs. They also discuss this in their discussion a few reasons why their research could be wrong about this :P

They say exactly the opposite about bug resolution time from what you claim:

Contrary to expectations, only a single one of our bug-related hypotheses could be accepted, namely that a decreased usage of the any type is correlated with a faster bug resolution time in TypeScript apps. In comparison to JavaScript apps.

And in their discussion part, they discuss atleast one other study who found that Typescript DOES decrease the number of bugs. So one could just as easily link to that research and claim the opposite of what you are saying...

Your problem #1: I dont follow your reasoning... You dont want to use named exports? Then dont... You can simply turn it off in your eslint. Your code completion is going to suck, but whatever floats your boat I guess 🤷

Your problem #2: Why would you want to fetch ts files over a network? You compile typescript to javascript... How imports are handled in the compiled js depends on the module resolution you specify in your tsconfig: typescriptlang.org/docs/handbook/e... you can control nearly every aspect of how your ts code is compiled into js, here are all the options: typescriptlang.org/tsconfig

Your problem #3 I disagree with completely. Typescript is powerful because it does type inference, MS spent a shitload of time making sure it has very strong type inference. They encourages you to NOT over-use typing, but rely on type inference whenever possible.

Collapse
 
zirkelc profile image
Info Comment hidden by post author - thread only accessible via permalink
Chris Cook

@brense thank you very much for taking the time to debunk this post! 🙏

I fully agree with your points!

Collapse
 
idleman profile image
idleman

Debunked? He failed to give any objective fact and and research paper.

Thank you very much for taking the time to debunk @brense!

Thread Thread
 
zirkelc profile image
Chris Cook

I see there is no sense in arguing with since the first thing you do is to hide my comment.

Thread Thread
 
idleman profile image
idleman

Well, your comment did not include any useful information for anyone. If it did, I wouldn't hide it. This is not a "give each other back thumbs" post. Read the disclaimer.

Collapse
 
idleman profile image
idleman • Edited
  1. Everything I claim has support in the research, everything. If you don't agree so is it unfortunate, but your words have no weight compared to that research paper.

  2. Regarding others research papers that claim the opposite:

PS. I know it exists other studies that say the opposite, but as noted in the research paper as well, those studies are either focus only on a few projects or library code. This is different than what most of us do in our daily life. Most of us code applications, not libraries.

I am free to change my mind, but you need to show me a research paper that have:

  • Conducted tests on more than 600 open source projects.
  • All projects should be similar, popularity and activity.
  • All projects are application-based.
  • The people behind research team have no connection to Microsoft or any organization that would benefit from TypeScript becoming more popular.
  1. Named exports is bad because it increase coupling and it my friend have proven to be bad. Why do you think we have variables? Functions? Modules? Every single thing of those are connected to less coupling. And do I actually need to tell you that you don't need to tell a more senior developer than you what she or he cannot do? Answer: You don´t.

  2. You want to avoid path traversal and you do it by providing specific import/dependency specifiers. If you don´t understand why it is bad thing with the explanation I gave in the post so is there nothing I can say to help you, unfortunately.

  3. So you would say the general recommendation in the TypeScript community is not to add type-annotations and instead let the TypeScript compiler figure it out? I gotta say, you have no clue what you are talking about then. If it was the goal, would TypeScript team remove the "strict" mode immediately and just give a warning the code complexity is so high so it cannot understand what type some value has.

Collapse
 
brense profile image
Rense Bakker

I quoted literal phrases from the research that YOU shared. They are not compatible with the claims that you make. Ergo, you are just here to troll. I would be impressed, except this particular troll topic has already been visited by so many other trolls, its kinda sad you couldn't come up with something new.

Thread Thread
 
idleman profile image
idleman • Edited

I claim TypeScript have equal or more bugs than JavaScript code. And it is the result from the research:

TypeScript applications have a higher bug fix commit ratio than JavaScript applications, i.e., are more or equally prone to bugs.

I don't claim TypeScript don´t have benefits, even if you code in assembler it has benefits. I claim TypeScript do not make your code having less bugs. THAT IS THE CLAIM!

Thread Thread
 
lionelrowe profile image
lionel-rowe

Correlation doesn't equal causation, though. There could be any number of reasons for that, e.g. TS apps could also be correlated with having more mature bug reporting systems, hence more bugs are reported, hence more bugs fixed. Another hypothesis could be that devs working on TS projects are more likely to classify something as a bug vs an enhancement. Or that they're less likely to combine multiple bugfixes into a single commit. Or that the overall speed of iteration is faster on TS projects, hence more bugs are introduced, because feature commits tend to cover more functionality at one time.

Not saying any one of those is necessarily true, just that a correlation on its own proves nothing without further investigation.

Thread Thread
 
idleman profile image
idleman • Edited

Sure, but its research. There is always a bunch a reason why something are the way they are. That is why more investigation is needed. However,if you keep in mind:

  1. JavaScript is a more simple language than TypeScript
  2. TypeScript is more code in general, more information to process.
  3. The developer experience is similar between the projects.

Makes your explanation very unlikely. Sure, it can be that way, but it's unlikely. Why should developers behave complete different in their commit-style if they have the same skill? They probably´t don't.

In science is it always extremely important to take the most logical explanation first until evidence says otherwise even if you don't like it. As newton would argue: An apple falls down to the ground. The ground does not rise to the apple.

Thread Thread
 
lionelrowe profile image
lionel-rowe

No, science is not about what seems "logical" to you, it's about empirically testing hypotheses and then observing the results in a way that's repeatable and controls for confounding variables. Gravity isn't true because Newton thought about it really hard in his armchair and logicked it out, it's true because every time you drop something it falls towards the earth unless some other force is acting on it.

Also it's kinda funny you chose that particular example, as Newtonian physics has already been superseded by relativity, and from a relativistic point of view, it's no more correct to say the apple falls from the tree than it is to say the ground rises to meet the apple.

Thread Thread
 
idleman profile image
idleman • Edited

Why do then the author himself draw that conclusion? Answer: It is the most logical. All studies is from observations and the observation says TypeScript projects has more issues and it takes longer to fix them. These are the numbers. The most simple answer is then the numbers are true, TypeScript do produce more bugs.

You think it is the only study, but its not. Multiple studies have been made about functional vs OOP, typed vs untyped and so on for decades. However, it is the best study on TypeScript vs JavaScript I know off that compare most projects and have no connection to Microsoft in any. You are free to suggest another study than goes further if you want and I will remove that part.

About the apple and the ground rises, you know. It was kinda my point. People see a apple fall from the tree instead of the ground rises because it is most logical except for those who have a belief this cannot be the case. You are similar. You want to see any explanation than the most obvious: TypeScript create more bugs. Probably because you love TypeScript.

A side note: Do you know people are prepared to do extreme things when something challenge their personal belief? Their brain do not respond the same way when personal belief are challenged. Even if you have observation that prove otherwise, do they still not believe it. You can monitor their brain and actually see it. People have committed horrible crimes in all history just because the alternative was to change their "belief". Don´t go down that road, be better.

Collapse
 
efpage profile image
Eckehard

We should also mention, that module encapsulation in Javascript is also not very strict (see here). As TS is transpiled to JS, this will affect the result anyway.

Some comments have been hidden by the post's author - find out more