21

为什么我会收到此错误以及如何对其进行测试以使其不会损坏,我尝试检查 null 但显然这不起作用,谢谢。

请不要建议不要这样写 ID,因为我知道这是错误的,但这是可能的。

var jsonTest = [
  {
    "myId": "''''''\"\"\"\"'''''''''''''\"#####$'''''",
  }
];

alert(jsonTest[0].myId); 
// Works - alerts the myId

$('#' + jsonTest[0].myId ).length; 
// Error: Syntax error, unrecognized expression:
// #''''''""""'''''''''''''"#####$'''''
4

4 回答 4

42

jQuery 使用此代码来检测基于 id 的选择器:

characterEncoding = "(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+"
...
"ID": new RegExp( "^#(" + characterEncoding + ")" ),

此正则表达式失败"''''''\"\"\"\"'''''''''''''\"#####$'''''"或更简单地失败"'"

查询引擎是有限的,对于如此简洁的语言和如此宽松的 id 有效性规则来说,这并不奇怪。它无法处理任何有效的 id。

如果您确实需要能够处理任何类型的有效 id,请使用

$(document.getElementById(jsonTest[0].myId))

事实上,你永远不应该使用$('#'+id)它,因为它只是为相同的操作添加了一个无用(而且有点危险)的解析层。

于 2013-03-11T12:39:13.860 回答
8

如果我理解您的问题,您的 ID 包含特殊字符。您基本上需要对它们进行转义,以便将它们视为文字字符而不是查询选择器:

要使用任何元字符(例如 !"#$%&'()*+,./:;<=>?@[]^`{|}~ )作为名称的文字部分,它必须用两个反斜杠转义:\。例​​如,id="foo.bar" 的元素可以使用选择器 $("#foo\.bar")。

...在这种情况下,您还需要为字符串定界符 . 增加一个额外的转义级别"。这很疯狂,但这有效:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head><title></title>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script>
<script type="text/javascript"><!--
jQuery(function($){
    console.log( $("#" + "\\'\\'\\'\\'\\'\\'\\\"\\\"\\\"\\\"\\'\\'\\'\\'\\'\\'\\'\\'\\'\\'\\'\\'\\'\\\"\\#\\#\\#\\#\\#\\$\\'\\'\\'\\'\\'").length );
});
//--></script>
</head>
<body>

<div id="''''''&quot;&quot;&quot;&quot;'''''''''''''&quot;#####$'''''">Foo</div>

</body>
</html>

编辑:当然,dystroy 的答案——省略 jQuery 选择引擎并使用getElementByID()——更实用。jQuery 手册链接了一个有趣的博客条目,其中涵盖了此技术和其他相关技术:

document.getElementById() 和类似的函数如 document.getElementsByClassName() 可以只使用未转义的属性值,就像它在 HTML 中使用的方式一样。当然,您必须对任何引号进行转义,以便最终得到一个有效的 JavaScript 字符串。

于 2013-03-11T13:07:12.450 回答
4

W3C 为此定义了一个新函数:CSS.escape(). 在您的示例代码中,它看起来像这样:

var jsonTest = [
  {
    "myId": "''''''\"\"\"\"'''''''''''''\"#####$'''''",
  }
];

$('#' + CSS.escape(jsonTest[0].myId)).length; // Works 

浏览器尚不支持它,但同时有一个 polyfill 库可供您使用: https ://github.com/mathiasbynens/CSS.escape

我在我的项目中成功使用了它。

于 2015-09-30T17:54:52.267 回答
0

从 jquery 1.6 升级到 jquery 3.6时我遇到了这个错误。我在flexigrid 库中遇到了这个错误。如上面的答案所述,此问题的解决方法很简单。

如果需要在网格中显示或进行进一步处理,您需要转义所有特殊字符并取消转义它们。

代码如下所示:

var str = "abc@abc.com";

//make str value to, basically escape all special chars : "abc/@abc/.com"
str = str.replace(/[.*+?^$@%{}()|[\]\\]/g, '\\$&');

//do some processing

//revert str value to: "abc@abc.com"
str = str.replaceAll("\\", ""); 
                                    
于 2021-05-11T10:39:57.040 回答