Common ES6+ Mistakes
This lesson explains Common ES6+ Mistakes with clear examples, use cases, and best practices so you can use modern JavaScript confidently in real projects.
Common ES6 Mistakes
ES6 introduced many powerful features that make JavaScript cleaner, safer, and easier to maintain. However, developers often misuse these features, leading to bugs, performance issues, memory leaks, and unexpected behavior. This guide covers the most common ES6 mistakes grouped by category along with the correct approach.
1. Variables (let, const, var)
- Using
varinstead ofletorconst. - Using
letwhen the value never changes. - Redeclaring variables in the same scope.
- Accessing variables before declaration (Temporal Dead Zone).
- Expecting
varto be block scoped. - Creating accidental global variables.
- Reassigning constants.
- Declaring variables too early instead of near usage.
// Wrong
var total = 10;
// Better
const total = 10; 2. Block Scope
- Trying to access
letoutside its block. - Using loop variables after the loop.
- Assuming nested blocks share variables.
- Using
varinside loops. - Ignoring block scope inside switch statements.
3. Arrow Functions
- Using arrow functions as object methods.
- Expecting arrow functions to have their own
this. - Using arrow functions as constructors.
- Forgetting implicit return rules.
- Returning object literals without parentheses.
- Using arrows everywhere even when regular functions are clearer.
- Using arrows for DOM event handlers without understanding lexical
this. - Using arrows in prototypes unnecessarily.
// Wrong
const user =
{
name: "John",
greet: () => {
console.log(this.name);
}
}; 4. Template Literals
- Using string concatenation instead of interpolation.
- Mixing quotes and backticks.
- Creating unreadable multi-line templates.
- Embedding complex logic inside template strings.
- Not escaping backticks when needed.
5. Destructuring
- Destructuring undefined objects.
- Using incorrect property names.
- Ignoring default values.
- Overusing nested destructuring.
- Confusing array and object destructuring.
- Mutating destructured values expecting originals to update.
// May fail
const { name } =
undefined; 6. Spread Operator
- Thinking spread performs deep copies.
- Using spread on non-iterables.
- Overusing spread inside loops.
- Accidentally overwriting object properties.
- Copying huge arrays repeatedly.
7. Rest Parameters
- Using rest anywhere except the last parameter.
- Confusing rest with spread.
- Using
argumentsin arrow functions. - Passing arrays instead of individual values.
8. Default Parameters
- Passing null expecting the default value.
- Using mutable default objects.
- Using expensive function calls as defaults.
- Ignoring parameter order.
9. Classes
- Forgetting
new. - Using classes for simple objects.
- Deep inheritance chains.
- Not calling
super(). - Confusing static and instance methods.
- Accessing private fields directly.
- Forgetting method binding.
- Putting unrelated logic inside one class.
10. Modules
- Mixing CommonJS with ES Modules.
- Incorrect default import syntax.
- Circular dependencies.
- Using relative paths incorrectly.
- Exporting too many unrelated items.
- Importing entire libraries unnecessarily.
11. Promises
- Forgetting to return promises.
- Ignoring rejected promises.
- Nesting multiple then blocks.
- Mixing callbacks and promises.
- Creating unnecessary promises.
- Ignoring finally.
- Promise constructor anti-pattern.
- Unhandled promise rejections.
12. Async Await
- Forgetting
await. - Using await inside non-async functions.
- Awaiting independent operations sequentially.
- Ignoring try/catch.
- Blocking loops with await.
- Using await unnecessarily.
- Not using Promise.all() for parallel requests.
- Ignoring timeout handling.
13. Arrays
- Using map without returning values.
- Using map instead of forEach.
- Using filter instead of find.
- Mutating arrays accidentally.
- Ignoring immutable updates.
- Using reduce for simple loops.
- Forgetting includes exists.
- Using sort without comparator.
14. Objects
- Mutating shared objects.
- Using == instead of ===.
- Copying nested objects incorrectly.
- Forgetting Object.freeze for constants.
- Using objects where Map is better.
- Confusing property references.
15. Map and Set
- Using objects instead of Map.
- Using arrays instead of Set.
- Expecting Set to sort values.
- Using object keys incorrectly.
- Ignoring Map iteration methods.
16. BigInt
- Mixing Number and BigInt.
- Expecting decimal support.
- Using Math functions with BigInt.
- JSON serialization errors.
- Using BigInt unnecessarily.
17. Optional Chaining
- Using optional chaining everywhere.
- Ignoring actual programming errors.
- Using it on required properties.
- Confusing null with undefined.
18. Nullish Coalescing
- Confusing
??with||. - Replacing valid zero values.
- Ignoring null and undefined differences.
- Combining operators incorrectly.
19. Iteration
- Using for...in on arrays.
- Using forEach with async.
- Using await inside forEach.
- Ignoring iterator protocols.
- Creating unnecessary loops.
20. Browser Compatibility
- Ignoring browser support.
- Skipping Babel.
- Missing polyfills.
- Ignoring older mobile browsers.
- Testing only in Chrome.
21. Performance Mistakes
- Creating unnecessary object copies.
- Using spread inside large loops.
- Creating functions inside render loops.
- Ignoring lazy loading.
- Deep cloning large objects repeatedly.
- Using async where synchronous code is sufficient.
- Overusing classes.
- Creating unnecessary promises.
22. Interview Mistakes
- Saying classes replace prototypes.
- Confusing spread and rest.
- Confusing == and ===.
- Not knowing lexical this.
- Not understanding closures.
- Ignoring Promise lifecycle.
- Not understanding async execution.
- Memorizing syntax without understanding behavior.
23. Production Code Mistakes
- Missing error handling.
- Not validating API responses.
- Mutating application state.
- Using global variables.
- Ignoring linting rules.
- Ignoring accessibility.
- Skipping unit tests.
- Skipping code reviews.
24. Security Mistakes
- Using eval().
- Trusting user input.
- Ignoring XSS protection.
- Using innerHTML carelessly.
- Hardcoding secrets.
- Ignoring CSP policies.
- Exposing API keys.
- Ignoring HTTPS.
25. ES6 Mistake Prevention Checklist
- Prefer
constwhenever possible. - Use
letonly for mutable values. - Avoid
var. - Use arrow functions appropriately.
- Use destructuring carefully.
- Handle Promise errors.
- Use async/await with try/catch.
- Prefer immutable updates.
- Use modules.
- Write small reusable functions.
- Keep classes focused.
- Test across browsers.
- Use ESLint and Prettier.
- Write unit tests.
- Review performance regularly.
Interview Tip
Senior JavaScript interviews rarely focus on ES6 syntax alone. They often ask about the mistakes developers make with ES6 features and how to avoid them. Understanding these pitfalls demonstrates practical, production-level JavaScript experience.