О насБлогКонтакты
Веб-разработка22 июня 2002 г. 4 мин 121Обновлено: 22 июня 2026 г.

LAMP: стек, который выиграл веб (2002)

AunimedaAunimeda
📋 Содержание

В 2002 году вопрос, на чём запускать веб-приложение, имел два ответа. Корпоративный: Windows 2000 Server + IIS + SQL Server + ASP - дорого, лицензии, Windows-администратор. Свободный: Linux + Apache + MySQL + PHP.

LAMP не был продуктом. Его никто не изобретал. Это был органически сложившийся набор open-source инструментов, которые работали вместе надёжнее, чем каждый из них по отдельности. К 2002 году на LAMP работало большинство новых коммерческих сайтов. Shared-хостинг по всему миру - Apache на Linux, MySQL включён бесплатно, PHP в комплекте. За $8 в месяц.

Это изменило всё: кто мог строить в вебе, как быстро и за сколько.


Компоненты LAMP в 2002 году

Linux (Red Hat 7.3 / Debian 3.0): ОС. Бесплатна. Ядро 2.4 - производственный стандарт.

Apache 1.3 / 2.0: Веб-сервер. mod_php загружал PHP как модуль Apache - никаких CGI-процессов на каждый запрос. PHP работал in-process, в разы быстрее Perl CGI.

MySQL 3.23 / 4.0: СУБД. В MySQL 3.23 транзакций не было (только MyISAM). MySQL 4.0 (2002) добавил стабильный InnoDB с транзакциями.

PHP 4.3: Язык. register_globals включён по умолчанию - катастрофа безопасности, которую убивали годами. Процедурный код прямо в HTML. Быстро пишется, быстро деплоится.


Настоящее PHP-приложение 2002 года

<?php
// config.php - подключение к БД, стиль 2002 года
// Нет PDO (только в PHP 5.1). Нет MySQLi в PHP 4.
// Только функции mysql_* - расширение, удалённое в PHP 7.

define('DB_HOST', 'localhost');
define('DB_USER', 'webapp');
define('DB_PASS', 'secret123');
define('DB_NAME', 'myapp');

$conn = mysql_connect(DB_HOST, DB_USER, DB_PASS);
if (!$conn) {
    die('Ошибка подключения к БД: ' . mysql_error());
}
mysql_select_db(DB_NAME, $conn);
mysql_query("SET NAMES 'utf8'", $conn);
?>
<?php
// products.php - страница каталога товаров
require_once 'config.php';

$cat_id   = isset($_GET['cat'])  ? (int)$_GET['cat']          : 0;
$page     = isset($_GET['page']) ? max(1, (int)$_GET['page']) : 1;
$per_page = 20;
$offset   = ($page - 1) * $per_page;

$where = $cat_id > 0
    ? "WHERE category_id = $cat_id AND active = 1"
    : "WHERE active = 1";

$total_row = mysql_fetch_assoc(
    mysql_query("SELECT COUNT(*) AS total FROM products $where", $conn)
);
$total_pages = ceil($total_row['total'] / $per_page);

$result = mysql_query(
    "SELECT id, name, price, image, description
     FROM products $where
     ORDER BY created_at DESC
     LIMIT $offset, $per_page",
    $conn
);
?>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
  <title>Каталог товаров</title>
  <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
  <link rel="stylesheet" type="text/css" href="/css/style.css">
</head>
<body>
<?php include 'header.php'; ?>
<div id="content">
  <h1>Каталог</h1>
  <?php if (mysql_num_rows($result) === 0): ?>
    <p>Товаров не найдено.</p>
  <?php else: ?>
    <table cellpadding="8" cellspacing="0" border="0" class="catalog">
      <tr><th>Фото</th><th>Товар</th><th>Цена</th><th></th></tr>
      <?php $i = 0; while ($row = mysql_fetch_assoc($result)): ?>
      <tr class="<?php echo ($i++ % 2 === 0) ? 'even' : 'odd'; ?>">
        <td><img src="/images/<?php echo htmlspecialchars($row['image']); ?>"
                 width="60" height="60"></td>
        <td>
          <a href="product.php?id=<?php echo $row['id']; ?>">
            <?php echo htmlspecialchars($row['name']); ?>
          </a>
          <br><small><?php echo htmlspecialchars(substr($row['description'], 0, 80)); ?>...</small>
        </td>
        <td><?php echo number_format($row['price'], 2); ?> руб.</td>
        <td><a href="cart.php?action=add&id=<?php echo $row['id']; ?>">В корзину</a></td>
      </tr>
      <?php endwhile; ?>
    </table>
    <div class="pagination">
      <?php for ($p = 1; $p <= $total_pages; $p++): ?>
        <?php if ($p == $page): ?><strong><?php echo $p; ?></strong>
        <?php else: ?><a href="?cat=<?php echo $cat_id; ?>&page=<?php echo $p; ?>"><?php echo $p; ?></a>
        <?php endif; ?>
      <?php endfor; ?>
    </div>
  <?php endif; ?>
