Перейти к содержимому

curl: мощный инструмент для работы с сетевыми запросами

curl: мощный инструмент для работы с сетевыми запросами

curl (Client URL) — это гибкий инструмент командной строки и библиотека для передачи данных с сервера на сервер с использованием различных протоколов. Это незаменимый инструмент для разработчиков, системных администраторов и тестировщиков, позволяющий тестировать API, отлаживать веб-запросы и автоматизировать взаимодействие с сетевыми сервисами.

В этой статье вы научитесь эффективно использовать curl для различных задач: от простых GET-запросов до сложных сценариев с аутентификацией и обработкой данных.


Что такое curl и зачем он нужен?

curl — это универсальный инструмент для:

  • Тестирования API и веб-сервисов
  • Отладки сетевых запросов
  • Скачивания файлов с различных протоколов
  • Автоматизации взаимодействия с веб-сервисами в скриптах
  • Проверки доступности серверов
  • Измерения времени ответа

Основные преимущества curl:

  • Поддержка более 25 протоколов (HTTP, HTTPS, FTP, SFTP, IMAP, SMTP и др.)
  • Работа на всех платформах (Windows, macOS, Linux)
  • Богатый набор опций для настройки запросов
  • Простота интеграции в скрипты и автоматизацию
  • Отсутствие графического интерфейса — всё управление через командную строку

Установка curl

Во многих системах curl уже предустановлен. Если его нет, установите следующим образом:

Linux (Debian/Ubuntu)

sudo apt update
sudo apt install curl
 

Linux (RHEL/CentOS/Fedora)

sudo yum install curl
# или для новых версий
sudo dnf install curl
  

macOS

curl обычно предустановлен в macOS. Для обновления используйте Homebrew:

brew install curl
  

Windows

В современных версиях Windows 10 и 11 curl встроен в систему. Если его нет:

  • Скачайте с официального сайта curl.se/windows
  • Или установите через Chocolatey: choco install curl
  • Или установите через Scoop: scoop install curl

Проверка установки

curl --version
  

Результат выполнения в терминале:

curl 7.81.0 (x86_64-pc-linux-gnu) libcurl/7.81.0 OpenSSL/3.0.2 zlib/1.2.11 brotli/1.0.9 zstd/1.4.8 libidn2/2.3.2 libpsl/0.21.0 (+libidn2/2.3.2) libssh/0.9.6/openssl/zlib nghttp2/1.43.0 librtmp/2.3 OpenLDAP/2.5.13
Release-Date: 2023-01-10
Protocols: dict file ftp ftps gopher gophers http https imap imaps ldap ldaps mqtt pop3 pop3s rtmp rtsp smb smbs smtp smtps telnet tftp
Features: alt-svc AsynchDNS brotli GSS-API HSTS HTTP2 HTTPS-proxy IDN IPv6 Kerberos Largefile libz NTLM NTLM_WB PSL SPNEGO SSL TLS-SRP UnixSockets zstd
  

Базовые команды curl

Простой GET-запрос

Самый базовый запрос — получение содержимого веб-страницы:

curl https://example.com
  

Результат выполнения в терминале:

<!doctype html>
<html>
<head>
    <title>Example Domain</title>
    <meta charset="utf-8">
    <meta http-equiv="Content-type" content="text/html; charset=utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <style type="text/css">
    body {
        background-color: #f0f0f2;
        margin: 0;
        padding: 0;
        font-family: -apple-system, system-ui, BlinkMacSystemFont, "Segoe UI", "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
    }
    div {
        width: 600px;
        margin: 5em auto;
        padding: 2em;
        background-color: #fdfdff;
        border-radius: 0.5em;
        box-shadow: 2px 3px 7px 2px rgba(0,0,0,0.02);
    }
    a:link, a:visited {
        color: #38488f;
        text-decoration: none;
    }
    @media (max-width: 700px) {
        div {
            margin: 0 auto;
            width: auto;
        }
    }
    </style>
</head>
<body>
<div>
    <h1>Example Domain</h1>
    <p>This domain is for use in illustrative examples in documents. You may use this
    domain in literature without prior coordination or asking for permission.</p>
    <p><a href="https://www.iana.org/domains/example">More information...</a></p>
</div>
</body>
</html>
   

Сохранение вывода в файл

curl -o example.html https://example.com
  

Эта команда сохранит содержимое страницы в файл example.html.

Следование редиректам

По умолчанию curl не следует редиректам. Чтобы включить эту функцию, используйте флаг -L:

curl -L https://httpbin.org/redirect-to?url=https://example.com
  

Отображение заголовков ответа

