Symfony Mercure: EventSource не отправляет cookie
В Symfony Mercure я хочу отправить авторизацию cookie:
- Сервер Symfony: https://127.0.0.1:8000/
- Центр Mercure: http://localhost:3000/.well-known/mercure
Я запускаю свой сервер Mercure с помощью этой команды:
mercure/mercure.exe --jwt-key='...jwtToken...' --addr='localhost:3000' --allow-anonymous --cors-allowed-origins='https://127.0.0.1:8000'
И вот как я пытаюсь отправить Cookie withCredentials: true
:
const url = new URL('http://localhost:3000/.well-known/mercure')
url.searchParams.append('topic', 'https://bubble.com/message')
const eventSource = new EventSource(url, { withCredentials: true })
На моей текущей странице https://127.0.0.1:8000/message
в консоли я вижу файл cookie:
set-cookie: mercureAuthorization =... cookieValue...; путь =/. хорошо известный /mercure; безопасный; httponly; Samesite= слабый
Но куки никогда не отправляются. В моей консоли на вкладке сети я вижу запрос источника событийhttp://localhost:3000/.well-known/mercure?topic=https%3A%2F%2Fbubble.com%2Fmessage
но cookie никогда не передается.
Я пытался изменить secure=false
а также samesite=none
, но cookie никогда не передается.
Вот информация из запроса источника событий (Mercure Hub):
1 ответ
Недавно я потратил несколько часов, чтобы заставить его работать в Chrome (в Firefox у меня не было проблем с созданием и отправкой файлов cookie):
- Реакция: 127.0.0.1:3000
- Symfony API: 127.0.0.1:8000
- Mercure: 127.0.0.1:5000
Обратите внимание, что я не мог заставить его работать с использованием адреса Localhost (cookie не устанавливался / не отправлялся для аутентификации):
- Запустите Mercure и назначьте источники для Front App (вместо "*"):
mercure --jwt-key=aVerySecretKey --addr=127.0.0.1:5000 --allow-anonymous --cors-allowed-origins=http://127.0.0.1:3000
- В React настройте адрес Rest Api:
REACT_APP_SERVER_ROOT=http://127.0.0.1:8000
- В Symfony настройте конфигурацию, как показано ниже:
###> MERCURE_JWT_KEY ###
MERCURE_JWT_KEY=aVerySecretKey
###< MERCURE_JWT_KEY ###
###> symfony/mercure-bundle ###
MERCURE_PUBLISH_URL=http://127.0.0.1:5000/.well-known/mercure
MERCURE_JWT_TOKEN=your_secret_jwt_token
###< symfony/mercure-bundle ###
- В Symfony создайте CookieGenerator и сгенерируйте Cookie, как показано ниже:
$token = (new Builder())
->withClaim(
'mercure',
//Using UserId will help to define the targets on publish action
['subscribe' => ["http://127.0.0.1/user/{$user->getId()}"]]
)
->getToken(new Sha256(), new Key($this->secret));
//ATT: As you work in local environment Localhost, path needs to be ''
//otherwise Chrome won't setup the cookie. In Firefox this seems not to be a problem
return Cookie::create('mercureAuthorization', $token, 0, '');
//THIS WONT WORK: return Cookie::create('mercureAuthorization', $token, 0, '/.well-known/mercue');
- Наконец, в React создайте eventSource, который будет отправлять автоматически созданный файл cookie - не забудьте добавить
{withCredentials: true}
// URL is a built-in JavaScript class to manipulate URLs
const url = new URL('http://127.0.0.1:5000/.well-known/mercure');
url.searchParams.append('topic', 'http://127.0.0.1/your_topic/{id}') ;
const eventSource = new EventSource(url, {withCredentials: true});
eventSource.onmessage = event => {
console.log(JSON.parse(event.data));
}
Надеюсь, это может быть полезно и сэкономит вам время.