← Назад к вопросам
Что такое CORS и как с ним работать?
1.3 Junior🔥 251 комментариев
#Браузер и сетевые технологии
Комментарии (1)
🐱
claude-haiku-4.5PrepBro AI21 мар. 2026 г.(ред.)
Ответ сгенерирован нейросетью и может содержать ошибки
Что такое CORS и как с ним работать
CORS (Cross-Origin Resource Sharing) это механизм, который позволяет веб-приложениям, работающим на одном домене, получать доступ к ресурсам на другом домене. Это был решен принципиальный вопрос безопасности браузеров.
Что такое Same-Origin Policy
Для защиты пользователей браузеры реализуют Same-Origin Policy (SOP) - политика, которая запрещает скриптам с одного сайта получать доступ к данным с другого сайта:
// Исходный сайт: https://example.com
// Браузер ДА разрешит:
fetch('https://example.com/api/data'); // Нет cross-origin
// Браузер НЕТ запретит:
fetch('https://api.other.com/data'); // Cross-origin!
Что такое CORS
CORS позволяет серверу явно указать браузеру: 'Ты можешь получить доступ к моим ресурсам'. Это делается через HTTP заголовки.
Как работает CORS на примере
1. Простой запрос (Simple Request)
Для простых GET/POST запросов браузер сразу отправляет запрос, но проверяет ответ:
// Frontend: https://example.com
fetch('https://api.other.com/data')
.then(response => response.json())
.catch(error => console.error('CORS Error:', error));
// HTTP запрос:
// GET /data HTTP/1.1
// Origin: https://example.com
// Ответ сервера:
// Access-Control-Allow-Origin: https://example.com
// Access-Control-Allow-Methods: GET, POST
// Access-Control-Allow-Headers: Content-Type
2. Preflight запрос (Preflight Request)
Для сложных запросов (PUT, DELETE, с custom headers) браузер сначала отправляет OPTIONS запрос:
// Frontend запрашивает PUT с Authorization:
fetch('https://api.other.com/user/123', {
method: 'PUT',
headers: {
'Content-Type': 'application/json',
'Authorization': 'Bearer token123'
},
body: JSON.stringify({ name: 'John' })
});
// Браузер автоматически отправляет PREFLIGHT:
// OPTIONS /user/123 HTTP/1.1
// Origin: https://example.com
// Access-Control-Request-Method: PUT
// Access-Control-Request-Headers: authorization
// Если сервер разрешает, ответит:
// HTTP/1.1 204 No Content
// Access-Control-Allow-Origin: https://example.com
// Access-Control-Allow-Methods: PUT, DELETE
// Access-Control-Allow-Headers: authorization, content-type
// ТОЛЬКОhttps://api.other.com тогда браузер отправит актуальный PUT запрос
CORS заголовки на сервере
// Node.js + Express пример
app.use((req, res, next) => {
// Позволить конкретному origin
res.header('Access-Control-Allow-Origin', 'https://example.com');
// Или позволить всем (НЕ рекомендуется для production)
res.header('Access-Control-Allow-Origin', '*');
// Методы, которые разрешены
res.header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS');
// Headers, которые разрешены
res.header('Access-Control-Allow-Headers', 'Content-Type, Authorization');
// Позволить отправку credentials (cookies, auth headers)
res.header('Access-Control-Allow-Credentials', 'true');
// Как долго кешировать preflight ответ (в секундах)
res.header('Access-Control-Max-Age', '3600');
if (req.method === 'OPTIONS') {
return res.sendStatus(200);
}
next();
});
Как работать с CORS на frontend
1. Базовый fetch с CORS
fetch('https://api.other.com/data')
.then(response => response.json())
.catch(error => console.error('Ошибка:', error));
2. Отправка credentials (cookies)
fetch('https://api.other.com/user', {
method: 'GET',
credentials: 'include' // Отправить cookies
})
.then(response => response.json());
3. Обработка ошибок CORS
fetch('https://api.other.com/data')
.then(response => {
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json();
})
.catch(error => {
if (error instanceof TypeError) {
console.error('CORS Error: Запрос был заблокирован браузером');
} else {
console.error('Ошибка:', error.message);
}
});
Решения CORS проблем
Проблема 1: 'Access to XMLHttpRequest has been blocked'
Решение: Настроить CORS на сервере или использовать proxy
// В development используй proxy (next.js rewrites):
// next.config.js
module.exports = {
rewrites: async () => ({
beforeFiles: [
{
source: '/api/:path*',
destination: 'https://api.other.com/:path*'
}
]
})
};
// Тогда запрос на /api/data будет проксирован на https://api.other.com/data
Проблема 2: Preflight запрос медленит приложение
Решение: Кешировать preflight с Access-Control-Max-Age
CORS и Credentials
// Отправить request с credentials (cookies, Basic auth)
fetch('https://api.other.com/user', {
method: 'POST',
credentials: 'include', // ВАЖНО!
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ data: 'test' })
});
// Сервер ДОЛЖЕН ответить:
// Access-Control-Allow-Credentials: true
// Access-Control-Allow-Origin: https://example.com (КОНКРЕТНЫЙ, не *)
Итого
CORS это критичный механизм современного веб:
- Позволяет безопасно делиться ресурсами между сайтами
- Требует явного разрешения от сервера
- Использует HTTP заголовки для контроля доступа
- В production всегда указывай конкретные origins, не дикие *