Ошибка разбора Javascript на символе Unicode '\ u2028'
Всякий раз, когда я использую литерал символа \u2028 в моем источнике javascript с типом содержимого, установленным в "text/html; charset = utf-8", я получаю ошибки анализа javascript.
Пример:
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>json</title>
<script type="text/javascript" charset="utf-8">
var string = '
';
</script>
</head>
<body>
</body>
</html>
Если значение <meta http-equiv>
опущено, все работает так, как ожидалось. Я тестировал это на Safari и Firefox, обе имеют ту же проблему.
Любые идеи о том, почему это происходит и как правильно исправить это (без удаления кодировки)?
Изменить:
После еще нескольких исследований особая проблема заключалась в том, что проблема была возвращена с использованием JSONP. Затем это интерпретировалось браузером, который читает u2028 как новую строку и выдает ошибку о недопустимой новой строке в строке.
Ответы
Ответ 1
Да, это особенность языка JavaScript, задокументированная в стандарте ECMAScript (раздел 3-го издания 7.3), что символы U + 2028 и U + 2029 считаются окончаниями строк. Следовательно, парсер JavaScript будет обрабатывать любой символ Un + 2028/9, равно как и символ новой строки. Поскольку вы не можете поместить строку строки в строковый литерал, вы получите синтаксическую ошибку.
Это неудачный надзор в дизайне JSON: на самом деле он не является надлежащим подмножеством JavaScript. Raw U + 2028/9 символов действительны в строковых литералах в JSON и будут приняты JSON.parse
, но не так в самом JavaScript.
Следовательно, безопасно генерировать код JavaScript с помощью анализатора JSON, если вы уверены, что он явно \u
- сохраняет эти символы. Некоторые это делают, другие - нет; many \u
- игнорировать все символы, отличные от ASCII, что позволяет избежать проблемы.
Ответ 2
Хорошо, чтобы ответить на мой собственный вопрос.
Обычно анализатор JSON удаляет эти проблемные символы, потому что я извлекал JSONP. Я не использовал парсер JSON, вместо того, чтобы браузер сам разбирал сам JSON, как только вызывался обратный вызов.
Единственный способ исправить это - убедиться, что сервер никогда не возвращает эти символы при запросе ресурса JSONP.
p.s.
Мой вопрос касался u2028, согласно Douglas Crockford json2 library все следующие символы могут вызвать эти проблемы:
'\ u0000\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff'
Ответ 3
Не могли бы вы использовать \u2028
вместо реального символа?, потому что U + 2028 разделитель строк unicode, браузеры подумают, что как истинный символ разрыва строки, например \n
.
Мы не можем делать, например,
x = "
"
Правильно? но мы делаем x = "\n"
, поэтому может быть такое же понятие.
Ответ 4
Ну, это имеет смысл, так как вы сообщаете браузеру, что HTML и script используют UTF-8, но затем вы указываете символ, который не кодируется UTF-8. Когда вы укажете "charset = UTF-8", вы будете взаимозависимы, чтобы убедиться, что байты, переданные в браузер, на самом деле являются UTF-8. Веб-сервер и браузер не будут делать это для вас в этой ситуации.