Чтобы увидеть заголовки ответа сервера, используйте флаг -i:

curl -i https://example.com
  

Результат выполнения в терминале:

HTTP/2 200
accept-ranges: bytes
age: 590222
cache-control: max-age=604800
content-type: text/html; charset=UTF-8
date: Sun, 15 Jan 2024 10:30:45 GMT
etag: "3147526947"
expires: Sun, 22 Jan 2024 10:30:45 GMT
last-modified: Thu, 17 Oct 2019 07:18:26 GMT
server: ECS (bsa/EB18)
x-cache: HIT
content-length: 1256

<!doctype html>
<html>
<head>
    <title>Example Domain</title>
    ...
   

Работа с HTTP-методами

GET-запрос

GET — метод по умолчанию. Пример с параметрами query string:

curl "https://httpbin.org/get?name=John&age=30"
  

Обратите внимание: URL в кавычках, чтобы амперсанд & не интерпретировался оболочкой как разделитель команд.

POST-запрос с данными формы

curl -X POST https://httpbin.org/post \
  -d "name=John" \
  -d "age=30"
  

Результат выполнения в терминале:

{
  "args": {},
  "data": "",
  "files": {},
  "form": {
    "age": "30",
    "name": "John"
  },
  "headers": {
    "Accept": "*/*",
    "Content-Length": "15",
    "Content-Type": "application/x-www-form-urlencoded",
    "Host": "httpbin.org",
    "User-Agent": "curl/7.81.0",
    "X-Amzn-Trace-Id": "Root=1-65a53a35-7c8d9b2f3c5a8b6d2e1f0c4a"
  },
  "json": null,
  "origin": "192.168.1.1",
  "url": "https://httpbin.org/post"
}
   

POST-запрос с JSON-данными

curl -X POST https://httpbin.org/post \
  -H "Content-Type: application/json" \
  -d '{"name": "John", "age": 30}'
  

Результат выполнения в терминале:

{
  "args": {},
  "data": "{\"name\": \"John\", \"age\": 30}",
  "files": {},
  "form": {},
  "headers": {
    "Accept": "*/*",
    "Content-Length": "27",
    "Content-Type": "application/json",
    "Host": "httpbin.org",
    "User-Agent": "curl/7.81.0",
    "X-Amzn-Trace-Id": "Root=1-65a53a35-7c8d9b2f3c5a8b6d2e1f0c4b"
  },
  "json": {
    "age": 30,
    "name": "John"
  },
  "origin": "192.168.1.1",
  "url": "https://httpbin.org/post"
}
  

PUT и DELETE запросы

# PUT запрос
curl -X PUT https://httpbin.org/put \
  -H "Content-Type: application/json" \
  -d '{"id": 1, "name": "Updated Item"}'

# DELETE запрос
curl -X DELETE https://httpbin.org/delete?id=1
  

Работа с заголовками

Добавление заголовков

Используйте флаг -H или --header для добавления заголовков:

curl -H "User-Agent: MyCustomAgent/1.0" \
     -H "Accept: application/json" \
     https://httpbin.org/headers
  

Результат выполнения в терминале:

{
  "headers": {
    "Accept": "application/json",
    "Host": "httpbin.org",
    "User-Agent": "MyCustomAgent/1.0",
    "X-Amzn-Trace-Id": "Root=1-65a53a35-7c8d9b2f3c5a8b6d2e1f0c4c"
  }
}
  

Базовая аутентификация

# Способ 1: через заголовок
curl -H "Authorization: Basic $(echo -n 'username:password' | base64)" https://httpbin.org/basic-auth/username/password

# Способ 2: встроенный механизм
curl -u username:password https://httpbin.org/basic-auth/username/password
  

Bearer-токены (JWT)

curl -H "Authorization: Bearer your_token_here" https://api.example.com/protected-resource
  

Работа с файлами

Загрузка файла на сервер

# Для multipart/form-data
curl -X POST https://httpbin.org/post \
  -F "file=@/path/to/local/file.txt" \
  -F "description=This is a test file"

# Для отправки файла как raw data
curl -X POST https://httpbin.org/post \
  --data-binary "@/path/to/local/file.txt" \
  -H "Content-Type: application/octet-stream"
  

Скачивание файла

# Сохранить с оригинальным именем
curl -O https://example.com/path/to/file.zip

# Сохранить с указанием имени
curl -o myfile.zip https://example.com/path/to/file.zip

# Скачивание с возобновлением при обрыве
curl -C - -O https://example.com/largefile.iso
  

Отладка и анализ запросов

Подробный вывод (verbose mode)

