Короче, XSS — штука простая по смыслу, но ловушка для многих. Главная беда — ввод с клиента, который браузер потом исполняет как код. Чтобы не словить геморрой, сначала стоит определить, где именно у тебя «дырки» — в URL, формах, в выводе текста на странице.
Самое простое и распространённое решение — экранировать вывод. Есть разные способы: htmlspecialchars в PHP, специальные функции в JS-фреймворках и так далее. Плюс такого подхода в том, что это почти на 100% закрывает возможности вставить скрипты через ввод. Минус — если неверно используешь, можно либо не закрыть дыру, либо случайно поломать логику на странице.
Другой вариант — Content Security Policy (CSP). Звучит сложно, но это настройка веб-сервера или метатэг, который говорит браузеру, что и откуда можно грузить. CSP хорош тем, что ограничивает, даже если где-то что-то проскочило. Но у него есть свои грабли — сложности с настройкой и совместимостью, плюс если используешь много внешних ресурсов, можно случайно заблокировать часть работы сайта.