BiTree
  • Search For Lessons
  • Curriculum
  • Pricing
  • For Educators
  • Become a Tutor
  • About
  • Contact
Log InGet Started

Questions, concerns, bug reports, or suggestions? We read every message, write to us at [email protected].

More ways to reach us →
BiTree

Live coding lessons for aspiring developers and security professionals.

[email protected]

(201) 785-7951

Mon–Fri, 9 AM–5 PM EST

Learn

  • Search For Lessons
  • Curriculum
  • Pricing

Company

  • About
  • For Educators & Schools
  • Become a Tutor
  • Contact Us

Legal

  • Terms of Service
  • Privacy Policy
© 2026 BiTree. All rights reserved.
Curriculum/Web Development/JavaScript Fundamentals
50 minBeginner

JavaScript Fundamentals

After this lesson, you will be able to: Write JavaScript that uses variables, functions, conditionals, and loops to solve small problems in the browser.

JavaScript adds behavior to a webpage. The core language has a lot in common with Python, variables, functions, conditionals, loops, but with different syntax and a few quirks. This lesson focuses on the core language; next lesson we'll connect it to actual webpages.

Prerequisites:CSS Fundamentals

Variables, let, const, and (almost never) var

Use const by default. Use let only when you need to reassign. Don't use var.

tsx
const name = "Alex"; // can't be reassigned
let score = 0; // can be reassigned
score = score + 10;
// Types are inferred, no need to declare them
const age = 17; // number
const isStudent = true; // boolean
const hobbies = ["code"]; // array

Functions, three ways to write them

Modern code uses arrow functions for short callbacks and named functions for everything else.

tsx
// Named function declaration
function greet(name) {
return "Hello, " + name;
}
// Arrow function (short, modern)
const greet2 = (name) => "Hello, " + name;
// Multi-line arrow function
const calcTotal = (price, taxRate = 0.08) => {
const tax = price * taxRate;
return price + tax;
};

Conditionals and loops

Same idea as Python, different syntax. Note the curly braces and parentheses.

tsx
const score = 87;
let grade;
if (score >= 90) {
grade = "A";
} else if (score >= 80) {
grade = "B";
} else {
grade = "C or below";
}
// Loop through an array
const names = ["Alex", "Jordan", "Sam"];
for (const name of names) {
console.log(name);
}
// Or with .forEach
names.forEach((name) => console.log(name));

ℹ️ Tip, open the browser console

Press F12 (or Cmd+Option+I on Mac) and click the Console tab. console.log() prints there. You can even type and run JavaScript directly in the console, great for quick experiments.

Working with strings

Template literals (backticks) are the modern way to build strings.

tsx
const name = "Alex";
const age = 17;
// Old way, concatenation
const msg1 = "Hi " + name + ", you are " + age;
// New way, template literals
const msg2 = `Hi ${name}, you are ${age}`;
// String methods
console.log(name.toUpperCase()); // "ALEX"
console.log(name.length); // 4
console.log(" hi ".trim()); // "hi"

Modern JavaScript essentials

The next five features arrived in ES2015 onward and are now the standard syntax every team uses in 2025. Skipping them is what makes code feel dated. The code block below shows them all with real comments. You won't memorize these on first read; what matters is recognizing the pattern when you see it.

Destructuring, spread/rest, optional chaining, nullish coalescing

Each pattern below replaces a longer, older form. Read the comments first, then run it mentally before moving on.

tsx
// Destructuring: pull values out of objects/arrays by name/position
const user = { name: "Alex", age: 17, role: "student" };
const { name, role } = user;
console.log(name, role); // "Alex" "student"
const nums = [10, 20, 30];
const [first, second] = nums;
console.log(first, second); // 10 20
// Spread (...): copy or expand iterables
const extra = [40, 50];
const combined = [...nums, ...extra]; // [10, 20, 30, 40, 50]
const clone = { ...user, role: "tutor" }; // overrides role on the copy
// Rest (...): collect remaining args into an array
function sum(...values) {
return values.reduce((acc, n) => acc + n, 0);
}
console.log(sum(1, 2, 3, 4)); // 10
// Optional chaining (?.): safely read nested properties
const maybeUser = null;
console.log(maybeUser?.name); // undefined (no crash)
console.log(user?.address?.city); // undefined (no crash)
// Nullish coalescing (??): fall back ONLY when value is null/undefined
const input = "";
const label1 = input || "Anonymous"; // "Anonymous" (empty string is falsy!)
const label2 = input ?? "Anonymous"; // "" (empty string is allowed)

