Phase 2 · Web FundamentalsModule 8~44 min read

HTTP & the PHP Request Lifecycle

Trace a request from browser to server and build correct PHP responses with headers and status codes.

What you'll learn

Every PHP web application is a machine that turns an HTTP request into an HTTP response. Once that model is clear, frameworks stop feeling magical.

  • Identify the four parts of an HTTP request and response
  • Read method, path, and headers through PHP
  • Send correct status codes, content types, and bodies
  • Explain document roots and PHP's role behind a web server
  • Route several URLs through one front controller

The HTTP model

HTTP is a stateless request/response protocol. A client sends one request; a server returns one response. The browser may make many additional requests for CSS, JavaScript, fonts, images, and API data.

A PHP request from end to end
1

URL

The browser resolves a host and opens a connection.

2

Request

It sends a method, target, headers, and optional body.

3

PHP

The server invokes your script with request data.

4

Response

PHP returns a status, headers, and response body.

PartRequest exampleResponse example
Start lineGET /courses/42 HTTP/1.1HTTP/1.1 200 OK
HeadersAccept: application/jsonContent-Type: application/json
BodyOften empty for GETHTML, JSON, a file, or no body
MeaningWhat the client wantsWhat happened and the representation returned

Key idea

The URL selects a resource, the method expresses intent, headers carry metadata, and the optional body carries a representation or submitted data.

Read the incoming request

PHP exposes web-server data through $_SERVER. Keys can vary by server, so read optional values defensively. parse_url() separates the route path from its query string.

inspect-request.php
<?php

declare(strict_types=1);

$method = $_SERVER['REQUEST_METHOD'] ?? 'GET';
$path = parse_url($_SERVER['REQUEST_URI'] ?? '/', PHP_URL_PATH);
$accept = $_SERVER['HTTP_ACCEPT'] ?? '*/*';

echo "Method: {$method}" . PHP_EOL;
echo "Path: {$path}" . PHP_EOL;
echo "Accept: {$accept}";
MethodTypical intentSafe/idempotent?
GETRead a representationSafe and idempotent
POSTCreate or trigger processingUsually neither
PUTReplace a resourceIdempotent
PATCHPartially update a resourceNot guaranteed
DELETERemove a resourceIdempotent by intent

Safe is not the same as secure

A safe method should not change server state. Authentication, authorization, encryption, and validation are separate security concerns.

Build a precise response

A professional response aligns three things: its status code describes the outcome, its headers describe the body, and the body follows that declared format.

create-course.php
<?php

declare(strict_types=1);

header('Content-Type: application/json; charset=utf-8');
http_response_code(201);

$response = [
    'data' => [
        'id' => 42,
        'title' => 'Learn HTTP',
    ],
];

echo json_encode($response, JSON_THROW_ON_ERROR);
StatusMeaningCommon use
200OKSuccessful read or update
201CreatedA new resource was created
204No ContentSuccess with no response body
302FoundTemporary redirect; use 303 after many form posts
400Bad RequestMalformed or invalid request
401UnauthorizedAuthentication is required
403ForbiddenIdentity is known but not allowed
404Not FoundNo matching resource
500Server ErrorUnexpected server-side failure

Headers must come first

Once body output starts, PHP may be unable to change headers. Avoid stray whitespace before <?php and decide status and headers before rendering.

Web server, document root, and PHP

The web server accepts the connection, serves static files directly, and passes PHP requests to the PHP runtime. The document root is the public directory the server exposes. Application source, secrets, and writable storage should sit outside it whenever possible.

Recommended structure
project/
├── public/           # document root
│   └── index.php     # public entry point
├── src/              # application code
├── templates/        # views
├── storage/          # logs and generated files
└── vendor/           # Composer dependencies

Route through a front controller

A front controller gives every dynamic request one entry point. It centralizes startup, error handling, sessions, middleware, and routing.

public/index.php
<?php

declare(strict_types=1);

$method = $_SERVER['REQUEST_METHOD'] ?? 'GET';
$path = parse_url($_SERVER['REQUEST_URI'] ?? '/', PHP_URL_PATH);

$route = "{$method} {$path}";

match ($route) {
    'GET /' => print '<h1>PHP Web Foundations</h1>',
    'GET /health' => print 'OK',
    default => (function (): void {
        http_response_code(404);
        echo '<h1>Page not found</h1>';
    })(),
};

Tip

Real routers handle parameters, URL decoding, method negotiation, and middleware. This tiny version is valuable because it exposes the same core responsibility.

Practice challenge

Add GET /api/status to the front controller. Return status 200, a JSON content type, and an object containing status and the current UTC time. Verify an unknown route still returns 404.

Recap & quick check

Key takeaways

  • A PHP web app transforms one HTTP request into one HTTP response.
  • Method, target, headers, and optional body describe a request.
  • Status, headers, and optional body must tell one consistent response story.
  • Keep private source and storage outside the public document root.
  • A front controller centralizes application startup and routing.

Quick check

1. Which response part describes whether the request succeeded?

2. Which method should normally only read data?

3. Why use a public/ document root?

4. What does a front controller centralize?