Building Your Learning Module...
Getting things ready for you!
Find videos you like?
Save to resource drawer for future reference!
Error handling prevents your application from crashing when something goes wrong. Use try-catch-finally to gracefully handle errors and provide fallbacks!
// App crashes on error
function parseJSON(jsonString) {
const data = JSON.parse(jsonString);
return data;
}
// If invalid JSON, app crashes! 💥
parseJSON('invalid json');
// Uncaught SyntaxError
// Nothing after error executes
console.log('This never runs');// App continues even if error occurs
function parseJSON(jsonString) {
try {
const data = JSON.parse(jsonString);
return data;
} catch (error) {
console.error('Invalid JSON:', error.message);
return null; // Fallback
}
}
// Handles error gracefully
const result = parseJSON('invalid json');
// Logs: Invalid JSON: ...
console.log(result); // null
// Code continues to execute
console.log('App still running!');Complete error handling flow
// Base Error class
class ValidationError extends Error {
constructor(message) {
super(message);
this.name = 'ValidationError';
}
}
class NetworkError extends Error {
constructor(message, statusCode) {
super(message);
this.name = 'NetworkError';
this.statusCode = statusCode;
}
}
class AuthenticationError extends Error {
constructor(message) {
super(message);
this.name = 'AuthenticationError';
}
}
// Usage
function validateAge(age) {
if (typeof age !== 'number') {
throw new ValidationError('Age must be a number');
}
if (age < 0 || age > 120) {
throw new ValidationError('Age must be between 0 and 120');
}
return true;
}
// Handling specific errors
try {
validateAge('twenty');
} catch (error) {
if (error instanceof ValidationError) {
console.log('Validation failed:', error.message);
} else if (error instanceof NetworkError) {
console.log('Network issue:', error.statusCode);
} else {
console.log('Unknown error:', error);
}
}When and how to throw errors
// Using .catch()
fetch('/api/data')
.then(res => res.json())
.then(data => {
console.log(data);
})
.catch(error => {
console.error('Failed:', error);
})
.finally(() => {
console.log('Request completed');
});
// Multiple catches
Promise.resolve()
.then(() => {
throw new Error('Step 1 failed');
})
.catch(error => {
console.log('Caught:', error.message);
return 'recovered';
})
.then(result => {
console.log(result); // 'recovered'
});// Using try-catch with async/await
async function fetchData() {
try {
const response = await fetch('/api/data');
const data = await response.json();
console.log(data);
} catch (error) {
console.error('Failed:', error);
} finally {
console.log('Request completed');
}
}
// Multiple async operations
async function processUser(id) {
try {
const user = await fetchUser(id);
const profile = await fetchProfile(user.id);
const posts = await fetchPosts(user.id);
return { user, profile, posts };
} catch (error) {
console.error('Error:', error);
return null;
}
}Handle errors in parallel operations
// Good - descriptive
throw new Error('User with ID 123 not found');
// Bad - vague
throw new Error('Error');try {
await riskyOperation();
} catch (error) {
console.error('Operation failed:', {
message: error.message,
stack: error.stack,
timestamp: new Date(),
userId: currentUser.id
});
}function getConfig() {
try {
return JSON.parse(localStorage.getItem('config'));
} catch (error) {
console.warn('Using default config');
return DEFAULT_CONFIG; // Fallback
}
}// Bad - swallows errors
try {
importantOperation();
} catch (error) {
// Nothing - error disappears!
}
// Good - log or handle
try {
importantOperation();
} catch (error) {
console.error('Failed:', error);
notifyUser('Operation failed');
}// Bad - pointless catch
try {
operation();
} catch (error) {
throw error; // Why catch at all?
}
// Good - add context
try {
operation();
} catch (error) {
throw new Error(`Operation failed: ${error.message}`);
}Try: risky code
Catch: handle errors
Finally: cleanup (always runs)
Extend Error class
Create meaningful error types
Add context and properties
Use try-catch with async/await
Use .catch() with promises
Promise.allSettled for multiple calls
Specific error messages
Log errors properly
Provide fallbacks, never silent failures