As you may already know, there are two different ways to share functions in JavaScript: default exports and named exports. Default exports are used...
For further actions, you may consider blocking this person and/or reporting abuse
Actually IDEs should not have any problem finding your default exports aslong as they are not anonymous functions or objects. If you use recommended eslint rules, it will tell you not to export anonymous functions and objects.
Yeah but that's a "if you setup that stuff correctly" 😕
Using named exports doesn't depend on ideal circumstances
This works in vscode without any additional configuration and I'm pretty confident it works in most other editors as well, if they understand named exports they also understand default exports as long as your default exports are not anonymous functions.
There is a clear difference between function expression and function declaration and they both serve a purpose.
This can't be a viable solution since imposing function declaration would mean losing the benefits of arrow functions that grab the outer context instead of creating a context. This can be destructive for some project relying on this mecanism.
Also, you can't use that reliably on scalar data types that uses default exports, it simply fails short on your text editor and its completion system (which comes most of the time from the language server). TypeScript/JavaScript language servers do not work well on default exporting scalar data types. So using a default export is very much problematic for a lot of things.
Instead, named exports are harmless in the sense that you can either named export a function expression as well as a function declaration, it does not impose on your team a way of doing things, plus the benefits mentioned above in this article. And it provides the best completions and auto-import capabilities from your language server when used in your text editor (and many editor benefit from that such as Emacs, Neovim, IntelliJ, VSCode, etc...).
You can do this with arrow functions as well:
I've read this paragraph several times now and I still think it makes no sense whatsoever. Can you explain what you mean by this?
Again, this doesn't make any sense to me whatsoever; what is the problem here? Default exports have no name, so what would you want to happen here?
This one makes more sense, but it's not really an argument against default imports. As long as your default export is also available as a named export (which is probably a good idea regardless), this still works 100%.
Again, this is a good reason to also have a named export for your default export, but it doesn't speak against having a default export in any way.
Setting that aside, regardless of consistency or not, if I look at a source file and see
import add from "sum"
I will probably scratch my head multiple times and tell whomever wrote that to fix it (or just not interact with the project if it's OSS)Conclusion
Just provide named alternatives for your default export and everyone will be happy. We can have both.
Isn't that a bit repetitive though? Regarding both default and named exporting.
it's three keywords per file, I don't think that's the kind of thing to seriously be worried about.
This could be a discussion rather than a judgement, this way you're misleading others, named export or default export each export type has a purpose, some times you need to export a single function from a file to serve specific purpose, as you can use named export when you wants to group multiple functions in a single file etc
You had me at "Refactoring" - very true.
Yep, spot on. Especially the Inconsistent Codebases section.
In the rare instances where a named export does need to be renamed, it can always be done with
as
:I'd say what the OP is suggesting is probably the safer bet, but this really is only an issue in really big code bases with lots of people working on it. Also in frameworks like React that have strict file naming conventions as long as you follow those conventions, you should just use the previous standards not make up your own. Another situation where default exports are better is when you are making a npm package, in this use case it only makes things worse for the user if they have to remember the name of the export.
Most of these aren't real problems, and many people use default exports just fine.
I have worked on code bases with default exports where casing and typos have caused discoverability issues.
If it can break "find in files" that's a good enough reason for me to not use it. IDEs make our lives easier in a lot of ways, but at the end of the day an IDE is just a tool. If you need it to understand your code, there's a problem. Anything that makes the code easier to understand without tooling is best practice in my book.
Default exports are not needed. Exporting a single named function from a module is completely unrestricted. If you need to rename a module, use the
as
directive.Then grepping the codebase will at least see the import reference. You won't even need it if you take your time namig things and refactor when things become so similar that their names overlap. So why use default exports?
Good thoughts, I like that you're challenging convention and asking us to think through things rather than just following the norms.
In my opinion, all of what you're saying is true when a file has multiple exports. I do find it confusing to have a default export mixed with named exports. But typically when a default export is used, I only see a single export from that file. I haven't run into any problems with that, especially since the file, function, and import almost always share the same name.
But at the same time, I also see no argument against using only named exports, so maybe you're on to something.
The IDE has no issues finding default exports while typing. It is a matter of providing proper information. Someone already said that if you export a nameless something, then that's a problem, but if you export something with a name, that name shows up in autocomplete.
Furthermore, NPM packages should provide proper d.ts files. Using my
vite-plugin-single-spa
package as example, you just install, then openvite.config.ts
and you start typing "import vitep". At this point you should see autocomplete showing you the right option (vitePluginSingleSpa
).To me , it seems like this articles seems like a personal issue l.
I use Vue , and Typescript , on top of that I apply OOP , which means there are a lot Class files that it makes sense that one File holds 1 default class and maybe some types. I use default export often an I have never any of the problems you mentioned my IDE (Webstorm, intelij) knows exactly where are they. On top of that I use the default export in conjunction with "named export" andy IDE k ow exactly how to import them . import A, {b}.
This is the developer-equivalence of first world problems.
IDEs have no problem discovering default exports in my experience. And I frequently rename default exports and vscode is smart enough to rename imports automatically.
I also have absolutely no issue with somebody deciding to only use named exports in their codebases, go for it. But here we're dressing personal preference as best practice which is incorrect.
The reason we have so many different tools at our disposal is so that we can use the best tool for a given context, and contexts vary greatly in this field. It is disappointing to see so much of these “never use X conventional method ever again” articles and videos which usually fail to sufficiently acknowledge the optimal use cases for the thing they are bashing on and seem aimed at being provocative and generating clicks more than offering genuine educational content. This article starts by acknowledging the correct use cases but then proceeds to suggest never using them ever again.
Default exports are absolutely the right choice when there’s only one thing to be exported, and there are plenty of architectural nuances from project-to-project that could warrant their use in other contexts. This point-blank statement of “default exports are bad and you shouldn’t use them” comes across as biased and imho could be potentially misleading to beginners.
A thing I tend to do, when I am working on a module where it makes sense to have multiple exports, but also one main default export is this:
If you're getting confused by exports then I'd recommend investing a few minutes in getting a free IDE.
As a newcommer to the JS env from cpp/python I don't really see the need of default exports. Everyone else has managed without them.
Good summary.
I especially dont like when I am forced to mix named and default imports from 3rd party libraries. (yes, I know I can make a custom reexport somewhere in codebase).
Totally agree. However, I want to read different point of views in the comments below 🤭
I would say it depends on the project, usually the default exports compilers minify them much better, especially for libraries and frameworks.
This is not a problem at all, at best this post is about preferences. It doesn't speak about numerous pitfalls of using names exports and it's performance
This grossly overlooks and disregards the cases when and reasons why you should use default exports.
Nice one Nguyen, for me as an amateur level developer I find this absolutely sensible 👍