</div>
<?php include 'footer.php'; ?>
</body>
</html>

.htaccess: швейцарский нож LAMP-разработчика

# .htaccess 2002 года - обязательное знание для каждого PHP-разработчика

RewriteEngine On
RewriteBase /

# Красивые URL: /product/42 → product.php?id=42
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^product/([0-9]+)/?$ product.php?id=$1 [L,QSA]
RewriteRule ^catalog/([a-z0-9-]+)/?$ products.php?slug=$1 [L,QSA]

# Отключаем register_globals - критично для безопасности
php_flag  register_globals  Off
php_flag  display_errors    Off
php_value upload_max_filesize 5M

# Запрет листинга директорий
Options -Indexes

# Защита конфигурационных файлов
<FilesMatch "^(config|db)\.php$">
    Order allow,deny
    Deny from all
</FilesMatch>

Что LAMP сделал правильно и неправильно

Правильно: нулевая стоимость лицензий. Один и тот же $8-хостинг работал у всех. mod_php давал достаточную производительность. LAMP открыл веб-разработку для тысяч разработчиков по всему миру, включая Россию.

Неправильно: register_globals = On по умолчанию делал SQL-инъекции и XSS тривиальными. Большинство российских сайтов 2002-2005 годов имели уязвимости именно из-за этого. Отсутствие транзакций в MyISAM по умолчанию приводило к несогласованным данным при сбоях.

Неправильно: mysql_real_escape_string() вместо параметризованных запросов - защита от SQL-инъекций была ручной и её часто забывали применять.

Эти ошибки исправлялись постепенно: PDO в PHP 5.1, InnoDB по умолчанию в MySQL 5.5, депрекация register_globals в PHP 5.3. Платформа росла вокруг своих уязвимостей.

К 2010 году LAMP лежал в основе WordPress, Drupal, Joomla, MediaWiki - программного обеспечения, на котором работало большинство контента в интернете. Это началось с $8 в месяц и свободного кода.

Читайте также

Разработка сайта в Самаре в 2026 году - цены, сроки, технологииaunimeda
Веб-разработка

Разработка сайта в Самаре в 2026 году - цены, сроки, технологии

Сколько стоит разработка сайта в Самаре в 2026 году. Реальные цены на лендинги, корпоративные сайты и интернет-магазины. Что влияет на стоимость и как выбрать подрядчика.

Как работать с API ВКонтакте на PHP: авторизация, посты, статистика (2015)aunimeda
Веб-разработка

Как работать с API ВКонтакте на PHP: авторизация, посты, статистика (2015)

ВКонтакте в 2015 году - 65 млн активных пользователей в месяц, крупнейшая соцсеть Рунета. API позволял авторизовывать пользователей, публиковать от имени сообщества, собирать аналитику. Вот полная интеграция: OAuth 2.0, VK Login, автопостинг, работа с wall.post.

Google Chrome и V8: когда JavaScript стал быстрым (2008)aunimeda
Веб-разработка

Google Chrome и V8: когда JavaScript стал быстрым (2008)

2 сентября 2008 года Google выпустил Chrome. Не браузер - манифест. Внутри был V8: JIT-компилятор JavaScript, написанный с нуля. SunSpider показал, что V8 в 10 раз быстрее Firefox 3. За один день ожидания от JavaScript радикально изменились. Начался browser war 2.0.

Нужна IT-разработка для вашего бизнеса?

Разрабатываем сайты, мобильные приложения и AI-решения для бизнеса в России. Бесплатная консультация.

Разработка сайтов

Получить консультацию Все статьи