Флаг -v или --verbose показывает детали запроса и ответа:

curl -v https://example.com
  

Результат выполнения в терминале:

*   Trying 93.184.216.34:443...
* Connected to example.com (93.184.216.34) port 443 (#0)
* ALPN, offering h2
* ALPN, offering http/1.1
* successfully set certificate verify locations:
*  CAfile: /etc/ssl/certs/ca-certificates.crt
*  CApath: /etc/ssl/certs
* TLSv1.3 (OUT), TLS handshake, Client hello (1):
* TLSv1.3 (IN), TLS handshake, Server hello (2):
* TLSv1.3 (IN), TLS handshake, Encrypted Extensions (8):
* TLSv1.3 (IN), TLS handshake, Certificate (11):
* TLSv1.3 (IN), TLS handshake, CERT verify (15):
* TLSv1.3 (IN), TLS handshake, Finished (20):
* TLSv1.3 (OUT), TLS change cipher, Change cipher spec (1):
* TLSv1.3 (OUT), TLS handshake, Finished (20):
* SSL connection using TLSv1.3 / TLS_AES_256_GCM_SHA384
* ALPN, server accepted to use h2
* Server certificate:
*  subject: CN=example.com
*  start date: May 24 00:00:00 2023 GMT
*  expire date: Jun 23 23:59:59 2024 GMT
*  subjectAltName: host "example.com" matched cert's "example.com"
*  issuer: C=US; O=DigiCert Inc; CN=DigiCert TLS RSA SHA256 2020 CA1
*  SSL certificate verify ok.
* Using HTTP2, server supports multi-use
* Connection state changed (HTTP/2 confirmed)
* Copying HTTP/2 data in stream buffer to connection buffer after upgrade: len=0
* Using Stream ID: 1 (easy handle 0x55e6f9b5d670)
> GET / HTTP/2
> Host: example.com
> user-agent: curl/7.81.0
> accept: */*
> 
* old SSL session ID is stale, removing
* Connection state changed (MAX_CONCURRENT_STREAMS == 100)!
< HTTP/2 200 
< accept-ranges: bytes
< age: 590222
< cache-control: max-age=604800
< content-type: text/html; charset=UTF-8
< date: Sun, 15 Jan 2024 10:30:45 GMT
< etag: "3147526947"
< expires: Sun, 22 Jan 2024 10:30:45 GMT
< last-modified: Thu, 17 Oct 2019 07:18:26 GMT
< server: ECS (bsa/EB18)
< x-cache: HIT
< content-length: 1256
< 
<!doctype html>
<html>
<head>
    <title>Example Domain</title>
    <meta charset="utf-8">
    ...
* Connection #0 to host example.com left intact
  

Только заголовки ответа

Флаг -I (заглавная i) показывает только заголовки ответа:

curl -I https://example.com
  

Результат выполнения в терминале:

HTTP/2 200 
accept-ranges: bytes
age: 590222
cache-control: max-age=604800
content-type: text/html; charset=UTF-8
date: Sun, 15 Jan 2024 10:30:45 GMT
etag: "3147526947"
expires: Sun, 22 Jan 2024 10:30:45 GMT
last-modified: Thu, 17 Oct 2019 07:18:26 GMT
server: ECS (bsa/EB18)
x-cache: HIT
content-length: 1256
  

Измерение времени выполнения запроса

curl -w "@curl-format.txt" -o /dev/null -s https://example.com
  

Содержимое файла curl-format.txt:

    time_namelookup:  %{time_namelookup}\n
       time_connect:  %{time_connect}\n
    time_appconnect:  %{time_appconnect}\n
   time_pretransfer:  %{time_pretransfer}\n
      time_redirect:  %{time_redirect}\n
 time_starttransfer:  %{time_starttransfer}\n
                    ----------\n
        time_total:  %{time_total}\n
  

Результат выполнения в терминале:

    time_namelookup:  0.004321
       time_connect:  0.009876
    time_appconnect:  0.034567
   time_pretransfer:  0.034601
      time_redirect:  0.000000
 time_starttransfer:  0.045678
                    ----------
        time_total:  0.045712
  

Продвинутые возможности

Работа с куками

# Сохранение куков в файл
curl -c cookies.txt https://example.com/login

# Использование куков из файла
curl -b cookies.txt https://example.com/dashboard
  

Прокси

# HTTP прокси
curl -x http://proxy.example.com:8080 https://example.com

# SOCKS прокси
curl --socks5 proxy.example.com:1080 https://example.com

# Прокси с аутентификацией
curl -x http://user:Адрес электронной почты защищен от спам-ботов. Для просмотра адреса в браузере должен быть включен Javascript.:8080 https://example.com
  

Ограничение скорости загрузки

# Ограничение до 100KB/s
curl --limit-rate 100K https://example.com/largefile.zip -O
  

Параллельные загрузки

# Загрузка нескольких файлов одновременно
curl -O https://example.com/file1.zip -O https://example.com/file2.zip
  

Использование в скриптах

#!/bin/bash

# Простой скрипт для проверки статуса API
API_URL="https://api.example.com/status"
TOKEN="your_api_token"

STATUS=$(curl -s -H "Authorization: Bearer $TOKEN" $API_URL | jq -r '.status')

if [ "$STATUS" = "ok" ]; then
    echo "API работает нормально"
    exit 0
else
    echo "Проблема с API: $STATUS"
    exit 1
fi
  

Практические примеры

Проверка доступности веб-сайта

curl -f -L -I -s https://example.com
echo $?
  

Код возврата 0 означает, что сайт доступен, любой другой код — проблемы с доступностью.

Получение данных с публичного API

curl "https://jsonplaceholder.typicode.com/posts?userId=1"
  

Тестирование REST API

# Создание ресурса
curl -X POST https://api.example.com/users \
  -H "Content-Type: application/json" \
  -d '{"name": "Alice", "email": "Адрес электронной почты защищен от спам-ботов. Для просмотра адреса в браузере должен быть включен Javascript."}'

# Получение ресурса
curl https://api.example.com/users/123

# Обновление ресурса
curl -X PUT https://api.example.com/users/123 \
  -H "Content-Type: application/json" \
  -d '{"name": "Alice Smith", "email": "Адрес электронной почты защищен от спам-ботов. Для просмотра адреса в браузере должен быть включен Javascript."}'

# Удаление ресурса
curl -X DELETE https://api.example.com/users/123
  

Проверка SSL-сертификата

curl -vkI https://example.com 2>&1 | grep -i expire
  

Эта команда покажет дату истечения срока действия SSL-сертификата.


Чек-лист для проверки усвоения материала

Проверяемый навык / знаниеСтатус
1 Я умею отправлять простые GET-запросы с помощью curl.
Я умею сохранять результат запроса в файл.
Я умею следовать редиректам с помощью флага -L.
2 Я умею отправлять POST-запросы с данными формы.
Я умею отправлять POST-запросы с JSON-данными.
Я умею отправлять PUT и DELETE запросы.
Я понимаю разницу между использованием -d и -F.
3 Я умею добавлять произвольные заголовки к запросам.
Я умею работать с базовой аутентификацией.
Я умею работать с Bearer-токенами (JWT).
4 Я умею использовать verbose-режим для отладки запросов.
Я умею показывать только заголовки ответа.
Я умею измерять время выполнения запроса.
5 Я умею загружать файлы на сервер.
Я умею скачивать файлы с возможностью возобновления.
6 Я умею работать с куками (сохранение и использование).
Я умею работать с прокси-серверами.
Я умею использовать curl в bash-скриптах для автоматизации.

Практическое задание для закрепления

  1. Основы curl:
    • Отправьте GET-запрос на https://httpbin.org/get
    • Сохраните результат в файл response.txt
    • Повторите запрос с включённым verbose-режимом
  2. Работа с HTTP-методами:
    • Отправьте POST-запрос с данными формы на https://httpbin.org/post
    • Отправьте POST-запрос с JSON-данными на тот же эндпоинт
    • Отправьте PUT и DELETE запросы на соответствующие эндпоинты httpbin
  3. Работа с заголовками:
    • Отправьте запрос с кастомным User-Agent
    • Отправьте запрос с заголовком Accept: application/json
    • Проверьте, как сервер реагирует на разные заголовки
  4. Практическое применение:
    • Напишите bash-скрипт, который проверяет доступность вашего сайта каждые 5 минут
    • Создайте скрипт для получения данных с публичного API и сохранения их в файл
    • Напишите команду для проверки SSL-сертификата любого сайта

curl — это мощный инструмент, который открывает множество возможностей для работы с сетевыми запросами. Освоив базовые команды, вы сможете эффективно тестировать API, отлаживать веб-приложения и автоматизировать различные задачи. Практика и эксперименты помогут вам глубже понять возможности этого инструмента.

Совет: Начинайте с простых команд и постепенно переходите к более сложным сценариям. Используйте флаг -v для отладки, когда что-то идёт не так — он покажет все детали запроса и ответа.

Удачной работы с curl!

Воскресенье, 14 декабря 2025
curl: мощный инструмент для работы с сетевыми запросами