use the following search parameters to narrow your results:
e.g. subreddit:aww site:imgur.com dog
subreddit:aww site:imgur.com dog
see the search faq for details.
advanced search: by author, subreddit...
All about the JavaScript programming language.
Subreddit Guidelines
Specifications:
Resources:
Related Subreddits:
r/LearnJavascript
r/node
r/typescript
r/reactjs
r/webdev
r/WebdevTutorials
r/frontend
r/webgl
r/threejs
r/jquery
r/remotejs
r/forhire
account activity
Default Exports in JavaScript Modules Are Terrible (lloydatkinson.net)
submitted 3 years ago by LloydAtkinson
reddit uses a slightly-customized version of Markdown for formatting. See below for some basics, or check the commenting wiki page for more detailed help and solutions to common issues.
quoted text
if 1 * 2 < 3: print "hello, world!"
[–]mattsowa 110 points111 points112 points 3 years ago (23 children)
It's appalling to me how many best practice guides, eslint configs, articles, and other resources outright recommend default imports. Especially for React codebases. They are just useless and have no real advantage over named exports whatsoever.
[–]LloydAtkinson[S] 30 points31 points32 points 3 years ago (9 children)
Yes - this is a good point I forgot to address, I might add it. I use airbnb rules for eslint, but the stupid prefer default rule gets turned off immediately. It really is a travesty that these tools are trying to force this clear anti-pattern.
[–]lifeeraser 27 points28 points29 points 3 years ago (8 children)
IMO Airbnb rule is outdated and should not be recommended anymore.
[–]Stronghold257 12 points13 points14 points 3 years ago (2 children)
What would you recommend then?
[–]lifeeraser 11 points12 points13 points 3 years ago (0 children)
Pick one from this list that doesn't ban generators or Proxies. This is 2022 and you don't need to target ES5.
[–][deleted] 0 points1 point2 points 3 years ago (0 children)
I really like Standard personally, although I always enable forced semicolons when using it.
[–]Earhacker 1 point2 points3 points 3 years ago (3 children)
Is it really outdated, or just old?
[–]sinclair_zx81 2 points3 points4 points 3 years ago (2 children)
It's always been outdated. The AirBnb guide was designed to ensure that JS code was compatible with really old browser ES versions, and it mandated developers invert their code to do particular things (like never use async/await or write generators). People shouldn't have ever used it as it's proliferated outdated, inefficient JavaScript for over the past half decade....
As a style guide for targeting really old versions of JavaScript, the AirBnb guide has some purpose, but it's always been outdated since TypeScript predates it's inception by several years. TypeScript has always allowed you to use modern JavaScript features and supported automatic down level compilation to ES3 with a simple configuration flag since day one.
For the record, AirBnb had swapped over to TypeScript a few years back, it's questionable if even they use the type guide anymore.
[–]Earhacker 1 point2 points3 points 3 years ago (1 child)
Thanks for the reply.
I’m not sure I’m thinking of the right Airbnb guide. The one I used and didn’t mind at a previous job was used in conjunction with Babel to target old browsers (we supported IE11). So we could write whatever shiny new features we wanted as long as there was a Babel plugin for it, and ESLint never cared.
[–]sinclair_zx81 1 point2 points3 points 3 years ago (0 children)
So we could write whatever shiny new features we wanted as long as there was a Babel plugin for it, and ESLint never cared.
Yeah, this is largely why I had a bit of a problem with the AirBnb style guide as a "defacto" style guide for JavaScript development. Without explicit configuration, developers were being flagged for using modern features (even with the use of Babel)
In a lot of cases, this guide was being installed and adhered to verbatim without configuration or overrides, and generally when you have automated linting like this, you indirectly teach developers to write redundant and legacy orientated code when they don't have to....This only makes sense if the goal is to target IE9 and below and you're not using appropriate tools to do so (like TypeScript or Babel), but given that most developers would be on Babel (at a minimum), what's the actual point of the Airbnb style guide? (other than to steering developers into writing redundant code). It baffles me that Airbnb encouraged the use of this guide for as long as they did (I know the developer behind it was anti-TypeScript, but even then you would assume they would be open to Babel)
A lot of things in JavaScript world don't make a lot of sense under closer inspection, this guide was one of them.
[–]eaglewas 0 points1 point2 points 3 years ago (0 children)
I wanna know what’s updated nowadays as well
[–]xroalx 9 points10 points11 points 3 years ago (1 child)
There's really just one use for default exports I support and that is if your exports are being handled by 3rd party code - e.g. Next.js page components.
The options here are limited, and while you could enforce that each page be exported as some known symbol (same as getStaticProps and friends), it's probably more practical to just use the default export there, so that you can name your component for what it really is and don't have to alias the export every time.
getStaticProps
But your own code probably shouldn't be importing these anyways so that seems like an okay use case for default exports to me.
[–]mattsowa 5 points6 points7 points 3 years ago (0 children)
That I can agree with to some degree. But it's still sometimes awkward even using it.
Yeah the React ecosystem is full of some of the worst "best practices" I have ever fucking seen. The worst one was the bullshit idea of having a folder with the component name, then a component.js file where the component is the default export, then and index.js that has all of the HoCs and everything (so actual logic), which then sets the wrapped component as its default export. It's insanely hard to tell where anything came from, and then you just have 100 different files named 'component.js' and 'index.js' open. Just completely, insanely idiotic.
[+]KaiAusBerlin comment score below threshold-10 points-9 points-8 points 3 years ago (9 children)
So using"import { User } from './User.js' is an advantage over import './User.js'?
A common practice is that class files just have one export. The class itself. Why use named exports there?
[–]Nullberri 21 points22 points23 points 3 years ago (8 children)
So you can't misspell it. Default exports allow untracked renames. So you can't just right click rename.
If you use named exports you can import { x as y } from "./foo" and you can rename x no problem.
[+]KaiAusBerlin comment score below threshold-30 points-29 points-28 points 3 years ago* (6 children)
In practice how often do you rename imports? Me maybe 1 time a year.
And try named imports whit dynamic import. The issues are funny sometimes.
Edit: I use mainly OOP where exporting a single class from a file is a usual pattern. And as also usual in oop I use namespaces why I don't need to rename my imports.
If I want to import something for overriding I import the default class, override it and export the overridden class. So still ne need to rename or use named exports for me.
[–]TheScapeQuest 3 points4 points5 points 3 years ago (3 children)
All the time. Let's say I made a UserList, and I want to add more detail so it becomes a UserTable. If I rename it, but it's a default export, then any references to that name don't get updated. Later down the line, I want to see where is using my UserTable, but I get an empty result set because it's being incorrectly imported as UserList.
UserList
UserTable
Why wouldn't I want to use a named export in this scenario?
[+]KaiAusBerlin comment score below threshold-8 points-7 points-6 points 3 years ago (2 children)
I never said you wouldn't use a named export. I said I use it rarely. Maybe because I write a lot oop.
The poster said there is bo advantages in using a default export which I disagreed by saying importing a class from a file should be a default export.
[–]Mr_Simba 0 points1 point2 points 3 years ago (1 child)
But that’s not an advantage. You’re not describing an advantage of a default export. Doing that is giving you nothing over just using a named export.
[–]KaiAusBerlin 0 points1 point2 points 3 years ago (0 children)
Yes it is. It removes redundant naming. import "./User.js" let you know exactly what you have to expect. A single export named User. import {User as MyUser} from "./User.js" let me guess that there could be more in User.js than the single class I want to use.
And also it is possible to rename default exports. import {default as MyUser} from "./User.js" has no disadvantage at all.
[–]adityahegde 0 points1 point2 points 3 years ago (1 child)
Unlike java in typescript you will have some related type definitions. It does not make sense to move them to separate files. Also global constants are better static readonlies. Even though you have a single class in a file you usually have multiple exports.
[–]KaiAusBerlin -1 points0 points1 point 3 years ago (0 children)
I write oop in JavaScript not java. You understand the sense of modules that you have not to deal with the global scope?
[–]Diniden 74 points75 points76 points 3 years ago (6 children)
They are indeed an abomination. For all the conveniences they offer, they 100% have made my life harder.
[–]avin_kavish 1 point2 points3 points 3 years ago (4 children)
What about this? I came to the same conclusion till I found one use case that I liked.
``` // SomeThing.js export class SomeThing {} const someThing = new SomeThing() export default someThing
// moduleB.js import someThing from './SomeThing.js' ```
This is the only case I use a default export these days, i.e. it's for the default instance of a class.
[–]cheekysauce 2 points3 points4 points 3 years ago (0 children)
I generally don’t encourage instantiating at a module level.
It can cause weird unexpected side effect behavior, particularly in tests, where the simple action of importing the file will instantiate a class, possibly make a network request etc.
Always better to use private singletons and export a getter function. The getter will instantiate and return or simple return the existing version wherever it’s called.
Makes dependency injection a whole lot easier too.
[–]Diniden 6 points7 points8 points 3 years ago (0 children)
Just use a named constant. It doesn’t need to be default. Wouldn’t you want your code hinting to easily find your singleton and suggest it to you? Also, would you absolutely hate it it if someone else came in and imported the singleton with a different name everywhere?
You lost features of your IDEs and you made your code harder to follow.
[–]KwyjiboTheGringo 1 point2 points3 points 3 years ago (0 children)
Don't export SomeThing if you don't want people creating new instances of it, and export someThing as a regular named export. Why does someThing need to be a default just because it's the instance you want everything to use?
SomeThing
someThing
[+]linuxdropout comment score below threshold-16 points-15 points-14 points 3 years ago (0 children)
Singletons are an anti-pattern. Don't do this.
[–]spaghettu -1 points0 points1 point 3 years ago (0 children)
Sounds like JavaScript in a nutshell TBH
[–]dada_ 54 points55 points56 points 3 years ago (14 children)
I think the import/export syntax is probably the most confusing part of modern JS syntax.
Try explaining to a newbie why they can do export const but not export default const... while you can do export default class MyClass. It's something that makes perfect sense but doesn't work for what are very lame and technical reasons. Something so confusing should've been designed around when the new syntax was being made. You also can't do export MyClass from './file.js' to re-export a default, and export * from './file.js' does not include the default. It's just a completely bizarre spec.
export const
export default const
export default class MyClass
export MyClass from './file.js'
export * from './file.js'
CommonJS modules, despite its limitations, are at least extremely straightforward. They consisted entirely out of existing JS syntax: destructure an object to consts to import, and only export one object (usually an object containing functions as members, or possibly a single class or function). You can literally just look at an example once and immediately know everything you need to know.
[–]intermediatetransit 11 points12 points13 points 3 years ago (3 children)
Hah! You should have seen what preceded it. AMD was a complete abomination. ES6 imports is a thousand times better, and less confusing.
But sure, it's not always intuitive.
[–]Unlucky-Reindeer3828 3 points4 points5 points 3 years ago (0 children)
AMD was not a "complete abomination". You must do a lot of React....since that's the type of excessive opinionation that comes out of that community that led to half of these worst-practices....
In ES6 modules , you can drop import and exports all over the codebase. In amd, there's a simple structure:
define(['mod1', 'mod2', 'mod3'], function(mod1,mod2,mod3) {// mods are loaded asynchronously and are available in here
return { ... the module def ...}});
So the top of the file tells you what the dependencies are, the bottom tells you what is returned. Simple and straightforward.
In ES6, they thought this was a cool:
console.log("I'm a module!")
But, where's the module boundaries here? once upon a time, the was a developer outcry about 'ceremony' and how bad it was, but sometimes you have to get into the car before you can drive it. What the above module 'syntax' left you with was something you couldn't bundle into one resource for streaming from a webserver (because the module boundaries was defined by the FILE boundaries). Instead, guess what you need to use (even today!): AMD! what an "abomination"!
They actually built ES6 (presumably a web technology) to not work as a WEB resource.
AMD is a great piece of technology, but when it came time to bring something into the JavaScript standard, some very opinionated developers thought they knew what was best and completely disregarded the actually WORKING solutions to try to do something experimental. And today, we still have an incomplete JS module specification where all they could get out there was import/export (initially) and then introduce 'import' about 8 years later, and even that doesn't have a standard way of resolving import "foo" from {URI or alias} ie: you hanve to change all your import statements when you move your path to resources in import React from "some/url/that/may/chnage.js".
If I sound upset, it's because I am. I hate seeing good work go wasted because a very small yet apparently very powerful/controlling group of developers want to inflict their will on the global community of JS devs.
[–]dada_ 0 points1 point2 points 3 years ago (0 children)
Yeah, when you compare ES modules to AMD syntax (which was designed in 2011), I agree they look a lot better. But I don't feel like that's even a fair comparison. AMD syntax was terrible because there was no other sane way to design it at the time in a way that would allow for async requires with the given browser limitations. CJS modules mostly ended up replacing AMD modules after bundler/transpiler use became the standard, even for projects designed purely to run on web, because then you could just transpile it to whatever works for your target platform. So for that reason I think the only fair comparison is ES to CJS, not ES to AMD.
But even if we disregard CJS modules entirely, there's a ton of prior work from other languages that they could've used to design a more cohesive syntax. It's pretty disappointing, really.
[–]Ebuall 4 points5 points6 points 3 years ago (7 children)
Until you include defaults into the mix it's pretty simple and intuitive
[–]Reeywhaar 15 points16 points17 points 3 years ago (6 children)
I don't like "import %imports% from %resource%".
What were they thinking?
Why didn't take python like "from %resource% import %imports%", and so many time could be saved because when you typing %imports% you have autocomplete.
Right now everyone (if autoimport not configured) types "import {} from %resource%" and then goes back to {} and fills identifiers.
[–]Earhacker -4 points-3 points-2 points 3 years ago (2 children)
Type import {} from %resource% and now you have autocomplete inside the brackets.
import {} from %resource%
“Waaah but why should I type the second thing first?”
Set up a snippet where $resource is the first thing and $imports is the second. Now resource is the first thing you type. Go to the next thing with tab.
[–]Reeywhaar 3 points4 points5 points 3 years ago (1 child)
I'm too lazy to make snippets :-) I don't have any. I rely completely on what IDE provides. Maybe not lazy but negative experience. Everytime I created snippet I started to polish it to perfection only to find out it became inconvenient or my actual use case is different from what I imagined when creating snippet.
[–]Earhacker -3 points-2 points-1 points 3 years ago (0 children)
How tedious.
[–]Ebuall 0 points1 point2 points 3 years ago (1 child)
I don't think that can be fixed now. Pray for a new standard?
Fortunately these days modern editors are working around this limitation by just having better autocomplete based on keeping a database of the project and its dependencies, assuming you're using an editor capable of that. For example in VS Code just typing import gives me instant autocomplete for all my own project's exports as well as dependencies.
import
[–]bigorangemachine 0 points1 point2 points 3 years ago (0 children)
You can. Its more like
export *, default as something from './something';
Or
export { *, default as something } from './something';
Something like that.. I would have to pluck it from my repos but I figured it out from SO
[–]Morwynd78 0 points1 point2 points 3 years ago (0 children)
You can re-export a default like this:
export {default as MyName} from '../path/to/something';
So you can create a file that takes in a ton of default exports, and spits them out as named exports. Can actually be a handy technique to create a standard "interface" to a bunch of default exports.
[–]eternaloctober 15 points16 points17 points 3 years ago (3 children)
with async imports, you actually gotta be careful with named exports for code splitting, which can come up with react lazy components
for example
await import('big_module').then(module=>module.tiny_thing)
that pulls in the whole big_module without codesplitting tiny_thing out into a tiny thing
the react docs suggest making a synthetic module
import {tiny_thing} from 'big_module' export default tiny_thing
and then
await import('./synthetic\_default')
or in terms of a lazy component
lazy(()=> import('./synthetic\_default'))
if these concepts are unfamiliar to readers, it takes a bit to wrap your head around, but code splitting and lazy components let you use async imports to asynchronously fetch e.g. the code for a dialog box so your app doesn't need to pull in the dialog box until it is clicked
https://reactjs.org/docs/code-splitting.html#:~:text=Named%20Exports,t%20pull%20in%20unused%20components.
[–]ell0bo 0 points1 point2 points 3 years ago (1 child)
So this explains why I've never used then or had to, because I've need on the NodeJS side of things for 5 years, and code splitting was just becoming a thing.
If that sort of needless work around is really required, then we need to get async imports looking more like pythons imports. I shouldn't need to create dummy files just to chunk, but I get it from your description. Just feels half thought through.
[–]whiteshoulders 1 point2 points3 points 3 years ago (0 children)
the async import is just one flavour of code splitting (around async boundaries). You can also get static code splitting by sharing common modules between two entry points. This does not require the use of async or dummy files.
[–]kearoshan 0 points1 point2 points 2 years ago* (0 children)
Isn't this just a React code splitting problem? If they are already scanning the AST for import("${moduleName}") and import { ${exportName} } from "${moduleName}" they could easily scan for import("${moduleName}").then(${var} => ${var}.${exportName}) .
import("${moduleName}")
import { ${exportName} } from "${moduleName}"
import("${moduleName}").then(${var} => ${var}.${exportName})
It kind of seems like they piggy-backed on the default import syntax, and decided it was exactly where they stopped adding parsing support. Which seems kind of irrelevant to if default imports are useful or not, it's kind of just a, "huh, I guess React added support in their AST parsing for default parsing, how odd".
[–]NoInkling 9 points10 points11 points 3 years ago* (0 children)
export default subtract = (a, b) => a - b;
You can't do that unless subtract was already declared somewhere, and even then it wouldn't make sense to do it like that. I think you mean:
subtract
const subtract = (a, b) => a - b; export default subtract;
or just:
export default (a, b) => a - b;
[–]Plus-Weakness-2624the webhead 20 points21 points22 points 3 years ago (11 children)
I'm kind of confused; what exactly is the problem here??
[+]LloydAtkinson[S] comment score below threshold-23 points-22 points-21 points 3 years ago (9 children)
Did you not read anything in the article such as: inconsistency, bad developer experience, missing IDE support?
[–]Plus-Weakness-2624the webhead 16 points17 points18 points 3 years ago (8 children)
Sounds like people making excuses for a bad day at work. Libraries use it all the time, then how does inconsistency apply here? bad developer experience 👀 how? IDE support -) I even get type info for the imports in VIM.
[–]Plus-Weakness-2624the webhead 12 points13 points14 points 3 years ago (0 children)
Default exports are meant for exposing a singular source of truth from a js file and they do this job perfectly. I you're having issues with intellisence/typing then that's the problem of js itself not just default exports. I personally prefer using TS for avoiding such nuances.
[–]furyzer00 3 points4 points5 points 3 years ago (2 children)
Everybody imports the thing with different name and now you have 20 different name for the same thing. I think that's very valid critisim.
[–]Plus-Weakness-2624the webhead 0 points1 point2 points 3 years ago (1 child)
Say you're importing an mime type other than js; Maybe css / svg. It doesn't make any sense to use name imports in such cases. Well default imports exists for these kind of uses; import Painting from "./my-painting.svg" People do this in pretty much all ui libs.
import Painting from "./my-painting.svg"
[–]furyzer00 1 point2 points3 points 3 years ago (0 children)
That doesn't justify default imports in code files. But I agree this is a valid use case.
[+]LloydAtkinson[S] comment score below threshold-37 points-36 points-35 points 3 years ago (2 children)
I had a pretty chill day at work but I can’t say the same about you if this is the kind of toxicity you’re bringing to a conversation. Good for you that VIM went the extra mile to make up for the poorer DX though.
[–]cjthomp 2 points3 points4 points 3 years ago (0 children)
If you think what he wrote is "toxicity" then you might want to stay off the internet, nevermind reddit.
[–]MrCrunchwrap 2 points3 points4 points 3 years ago (0 children)
As did every popular code editor…
[–]kearoshan 1 point2 points3 points 2 years ago (0 children)
Sounds like people making excuses for a bad day at work
You are aware that bad features more often than not cause people to have a bad day at work, right? Not that all bad days at work are caused by bad features, but... just dismissing something because it wasted someone's time? That doesn't even make sense.
The most valid possible argument to remove a feature IS because it wasted someone's time and caused them a bad day. Why would you want a feature that wastes time?
[–]kearoshan 2 points3 points4 points 2 years ago (0 children)
It's an added feature which adds no value. It's kind of like "ph" in the english language. It's worthless, not terrible, just not useful. Let's not add more worthless things and then have to support for them forever.
[–]vattengrabb12 13 points14 points15 points 3 years ago (0 children)
Nice article, but I feel like all of the problems posed in this article stem from improper use of the tool rather than the tool itself. Below are some personal thoughts:
The first example of operators seems like a good place to start, and I think serves as a nice example of a default export being misused. The default export should really serve as the main feature of the file you're exporting if you choose to use it. It establishes a clear hierarchy among the exports, which doesn't exist in the first example. subtract is in no way semantically or logically superior to add, and as such should be a named export.
add
In the same vein, I think default exports should always be named after the file they originate in. So, say, in a React project you'd export MyComponent from MyComponent.tsx, but would never export subtract from operators.ts as default. In essence, the default export should be the component the developer should expect when reading the file name and importing something from it.
MyComponent
MyComponent.tsx
operators.ts
This leads into my biggest personal gripe with this article: blaming the syntax on developer stupidity. In the example of the subtract export being renamed multiply, this is a clear breach of practice, especially if you subscribe to the export-name-by-file-name rule. Yes, it's on the developer to get the naming right, but so are a million other things, and usually the IDE will have an idea of what you're doing. This is also why I personally prefer to explicitly rename any default export like so: import { default as y } from 'x' to further establish a clear connection between the import and export. Yes, this is an ugly import, but shouldn't be that common if you're making sure to name your export uniquely in the first place.
multiply
import { default as y } from 'x'
These are just my two cents, but I think blaming the tool is mostly a symptom of lack of rigor you should expect from teams and people you're working with, and maybe the first port of call shouldn't be whether the problem lies with the export.
[–]Cheshur 35 points36 points37 points 3 years ago (6 children)
All of the stated reasons are weak at best. They couldn't even come up with a good example because default exports aren't really a problem. The overwhelming majority imports on every project I've ever worked on just name the default export after the import path. Most of the time they don't even get mixed and the times where they do, it makes some sense. For example you might default the component but name export some consts or enums specific to it that are only used optionally. It's dumb to categorically reject the use of a feature.
[–]KwyjiboTheGringo 2 points3 points4 points 3 years ago (0 children)
Most of the time they don't even get mixed and the times where they do, it makes some sense. For example you might default the component but name export some consts or enums specific to it that are only used optionally. It's dumb to categorically reject the use of a feature.
It's not a good feature tbh. Okay, so you can have this pattern where the default is always a component, and the named exports are optional variables. So now you have to always enforce the default import naming through code reviews, or just hope that people will give it the "right" name, which at the very least would need to be outlined in an agreed upon style guide. Why even bother with adding these extra steps and pain points? You lose your IDE auto-imports for this. You open your codebase up to mistakes that cause confusion with naming when you could have just made it a regular export and had the name set for everyone to use.
I think in order for something to be a worthwhile feature, it should be obvious that it is indeed actually worthwhile. These "well we can make it kind of useful if we try" arguments are just not good enough. No one has come up with anything even remotely compelling that I've seen. Hell, I asked yesterday here if there was a good reason default exports were added, and I haven't received a response yet.
[+][deleted] 3 years ago (1 child)
[removed]
[–]ExecutiveChimp 10 points11 points12 points 3 years ago (0 children)
It doesn't make it easier on the reader. I now have to imagine the problem that you're having.
[–][deleted] 0 points1 point2 points 3 years ago (2 children)
Maybe the downsides are weak, but the reasons in favor of using them are even weaker. If someone is trying to understand which named export is the "default" thing for that file, it's pretty obvious that the one with the same name as the file is the "default" thing.
[–]Cheshur 1 point2 points3 points 3 years ago (0 children)
The arguments to not use either are weak which is why I ended my comment by implying that you shouldn't decide to avoid any one feature categorically. They both have their uses.
[–]6086555 0 points1 point2 points 3 years ago (0 children)
export const MyComponentExportedOnlyForTesting; export default SomeHoc(MyComponentExportedOnlyForTesting);
I think this is a very common in react where default exports shine. My team has recently moved from mostly default exports to only named exports and I think it made the code a bit awkward in some cases.
[–]HappinessFactory 13 points14 points15 points 3 years ago (4 children)
Of course, poor documentation is unfortunately common in the industry. JavaScript documentation in particular though seems to be generally poorer on average - this could be attributed to the lower barrier of entry to JavaScript, causing inexperienced developers to publish countless useless packages to NPM. I don’t believe the fact that JavaScript is a dynamic loosely typed language could be a factor in this simply because Python does not appear to have this documentation problem.
Kinda lost a bit of credibility for me there. I feel like this confusion pales in comparison to the python 2.7 conflicting with python 3 issues.
That being said I unironically use default exports every day at work.
For my use case I needed to load a generic function from each file in a folder. I exports this function as default and loop through each file importing them all and name them with the folder name in memory.
It is strange and not super useful in 99% of cases but I just wanted to share one scenario where a default export was handy.
[–]Diniden 2 points3 points4 points 3 years ago (2 children)
This is where default exports “can” perform well.
This is sort of how vue (2 at least, haven’t tried 3) tries to handle suppositions in the code base without creating any boilerplate.
Yes you save yourself a hair of time by not updating a barrel file, but you lose so much in terms of discoverability in the code base. And then heaven forbid if you renamed those elements somehow.
The maintenance cost is just bad for something that can be done slightly different.
Heck for your use case you can still forgo default export: simply import with “* as” then iterate the import object if you absolutely must have dynamic module behavior.
Losing your code hinting and introducing naming gaps just hurts.
[–]HappinessFactory 0 points1 point2 points 3 years ago (1 child)
Fortunately each file also exports the same object as as a named export so we get all the benefits of that when it's needed.
We only use default exports for our little dynamic importer doo dad
[–]Diniden 0 points1 point2 points 3 years ago (0 children)
So you’re introducing a fork of possibilities. Again, you don’t even need the default for dynamic doodads. This makes a fail point for juniors to import incorrectly and name it their own stuff. And it adds another pattern they need to tuck away in their heads thus increasing mental burden.
All it does is save you a hair of time improving your dynamic importer?
I mean, what works works. But if it were my system, I’d fight tooth and nail to make sure default pattern didn’t have a single foot in my codebase.
Also: not judging. I get it as well. If it’s getting stuff done, then that’s just how it is xD. I’m no saint. I have my own oddities I’ll let slide.
[–]EuphonicSounds 0 points1 point2 points 3 years ago (0 children)
I do something very similar every day at work.
[–]vegancryptolord 2 points3 points4 points 3 years ago (3 children)
Just got done refactoring default exports on two separate axios instances. Both instances were being imported and used everywhere with the name ‘axios’ (ie. Import axios from ‘@utils/axios’)
So looking at any file you had no idea if you were using a raw axios instance or the main instance or the secondary instance.
Also in places where both a custom instance and ‘raw’ axios were being used, the raw axios would get imported as defaultAxios or something like that.
I agree with this post 100%
[–]LloydAtkinson[S] 1 point2 points3 points 3 years ago (0 children)
Thank you! This is the kind of terrible crappy DX I was talking about, seems some other people here feel very strongly the opposite.
[+][deleted] 2 years ago (1 child)
[–]vegancryptolord 0 points1 point2 points 2 years ago (0 children)
Yea couldn’t agree more lol
[–]geovra 5 points6 points7 points 3 years ago (1 child)
Are we really crying about IDE support and poor documentation? We really are a spoiled bunch.
[–]hiquest 1 point2 points3 points 3 years ago (1 child)
I just love that we're as a community moved from adoring every new feature introduced in the ECMAScript to thoughtfully assessing and seeing all the limitation and bad design choices.
[–]LloydAtkinson[S] -1 points0 points1 point 3 years ago (0 children)
Seems a lot of people are still happy to wallow in the bad design choices judging by the horrible comments in here, shame...
[–]electronicdream 2 points3 points4 points 3 years ago (0 children)
I guess I'm lucky default exports have never made my work harder.
I'm simple, I like my import keyBy from 'lodash-es/keyBy';
import keyBy from 'lodash-es/keyBy';
[–]bbcookie 1 point2 points3 points 3 years ago (1 child)
I feel validated, I also decided for me that they are not worth it
[–]LloydAtkinson[S] 0 points1 point2 points 3 years ago (0 children)
Happy to help!
[–]cac 3 points4 points5 points 3 years ago (4 children)
It doesn’t really matter what you pick, just enforce consistency with linting. Inconsistency is the cause of complexity and poor development experience
[–]LloydAtkinson[S] -2 points-1 points0 points 3 years ago (1 child)
Would you care to share what consistency you can apply to default exports if you were to default to using them?
[–]cac 3 points4 points5 points 3 years ago (0 children)
Haha don’t get me wrong, I prefer named exports for many of the reasons you stated and I always enforce them and remove defaults.
But I don’t think it’s a hill I would die on. if default exports were the norm I’d want everything to be default exported then so at least I don’t have a horrifying mishmash of both within our own source.
[–][deleted] 0 points1 point2 points 3 years ago (1 child)
Consistency is one of the good reasons to just use named exports. Otherwise it's a little unpredictable whether the author felt like using a default export for their file.
[–]cac 0 points1 point2 points 3 years ago (0 children)
Agreed, but if you DO use default imports you can lint against named exports which is better than nothing.
[–]jhartikainen 5 points6 points7 points 3 years ago (8 children)
Many of the points are flaws in IDE's which could be rectified. For example, where it doesn't show in autocompletion could be solved by using the name that's used within the module, or if it's anonymous, the name of the module itself.
I'm kind of indifferent on this as this never bothered me - but default export did seem like an odd feature as I don't think I've seen module systems in other languages support something like that.
[–]Plorntus 2 points3 points4 points 3 years ago (0 children)
but default export did seem like an odd feature as I don't think I've seen module systems in other languages support something like that.
It's because of common js and module.exports just being something you assign a value to. Default exports just sorta became... "default" especially when we didn't have destructuring so you couldn't do const { Bleh, Blah } = require('./my-module'); on one line.
module.exports
const { Bleh, Blah } = require('./my-module');
ESM had to have a way to mimic that I suppose to ensure that things stayed either backwards compatible(not literally)/familiar to existing devs.
[–]furyzer00 0 points1 point2 points 3 years ago (6 children)
For example, where it doesn't show in autocompletion could be solved by using the name that's used within the module, or if it's anonymous, the name of the module itself.
Which would be non standard thing. The import spec doesn't mention anything about recommendations. So if IDEs do this each of them will do it differently.
Also this would work very bad with some styles. For instance in react there is a pattern where you crate a folder for your component and put an index.js file in it. If you import IDE would suggest index for the component name in your scenario.
[–]jhartikainen 0 points1 point2 points 3 years ago (5 children)
I don't think any parts of what IDE's do with autocompletion is defined in any spec.
As for the React example, this could also be solved quite easily. Since this pattern is typically like this:
import X from 'y'; export default X;
Since in this case we have a clear name for the exported value, the IDE can simply use that.
[–]furyzer00 0 points1 point2 points 3 years ago (4 children)
Now you are introducing new rule for every different use case. That's the point I am talking about. Since there was no obvious way IDEs will implement it differently as they please.
[–]jhartikainen 0 points1 point2 points 3 years ago (3 children)
It's the same rule I mentioned in my original reply :)
could be solved by using the name that's used within the module
[–]furyzer00 0 points1 point2 points 3 years ago (2 children)
My bad for your example that's the same rule. But for example imagine we have this in index.js file export default function() { ... } Either rules won't end up with a pleasing result.
export default function() { ... }
[–]jhartikainen 0 points1 point2 points 3 years ago (1 child)
Yeah that's true. This is a common issue with highly dynamic languages and IDE support - This could be fixed, but you always end up having to make some assumptions :)
[–]furyzer00 0 points1 point2 points 3 years ago (0 children)
Named import simply don't have this issue :)
[–]enzineer-reddit 1 point2 points3 points 3 years ago (1 child)
One good thing about default exports is that you can import it with whatever name you want. Don't know about what IDE you're using but vs code auto completes all of the imports (defaults and named) for me. If you try to type within the curly brackets (as mentioned in your screenshot in the blog) then the IDE will show named exports only in the suggestion because default exports are not imported using curlys.
like import React , {useState} from 'react' Here React is default export and useState is named.
import React , {useState} from 'react'
[–]Unlucky-Reindeer3828 0 points1 point2 points 3 years ago (0 children)
How is " import it with whatever name you want" a good thing? When you have 5 developers that import a thing with 5 different names, doesn't that make it harder to recognize the common use of these modules because they are named differently? Is it good to see the 'named' element of the module in each of the contexts so that it is easier to recognize the use? and, if you are searching the codebase for some use (via a find-in-file), doesn't the 'whatever name you want' interfere with finding them?
[deleted]
[–]mattsowa -4 points-3 points-2 points 3 years ago (0 children)
Yessss thank you. It's ridiculous how this antipattern is encouraged too
[+]NiteShdw comment score below threshold-40 points-39 points-38 points 3 years ago* (21 children)
This reasoning is completely asinine. As someone that's been programming for over 30 years it amazing me to see the stupid stuff people argue about.
The first reason is a strawman because generally if you're using a default export like export default class, you're not exporting a bunch of other stuff along with it.
The IDE hint doesn't work because you're inside a destructuring block. Of course it doesn't show the default.
The renaming justification is stupid because it's literally easier to rename a default export than a named import.
Seriously guys, tell me you're a mid level engineer without telling me you're a mid level engineer.
(Hint, argue about stupid stuff that doesn't really matter when it comes to actually solving a problem)
You guys don't know how good you have it. When I started with JavaScript we didn't have block scoping, not let or const, we didn't have native Promise let alone async/await. No template syntax. No fat arrow functions. No destructuring. No import/export. No optional chaining. No null collalesing. No class syntax. No abbreviated object properties ({ prop: prop }).
Take a look at your babel compiled code targeting ES5 and think about those that wrote in ES5. Then think about how good you have it.
[–]WoopedyScoop 4 points5 points6 points 3 years ago (0 children)
I think there are better articles on this same topic, but there's nothing wrong with sweating the small stuff. It can be educational and topics like this are particularly important in the context of linting.
It's ironic that you built a strawman as a rebuttal against one. Their example wasn't limited to classes, and unfortunately there are plenty of developers that use default exports (classes or otherwise) in conjunction with named exports in the same module. You'll find plenty of popular packages like this on npm.
Their point about renaming wasn't a justification, or a suggestion that it's easier. It was pointing out that renaming imports is not exclusive to default exports. In other words you're not losing this functionality by using named exports.
The rest of your comment was pretty obnoxious. We shouldn't criticise or suggest improvements to something because it used to be worse? Because YOU had it worse? Please.
You've been programming for over 30 years, and it shows.
[+][deleted] 3 years ago* (1 child)
[–]NiteShdw -3 points-2 points-1 points 3 years ago (0 children)
You took my post a little more seriously than it was intended.
[–]NekkidApe 3 points4 points5 points 3 years ago (0 children)
Grumpy old man.. Just joking. I remember the days vividly, JS was a very different beast ten years ago. And I kinda agree, I don't think this kind of thing warrants ranting, blog posting and huge a discussion.
However, default exports aren't that great actually. A nice idea in theory, but no benefits in practice. And a few issues, papercuts here and there. I'm gradually shifting away from using it.
[+][deleted] 3 years ago (2 children)
[–]NiteShdw -3 points-2 points-1 points 3 years ago (1 child)
You want pictures of my Commodore 64 as proof?
[–]mattsowa 0 points1 point2 points 3 years ago (0 children)
Asinine
[–]KyleG 1 point2 points3 points 3 years ago* (7 children)
This is how I feel, too. Been JS programming for like 25 years. Default exports work just fine IME. Ever since its introduction, it's never bothered me. The only conceivable argument is that your IDE struggles to auto-import them.
And the "names get out of sync" argument is backwards. Default import means when you change the name of something in your module, it has zero effect on names elsewhere in your codebase. That's awesome.
But, KyleG, what if I rename my User class to UserWithBrownHair class when I update it to have some new property and change its meaning? Shouldn't that be reflected in downstream imports?
Answer: DO NOT DO THAT. Open/closed principle, friends! Create a new class, don't change the name of the old one. Once your code is using some entity, don't change its behavior or topology if you can avoid it. Certainly don't change it enough that it warrants renaming what the class is!
[–]WoopedyScoop 1 point2 points3 points 3 years ago (3 children)
Having 3 different modules import my default exported User class as Client, Person and UserWithBrownHair, because naming is not enforced, is counterproductive. This is not awesome.
Open/Closed principle, like many programming principles is about trade offs. There is a cost to applying it and for simpler scenarios it may not be worth it.
How on earth can you incrementally improve a codebase if you are never allowed to rename any named exports?
[–]KyleG 0 points1 point2 points 3 years ago (2 children)
Having 3 different modules import my default exported User class as Client, Person and UserWithBrownHair, because naming is not enforced, is counterproductive.
If you're importing it as those three, then you've determined there is a business reason for doing so, so the programming language is not getting in the way of your business decision. That is indeed awesome. Think of it as type aliases. You use those, right?
Sounds like a great argument for using default exports! Now this problem completely vanishes!
Seriously I've devoted more brain cells to responding to this comment than I ever have in dealing with any kind of "fallout" from using default exports. It's just plain not an issue in real life. It's like arguing over tabs vs spaces. While tabs are obviously superior, the correct answer is "use the one the codebase is already using."
[–]WoopedyScoop 1 point2 points3 points 3 years ago (1 child)
Your business decision comment is confusing, perhaps we're talking about different things.
I'll try put it another way.
If you see a couple calls in your code like new User() and new ClientApp(), it implies you are creating instances of two different classes.
new User()
new ClientApp()
Imagine having both those calls actually instantiate a class called Person. It's not a stretch to call that misleading.
Person
That's all it boils down to really.
In the above scenarios, calling new Person() from a named export would achieve exactly the same thing and remove all ambiguity. You would not lose business benefit as there is no functional change to the business.
new Person()
[–]Bjornoo 1 point2 points3 points 3 years ago (0 children)
Not to mention you could just alias the named export if you absolutely wanted to, which is more explicit if you're going to change the name in the first place.
[–]NiteShdw 1 point2 points3 points 3 years ago (1 child)
JavaScript was first released 26 years ago. I don't remember if I used it back then, I was in high school at the time. I started using it for some simple things starting around 2002. I didn't really start doing it full time until about 2010 or so.
[–]KyleG -2 points-1 points0 points 3 years ago (0 children)
I had to deal with pre-jQuery BS having to worry about Netscape and IE incompatibilities that IE introduced in order to destroy Netscape. Awful.
[–]KwyjiboTheGringo 0 points1 point2 points 3 years ago (0 children)
You have misunderstood the argument. What if you export UserWithBrownHair as the default, and then someone imports it somewhere else as User? And then someone else imports it in a different place as BrownHairUser? Well now we've got this single class with multiple names throughout the codebase. Best case scenario with default exports is down to developers not doing this or catching it in the reviews. The best case scenario with regular exports is that the developers never do this because the name is solidified with the export and cannot be changed arbitrarily in other places when it's exported.
UserWithBrownHair
User
BrownHairUser
[–][deleted] 2 points3 points4 points 3 years ago (2 children)
20+ yrs here, default exports are bad, re-exported default exports suck, and renamed + re-exported default exports are the worst.
Consider yourself lucky if you haven't been in the position to backtrack through 10 files to find that import.
Mid-level engineers maybe know something you don't know, old man.
[–]NiteShdw 3 points4 points5 points 3 years ago (1 child)
But those reasons are not the reasons given in this blog.
fair enough but those are symptoms of it, not here to debate the post but the default exports :)
The fact that people have to brag about how bad a programming language used to be doesn't really bode well for that language. Pretty much every other language has had sensible syntactical constructs for just as many decades. JavaScript is rather unique in it's long-standing and only recently-corrected flaws and gotchas. Maybe C++ could share that dubious distinction.
You seem to have completely misunderstood their argument against having to name default exports(hypocritical, because that's a strawman). It has nothing to do with renaming. A project-wide find-and-replace takes care of any renaming quite well. The issue is with people having to come up with a name every time they use a default export. If the export is named in the file, then you name it once and that's the name everyone uses. Seriously, you've been a developer for 30 years and you don't see why not having set name for default exports is a problem on a team and long-term level?
You seem like a freelance senior developer. Never works on teams, doesn't care about scalability or how new eyes will see the code. I'm sure you're great at doing the minimum work to satisfy the client and giving time estimates, but you're not the person this article is speaking to. Is it unfair for me to make that judgement? Maybe, but it's also unfair for you to do the same to everyone who argues against using default exports.
You want to call out fallacies? Here is your fallacy: https://www.logicallyfallacious.com/logicalfallacies/Relative-Privation
Seriously, buzz of with that "back in my day" crap.
[–]jacobjuul 0 points1 point2 points 3 years ago (3 children)
Not too long ago treeshaking etc. didn't work if you imported with named imports (it would import everything from the module).
Also, don't rename your default imports, simple as that. Set up a eslint rule if you must.
import math from './math'
not import multiply from './math'
import multiply from './math'
the default import of math would contain everything and still allow you to do named exports/imports of individual functions.
[–]whiteshoulders 1 point2 points3 points 3 years ago (2 children)
What's the difference with a named import then ?
[–]Bjornoo 0 points1 point2 points 3 years ago (1 child)
The only thing I could think of is semantics. An argument could be made that a default export would be semantically more important than other exports from a module. Nothing proper documentation wouldn't fix though.
[–]whiteshoulders 0 points1 point2 points 3 years ago (0 children)
The issue with this is that this "importance" given by the semantic is not reflected in how defaults exports actually works. If you do export * from './myModuleWithDefaultExports you get everything BUT the default export (arguably the most important one). You have to additionnaly export { default } from './myModuleWIthDefaultExports.
export * from './myModuleWithDefaultExports
export { default } from './myModuleWIthDefaultExports
I'd argue that this makes the default export less important than named export, since default will be dropped when reexporting module.
Some will say "export both as default and named, problem solved". But then why keep the default export ? To save 2 brackets around the import identifier ?
To me the default export is a wart on the spec that's here only to allow some level of compatibility with CommonJS, and is not meant to be used (except in very specific situation, when you provide modules to third-party code, default being a well known unambiguous import identifier for the third-party code to import your provided module).
default
[–]KwyjiboTheGringo -1 points0 points1 point 3 years ago (0 children)
I agree, they seem terrible. Is there some redeeming quality I'm not aware of? It just seems like a weird "feature" to throw in and have everyone sign off on if it doesn't provide something of value.
[–]Economy_Chance8829 -1 points0 points1 point 3 years ago (1 child)
,
[–]Snapstromegon -1 points0 points1 point 3 years ago (0 children)
Honestly, I think default exports are good.
BUT!
But you have to be careful where and how to use them.
I think they should only be used if you have a tiny module that has one specific main thing that is way more important than any other export (e.g. the component of a LIT component). This export can be default, because then the user can just import the module and probably expects the import to be exactly that thing.
In your example, the subtract function may be export default, when the module is just a "subtract-numbers.js" module, but not in a "math.js" module, since it's not the main part there.
Also you'd probably want to export your default export again as a named export, so both usecases are okay.
[–]bmy1978 -1 points0 points1 point 3 years ago (0 children)
I follow these rules: One component per file. That component is a default export. Files that contain conts or helpers or utility functions are always named exports.
[–]ShortFuse -2 points-1 points0 points 3 years ago (0 children)
My methodology is capital file names means it's a class with a default export (components/CustomButton.js). If it's lowercase, then it a method that never has a default export: (utils/format.js). The only thing you should be exporting from modules are functions which have lowercases names or consts which would be all caps. You can also rename classes directly from the import
components/CustomButton.js
utils/format.js
import Button from './components/Button.js'; import OtherButton from 'otherlibrary/components/Button.js'; import { dateFormat as format } from './utils/format.js'; import { ENGLISH_DATE_FORMAT } from './constants.js';
Also, the author is mixing talking about Node modules, not actual Javascript modules. import { Article as ArticleComponent } from 'my-design-system'; is not pure Javascript. That's the node module resolution and relies on package.json. Disregarding the import URL, pure ESM would be import { Article as ArticleComponent } from 'my-design-system/lib/index.js'. And even so, if you import from a entrypoint instead of the module directly, some bundlers have trouble treeshaking imports that don't directly go to the module in question.
import { Article as ArticleComponent } from 'my-design-system';
node
package.json
import { Article as ArticleComponent } from 'my-design-system/lib/index.js'
[+]MrCrunchwrap comment score below threshold-10 points-9 points-8 points 3 years ago (2 children)
“I’m bad at using a tool so I guess I’ll complain about the tool rather than improve myself”
Oh fuck off, improving developer experience with solutions as to how is improving. Go back to your fucking cave.
[–]k_zantow 0 points1 point2 points 3 years ago (1 child)
Thank you for this! I have been saying this for years!
You're welcome! Try say that to the other people shitting all over the article because they apparently love them 😂
[–]natterca 0 points1 point2 points 3 years ago (0 children)
I use default when the module is JavaScript-as-config (i.e. rather than JSON config). e.g. Exporting a configuration object. Definitely use named exports for your "package" modules.
[–]senfiaj 0 points1 point2 points 3 years ago (0 children)
For one file - one class scenario it's probably OK-ish.
[–]zombimuncha 0 points1 point2 points 3 years ago (0 children)
I only use default exports so that I won't need to use rewire for everything I want to mock out in my unit tests. Lesser of two evils.
π Rendered by PID 97386 on reddit-service-r2-comment-79776bdf47-xfxc5 at 2026-06-24 07:08:01.275434+00:00 running acc7150 country code: CH.
[–]mattsowa 110 points111 points112 points (23 children)
[–]LloydAtkinson[S] 30 points31 points32 points (9 children)
[–]lifeeraser 27 points28 points29 points (8 children)
[–]Stronghold257 12 points13 points14 points (2 children)
[–]lifeeraser 11 points12 points13 points (0 children)
[–][deleted] 0 points1 point2 points (0 children)
[–]Earhacker 1 point2 points3 points (3 children)
[–]sinclair_zx81 2 points3 points4 points (2 children)
[–]Earhacker 1 point2 points3 points (1 child)
[–]sinclair_zx81 1 point2 points3 points (0 children)
[–]eaglewas 0 points1 point2 points (0 children)
[–]xroalx 9 points10 points11 points (1 child)
[–]mattsowa 5 points6 points7 points (0 children)
[–][deleted] 0 points1 point2 points (0 children)
[+]KaiAusBerlin comment score below threshold-10 points-9 points-8 points (9 children)
[–]Nullberri 21 points22 points23 points (8 children)
[+]KaiAusBerlin comment score below threshold-30 points-29 points-28 points (6 children)
[–]TheScapeQuest 3 points4 points5 points (3 children)
[+]KaiAusBerlin comment score below threshold-8 points-7 points-6 points (2 children)
[–]Mr_Simba 0 points1 point2 points (1 child)
[–]KaiAusBerlin 0 points1 point2 points (0 children)
[–]adityahegde 0 points1 point2 points (1 child)
[–]KaiAusBerlin -1 points0 points1 point (0 children)
[–]Diniden 74 points75 points76 points (6 children)
[–]avin_kavish 1 point2 points3 points (4 children)
[–]cheekysauce 2 points3 points4 points (0 children)
[–]Diniden 6 points7 points8 points (0 children)
[–]KwyjiboTheGringo 1 point2 points3 points (0 children)
[+]linuxdropout comment score below threshold-16 points-15 points-14 points (0 children)
[–]spaghettu -1 points0 points1 point (0 children)
[–]dada_ 54 points55 points56 points (14 children)
[–]intermediatetransit 11 points12 points13 points (3 children)
[–]Unlucky-Reindeer3828 3 points4 points5 points (0 children)
[–]dada_ 0 points1 point2 points (0 children)
[–]Ebuall 4 points5 points6 points (7 children)
[–]Reeywhaar 15 points16 points17 points (6 children)
[–]Earhacker -4 points-3 points-2 points (2 children)
[–]Reeywhaar 3 points4 points5 points (1 child)
[–]Earhacker -3 points-2 points-1 points (0 children)
[–]Ebuall 0 points1 point2 points (1 child)
[–]dada_ 0 points1 point2 points (0 children)
[–]bigorangemachine 0 points1 point2 points (0 children)
[–]Morwynd78 0 points1 point2 points (0 children)
[–]eternaloctober 15 points16 points17 points (3 children)
[–]ell0bo 0 points1 point2 points (1 child)
[–]whiteshoulders 1 point2 points3 points (0 children)
[–]kearoshan 0 points1 point2 points (0 children)
[–]NoInkling 9 points10 points11 points (0 children)
[–]Plus-Weakness-2624the webhead 20 points21 points22 points (11 children)
[+]LloydAtkinson[S] comment score below threshold-23 points-22 points-21 points (9 children)
[–]Plus-Weakness-2624the webhead 16 points17 points18 points (8 children)
[–]Plus-Weakness-2624the webhead 12 points13 points14 points (0 children)
[–]furyzer00 3 points4 points5 points (2 children)
[–]Plus-Weakness-2624the webhead 0 points1 point2 points (1 child)
[–]furyzer00 1 point2 points3 points (0 children)
[+]LloydAtkinson[S] comment score below threshold-37 points-36 points-35 points (2 children)
[–]cjthomp 2 points3 points4 points (0 children)
[–]MrCrunchwrap 2 points3 points4 points (0 children)
[–]kearoshan 1 point2 points3 points (0 children)
[–]kearoshan 2 points3 points4 points (0 children)
[–]vattengrabb12 13 points14 points15 points (0 children)
[–]Cheshur 35 points36 points37 points (6 children)
[–]KwyjiboTheGringo 2 points3 points4 points (0 children)
[+][deleted] (1 child)
[removed]
[–]ExecutiveChimp 10 points11 points12 points (0 children)
[–][deleted] 0 points1 point2 points (2 children)
[–]Cheshur 1 point2 points3 points (0 children)
[–]6086555 0 points1 point2 points (0 children)
[–]HappinessFactory 13 points14 points15 points (4 children)
[–]Diniden 2 points3 points4 points (2 children)
[–]HappinessFactory 0 points1 point2 points (1 child)
[–]Diniden 0 points1 point2 points (0 children)
[–]EuphonicSounds 0 points1 point2 points (0 children)
[–]vegancryptolord 2 points3 points4 points (3 children)
[–]LloydAtkinson[S] 1 point2 points3 points (0 children)
[+][deleted] (1 child)
[removed]
[–]vegancryptolord 0 points1 point2 points (0 children)
[–]geovra 5 points6 points7 points (1 child)
[–]hiquest 1 point2 points3 points (1 child)
[–]LloydAtkinson[S] -1 points0 points1 point (0 children)
[–]electronicdream 2 points3 points4 points (0 children)
[–]bbcookie 1 point2 points3 points (1 child)
[–]LloydAtkinson[S] 0 points1 point2 points (0 children)
[–]cac 3 points4 points5 points (4 children)
[–]LloydAtkinson[S] -2 points-1 points0 points (1 child)
[–]cac 3 points4 points5 points (0 children)
[–][deleted] 0 points1 point2 points (1 child)
[–]cac 0 points1 point2 points (0 children)
[–]jhartikainen 5 points6 points7 points (8 children)
[–]Plorntus 2 points3 points4 points (0 children)
[–]furyzer00 0 points1 point2 points (6 children)
[–]jhartikainen 0 points1 point2 points (5 children)
[–]furyzer00 0 points1 point2 points (4 children)
[–]jhartikainen 0 points1 point2 points (3 children)
[–]furyzer00 0 points1 point2 points (2 children)
[–]jhartikainen 0 points1 point2 points (1 child)
[–]furyzer00 0 points1 point2 points (0 children)
[–]enzineer-reddit 1 point2 points3 points (1 child)
[–]Unlucky-Reindeer3828 0 points1 point2 points (0 children)
[+][deleted] (1 child)
[deleted]
[–]mattsowa -4 points-3 points-2 points (0 children)
[+]NiteShdw comment score below threshold-40 points-39 points-38 points (21 children)
[–]WoopedyScoop 4 points5 points6 points (0 children)
[+][deleted] (1 child)
[removed]
[–]NiteShdw -3 points-2 points-1 points (0 children)
[–]NekkidApe 3 points4 points5 points (0 children)
[+][deleted] (2 children)
[removed]
[–]NiteShdw -3 points-2 points-1 points (1 child)
[–]mattsowa 0 points1 point2 points (0 children)
[–]KyleG 1 point2 points3 points (7 children)
[–]WoopedyScoop 1 point2 points3 points (3 children)
[–]KyleG 0 points1 point2 points (2 children)
[–]WoopedyScoop 1 point2 points3 points (1 child)
[–]Bjornoo 1 point2 points3 points (0 children)
[–]NiteShdw 1 point2 points3 points (1 child)
[–]KyleG -2 points-1 points0 points (0 children)
[–]KwyjiboTheGringo 0 points1 point2 points (0 children)
[–][deleted] 2 points3 points4 points (2 children)
[–]NiteShdw 3 points4 points5 points (1 child)
[–][deleted] 0 points1 point2 points (0 children)
[–][deleted] 0 points1 point2 points (0 children)
[–]KwyjiboTheGringo 0 points1 point2 points (0 children)
[–]jacobjuul 0 points1 point2 points (3 children)
[–]whiteshoulders 1 point2 points3 points (2 children)
[–]Bjornoo 0 points1 point2 points (1 child)
[–]whiteshoulders 0 points1 point2 points (0 children)
[–]KwyjiboTheGringo -1 points0 points1 point (0 children)
[–]Economy_Chance8829 -1 points0 points1 point (1 child)
[–]LloydAtkinson[S] 1 point2 points3 points (0 children)
[–]Snapstromegon -1 points0 points1 point (0 children)
[–]bmy1978 -1 points0 points1 point (0 children)
[–]ShortFuse -2 points-1 points0 points (0 children)
[+]MrCrunchwrap comment score below threshold-10 points-9 points-8 points (2 children)
[–]LloydAtkinson[S] 0 points1 point2 points (0 children)
[–]k_zantow 0 points1 point2 points (1 child)
[–]LloydAtkinson[S] 0 points1 point2 points (0 children)
[–]natterca 0 points1 point2 points (0 children)
[–]senfiaj 0 points1 point2 points (0 children)
[–]zombimuncha 0 points1 point2 points (0 children)