💡 Why ?? often beats || for defaults

`||` falls back on any falsy value: `0`, `""`, `false`, `null`, `undefined`. That bites you when `0` or `""` is a valid input (e.g. quantity 0, an empty search query). `??` falls back only on `null`/`undefined`, which is almost always what you actually want for default values. Reach for `??` first; use `||` only when you genuinely want every falsy value to fall back.

Async code: promises and async/await

Most real JavaScript work is asynchronous — fetching data, reading a file, waiting for a click. The modern pattern is `async`/`await` (not the older `.then()` chains). You'll learn fetch properly in the APIs lesson; this is the preview.

tsx
// async function = always returns a Promise
async function loadUser(id) {
// await pauses inside the async function until the Promise resolves
const response = await fetch(`https://jsonplaceholder.typicode.com/users/${id}`);
if (!response.ok) {
throw new Error(`HTTP ${response.status}`);
}
const user = await response.json();
return user;
}
// Use it. Errors bubble out as exceptions you can try/catch.
async function main() {
try {
const user = await loadUser(1);
console.log(user.name);
} catch (error) {
console.error("Failed to load user:", error.message);
}
}
main();
// Old style for reference (don't write new code this way)
// fetch("...").then(r => r.json()).then(u => console.log(u.name)).catch(...);

Try it: a small JavaScript exercise

In the in-browser editor, open script.js (or add a <script> tag in index.html) and write this. Use modern syntax — `const`, arrow functions, destructuring where it helps.

  1. 1

    Declare an array of 5 numbers

  2. 2

    Write an arrow function const sumArray = (nums) => ... that returns the total

  3. 3

    Write const average = (nums) => sumArray(nums) / nums.length

  4. 4

    Log the average to the console using a template literal: `Average: ${average(myNums)}`

  5. 5

    Open the browser console (F12) to verify it printed

  6. 6

    Bonus: rewrite sumArray as a one-liner using nums.reduce((acc, n) => acc + n, 0)

Quick Check

What's the difference between let and const?

Hint: it's about whether the variable can change.

💡 Common mistakes only experienced devs catch

Five JavaScript traps that even good juniors fall into. (1) Using `==` instead of `===` — `0 == ""` is true, `null == undefined` is true. Always use `===` unless you have a specific reason. (2) Reaching for `var` when you saw it in an old tutorial — it has function scope, not block scope, and leaks variables out of `if`/`for` blocks in ways that surprise everyone. Use `const`/`let`. (3) `||` for default values when `0` or `""` is valid input — use `??` instead, as explained above. (4) Forgetting `await` inside an async function — you get back a Promise object instead of the value, and `JSON.stringify(promise)` returns `"{}"`. If a value looks suspiciously like `[object Promise]`, you missed an `await`. (5) Mutating function arguments — `function reverse(arr) { return arr.reverse() }` mutates the caller's array because `.reverse()` is in-place. Most array methods (`.map`, `.filter`, `.slice`, `.concat`) return new arrays; learn which ones mutate.

💡 Next concept to know: Big O

Once a loop runs over thousands of items, how fast your code is starts to matter. Big O notation is the shorthand engineers use to describe how an algorithm's cost grows with input size, and it is the single most common topic in coding interviews. It is short enough to learn in one sitting: see the Computer Science Fundamentals > Algorithms Big O lesson. You do not need it to finish this track, but you will want it before your first technical interview.

Sign in and purchase access to unlock this lesson.

Sign in to purchase
←Component-Driven Design Thinking
Back to Web Development
JavaScript and the DOM→