Three things every tutorial assumes you already know. If any of them are fuzzy, this is the most important chapter in the guide. Everything from Chapter 4 onward builds on these concepts.

APIs are the waiter who takes your order to the kitchen. API keys are your membership card that proves you are allowed to order. GitHub is the recipe binder that stores every version of your restaurant's recipes. The .gitignore is the "do not photocopy" stamp on your confidential recipes.
Every modern product is built from dozens of services that talk to each other through APIs.
When your app needs to do something it cannot do itself — process a payment, send an email, generate an AI response, verify a phone number — it makes an API call to another service. Your app sends a request. The service does the work. The service sends a response back. That is it.
You will never build a product that does everything itself. Stripe handles payments. SendGrid handles email. OpenAI or Anthropic handles AI. Twilio handles SMS. Your product is the director that coordinates these services — and APIs are how they communicate.
A structured way for one piece of software to send a request to another and get a response back. Think of it as a menu at a restaurant — it lists everything the kitchen can make and how to order it. You do not walk into the kitchen. You read the menu, place your order, and the waiter brings it back.
Every API call is one of four types. Learn these and you can read any API documentation.
Fetch data without changing anything. "Show me this user's profile." "List all products." "Get the current weather." The most common request type. Safe to repeat — asking for data does not change data.
Send data to create something new. "Create a new user account." "Submit a payment." "Generate an AI response." Sends data in the request body. Not safe to repeat — sending the same POST twice might create two accounts.
Change existing data. "Update the user's email address." "Change the subscription plan." PUT replaces the entire record. PATCH changes only specific fields. Most of the time you want PATCH.
Remove data. "Delete the user's account." "Cancel the subscription." Permanent in most systems. Some APIs do "soft deletes" (mark as deleted but keep the data) — read the docs to know which.
Every API response includes a number that tells you what happened. Learn six and you cover 95% of situations.
| Code | Meaning | What to Do | Restaurant Version |
|---|---|---|---|
| 200 | Success — here is your data | Everything worked. Process the response. | "Here is your steak, cooked perfectly." |
| 201 | Created — new resource made | Your POST request created something. Save the returned ID. | "Your reservation is confirmed." |
| 400 | Bad request — you sent something wrong | Check your request format. A field is missing or invalid. | "We don't serve 'pasta with ice cream.' Try again." |
| 401 | Unauthorized — who are you? | Your API key is missing, expired, or wrong. Check your credentials. | "You need a membership card to order here." |
| 404 | Not found — that does not exist | The URL or resource ID is wrong. Check the endpoint path. | "We don't have a table 47. Are you sure?" |
| 500 | Server error — their problem, not yours | The service broke. Wait and retry. If persistent, check their status page. | "Sorry, the kitchen is on fire. Come back later." |
The 2xx range means success. The 4xx range means you made a mistake. The 5xx range means their server has a problem.
API docs look intimidating. They follow a pattern. Learn the pattern once.
Every API documentation page for every endpoint tells you the same five things: the method (GET/POST/etc), the URL to call, what to send, what comes back, and what can go wrong. Once you recognize this pattern, you can read any API docs — Stripe, Twilio, OpenAI, any service.
① THE METHOD + URL (what to call and how)
POST https://api.stripe.com/v1/checkout/sessions
② AUTHENTICATION (prove you're allowed)
Header: Authorization: Bearer sk_live_your_secret_key
③ REQUEST BODY (what to send)
{
"mode": "subscription",
"line_items": [{ "price": "price_abc123", "quantity": 1 }],
"success_url": "https://yoursite.com/success",
"cancel_url": "https://yoursite.com/cancel"
}
④ RESPONSE (what comes back on success)
{
"id": "cs_live_abc123",
"url": "https://checkout.stripe.com/pay/cs_live_abc123"
}
⑤ ERRORS (what can go wrong)
400: Missing required field "success_url"
401: Invalid API key
429: Rate limit exceeded — too many requests
When you ask AI to integrate with an API, give it the documentation URL. "Here is the Stripe API docs for creating a checkout session: [URL]. Write the function to create a checkout session with these parameters." The AI reads the docs and writes the correct integration. Without the docs, it guesses — and the guesses are often close but subtly wrong in ways that break in production.
Most APIs limit how many requests you can make per minute or per hour. Stripe allows 100 requests per second. OpenAI allows a set number of tokens per minute depending on your plan. If you exceed the limit, the API returns a 429 error ("too many requests") and temporarily blocks you. This matters when you build batch operations (Chapter 17) — sending 1,000 requests in a loop will hit the rate limit. Space them out or use the API's batch endpoints.

Every service gives you a unique key. Protect it like a bank password.
When you sign up for Stripe, OpenAI, or any external service, they give you an API key — a long string of random characters that identifies you. Every request your app makes includes this key so the service knows who is asking and whether they are allowed. Without the key, the service rejects the request (401 Unauthorized).
Most services give you two keys: a test key and a live key. Test keys work against fake data — you can simulate payments without charging real credit cards. Live keys work against real data — real charges, real emails, real consequences. Never mix them up. Your development environment uses test keys. Your production environment uses live keys. Mixing them is how you accidentally charge a test account $29.99 for real.
A unique string that identifies you to a service. Like a password for software. Leak it and anyone can use your account — make API calls on your behalf, access your data, and run up your bill. Treat it like a credit card number.
A value stored outside your code that your app reads at runtime. API keys live in a .env file on your computer — never in the actual code files. Your code reads the value: process.env.STRIPE_KEY. If someone reads your code, they see the variable name but never the actual key.
# Payment processor
STRIPE_SECRET_KEY=sk_live_abc123...
STRIPE_TEST_KEY=sk_test_xyz789...
# AI provider
AI_API_KEY=sk-ant-abc123...
# Database
DATABASE_URL=postgresql://user:pass@host/db
# Email service
EMAIL_API_KEY=SG.abc123...
# This file is NEVER uploaded to GitHub
# It stays on your computer and on your server
A developer accidentally pushed their AWS key to a public GitHub repo. Within 15 minutes, automated bots found it and spun up cryptocurrency mining servers on their account. The bill: $14,000 in 3 hours. GitHub and cloud providers now scan for leaked keys automatically, but the window between leak and detection can be expensive. The fix is prevention, not detection.
On your computer: in a .env file at the root of your project. This file is listed in .gitignore so it never gets uploaded to GitHub.
On your hosting platform: in the platform's environment variables dashboard (Vercel, Netlify, AWS, your database provider all have this). You set them through the web interface, not through code.
On your phone/app build: some keys are embedded in mobile apps using build-time environment variables. These are slightly less secure because apps can be decompiled — use only public/restricted keys in mobile code, never secret keys.
In your AI conversations: never paste full API keys into AI chat. The AI does not need them. If you need to discuss a key-related issue, paste the first 8 characters and replace the rest with asterisks: sk_live_abc1****.
Version control sounds boring. It saves your product at least once a month.
Git is a tool that tracks changes to your code. Every time you save a "snapshot" (called a commit), Git remembers exactly what every file looked like at that moment. If you break something tomorrow, you can go back to today's snapshot. No change is ever truly lost.
GitHub is a website that hosts your Git repositories in the cloud. Think of Git as the camera and GitHub as the photo album. The camera takes the pictures (commits). The album stores them online where you can access them from any computer, share them with collaborators, and restore them if your computer dies.
A project folder on GitHub. Contains all your code, its entire history, and configuration files. Like a binder that holds every version of every recipe you have ever written — and you can flip back to any page at any time.
A snapshot of your code at a specific moment, with a note about what changed. "Added pricing page." "Fixed login bug." "Updated payment webhook." Every commit is a restore point you can go back to if things break.
A parallel copy of your code where you can experiment without affecting the main version. Like making a photocopy of your recipe before trying a new ingredient — if it is terrible, the original is untouched. Merge the branch back when the experiment works.
# Stage your changes (tell Git what to save)
git add .
# Save a snapshot with a descriptive note
git commit -m "added pricing page with 3 tiers"
# Upload to GitHub (backup + share)
git push
# Download the latest from GitHub
git pull
That is it. Four commands. add stages changes, commit saves a snapshot, push uploads, pull downloads. Everything else is edge cases you learn as you encounter them.
# See all your snapshots
git log --oneline
a3f7b21 added pricing page with 3 tiers
9c2e4d8 fixed login timeout bug
1b5a8f3 initial project setup
# Go back to a working version
git checkout 9c2e4d8
# Your code is now exactly as it was
# after the login fix — before you
# broke the pricing page
Anyone on the internet can read your code. Open source projects use public repos. Never put a product with API keys (even in .env) in a public repo unless you are 100% sure the .gitignore is working. The code is fine to share. The keys are not.
Only you (and people you invite) can see the code. Every product you build should be in a private repo. GitHub Free includes unlimited private repos. There is no reason to make your product's code public unless you are intentionally open-sourcing it.
Write commit messages for the person who will be reading them at 2am trying to figure out what broke. That person is you, three months from now, with no memory of what you were thinking today.
Bad: "fixed stuff" / "updates" / "asdf" / "WIP" — these tell you nothing when you are scrolling through history trying to find when the payment bug was introduced.
Good: "fixed login timeout by increasing token expiry to 24h" / "added annual pricing plans, web-only" / "split payment webhook into 3 functions" — these tell the complete story. Three months from now, you will scan this list and immediately know which commit to investigate.
Break any link and your keys are exposed.
This file tells Git what to skip. Set it up BEFORE your first commit.
# Secret keys — NEVER upload these
.env
.env.local
.env.production
# Dependencies — downloaded, not stored
node_modules/
# Build output — regenerated, not stored
.next/
dist/
build/
# OS files — junk your computer creates
.DS_Store
Thumbs.db
# IDE settings — personal preferences
.vscode/
.idea/
Create this file before your first commit. Not after. The moment a key hits GitHub's history, it is compromised — even if you delete the file and commit again. Git keeps the complete history of every file. Deleting a file from the current version does not remove it from history. GitHub and cloud providers scan for exposed keys and revoke them automatically, but the window between leak and detection can be expensive.
If you accidentally push a key: revoke the key immediately from the service's dashboard, generate a new one, update your .env file, and update your hosting platform's environment variables. Do not try to "undo" the push — the key is already compromised. Revoke and replace is faster and safer.
How APIs, keys, and GitHub work together when a user taps "Subscribe."
Your app's frontend sends a POST request to your backend function. The request includes: which plan the user selected and their user ID.
Your backend function reads STRIPE_SECRET_KEY from the environment variables. It never sees the actual key value in the code — just the variable name. The hosting platform injects the real value at runtime.
Your backend sends a POST request to api.stripe.com/v1/checkout/sessions with the plan details and your API key in the header. Stripe creates a checkout session and returns a URL.
User enters their card on Stripe's checkout page. Payment succeeds. Stripe sends a webhook (another API call, but in reverse) to your webhook-receiver function with the payment details.
Your webhook function verifies the event is real (using your webhook signing secret from environment variables), then updates the user's subscription status in your database. User now has access.
All of this code — the frontend, the backend function, the webhook handler — lives on GitHub in your private repo. The API keys do not. They live in .env locally and in environment variables on your hosting platform.

Every product you build is a composition of services connected by APIs, authenticated by keys, and versioned by Git. Master these three concepts and every tutorial in every framework makes sense.
Every one of these costs hours. Knowing them in advance costs you zero.
Putting const API_KEY = "sk_live_abc123" directly in your code file. It works — until you push to GitHub and the key is exposed. Always use environment variables. Always.
Creating a .gitignore after you already committed your .env file. The .env is now in Git history forever. Even deleting and recommitting does not remove it from history. Set up .gitignore first.
Testing with your production Stripe key instead of the test key. You charge real cards. Real money. Real angry customers. Always test with test keys.
Vague commit messages that mean nothing three months later. "fix" does not tell you what was fixed. "updated pricing page to show annual plans" does. Future you will thank present you.
Getting a 401 (Unauthorized) and assuming the API is broken. It is almost never the API. Your key is wrong, expired, or missing. Check the key first. Then check if you are using the test key against the live endpoint or vice versa.
Set up your .gitignore before your first commit. Not after. The moment a key hits GitHub's history, it is compromised — even if you delete it later. GitHub scans for exposed keys and services revoke them automatically, but the damage window can be expensive. Prevention, not detection.