j 在 Rails 中使用 Coffeescript 渲染并了解如何清理 Javascript
j render With Coffeescript in Rails and Understanding How to Sanitize Javascript
我正在尝试使用 javascript 显示资源的属性。我确定我犯了一个简单的错误或遗漏。
我正在尝试了解 j render
的工作原理以及它的必要性。我知道这与恶意用户输入 javascript 的场景有关,它会在应用程序中执行,这可能会导致不好的事情发生。
设置:rails 应用中的简单博客模板:rails g scaffold Blog title:string content:text
views/blogs/show.html.erb
<div id="blogContent"> Javascript should enter result of @blogger.content here: </div>
assets/javascripts/blogs.咖啡
$document.on "page:change", ->
$blogPost = "<%= j render(@blog.content) %>"
alert($blogPost)
$('#blogContent').append($blogPost)
以下是我 运行 关注的问题:
警告框的字面意思是 returning: <%= j render(@blog.content %>
。我想要 return 该博客的内容。
一旦我让它运行到显示博客内容的地方,我想向自己证明有必要转义 javascript 这样恶意用户输入就不会在我的应用。因此,例如,如果恶意用户在内容中输入:<a href='DangerousSite.xyz'>Hacker says click for free stuff</a>
那么我的应用程序呈现 @blog.content
的结果将是一个 link,上面写着:Hacker says click for free stuff
。一旦我向自己证明转义 javascript 是防止此类事情的必要条件,我希望能够转义它并让结果字面上显示 <a href="Dangerous Site">Hacker says click for free stuff</a>
,或者以其他任何方式呈现消毒 javascript 看起来像。
1. 您可能需要遵循以下提示:
Rails: access controller instance variable in CoffeeScript or JavaScript asset file
2. 如果你要避免 HTML,你应该转义 HTML,从我读过的内容来看,j render 只会转义 Javascript,并防止 运行,但不能阻止 HTML,就像你举的例子一样。
要用 JavaScript 转义 HTML,请使用这样一个方便的函数:
var entityMap = {
"&": "&",
"<": "<",
">": ">",
'"': '"',
"'": ''',
"/": '/'
};
function escapeHtml(string) {
return String(string).replace(/[&<>"'\/]/g, function (s) {
return entityMap[s];
});
}
为了回答关于转义的第一部分 Javascript 让我们看一下这段代码:
$blogPost = "<%= j render(@blog.content) %>"
现在想象一个用户决定用 DHH 的一句话开始他们的博客 post:
“Workaholics don't actually accomplish more than nonworkaholics.”
现在,由于此上下文中的 Javascript 发生在客户端,因此代码中的 Ruby 将首先被评估。因此,您的 Javascript 现在看起来像这样:
$blogPost = "“Workaholics don't actually accomplish more than nonworkaholics.”"
如您所见,其中有一组额外的引号从字符串中断开。实际引用将被解释器读取为 Javascript,这将中断,因为它是无效的 Javascript。恶意用户可以通过重写他们的博客 post 以包含 Javascript 而不是引用来利用这一点。为了解决这个问题,我们用 j(escape_javascript 的缩写)转义引号,所以:
“Workaholics don't actually accomplish more than nonworkaholics.”
变为:
\"Workaholics don't actually accomplish more than nonworkaholics.\"
现在进入第二部分。您的代码实际上返回 "j render(@blog.content)" 的原因是因为您的那部分代码是 Ruby 并且需要在您的 Javascript 发送到浏览器之前由 ERB 处理。要让 ERB 处理此文件,只需将 .erb 添加到您的文件名中:
assets/javascripts/blogs.coffee.erb
但是,这是一种不好的做法,因为资产中的 Javascript 与您的应用程序处于不同的上下文中,因此我怀疑它不会找到 @blogs 变量。因此,您应该将 blogs.coffee.erb 文件移动到适当的视图文件夹,如下所示:
app/views/blogs/index.coffee.erb
(虽然一旦您将其移至视图中,我相信不再需要 .erb,正如 Rails 暗示的那样)
我正在尝试使用 javascript 显示资源的属性。我确定我犯了一个简单的错误或遗漏。
我正在尝试了解
j render
的工作原理以及它的必要性。我知道这与恶意用户输入 javascript 的场景有关,它会在应用程序中执行,这可能会导致不好的事情发生。
设置:rails 应用中的简单博客模板:rails g scaffold Blog title:string content:text
views/blogs/show.html.erb
<div id="blogContent"> Javascript should enter result of @blogger.content here: </div>
assets/javascripts/blogs.咖啡
$document.on "page:change", ->
$blogPost = "<%= j render(@blog.content) %>"
alert($blogPost)
$('#blogContent').append($blogPost)
以下是我 运行 关注的问题:
警告框的字面意思是 returning:
<%= j render(@blog.content %>
。我想要 return 该博客的内容。一旦我让它运行到显示博客内容的地方,我想向自己证明有必要转义 javascript 这样恶意用户输入就不会在我的应用。因此,例如,如果恶意用户在内容中输入:
<a href='DangerousSite.xyz'>Hacker says click for free stuff</a>
那么我的应用程序呈现@blog.content
的结果将是一个 link,上面写着:Hacker says click for free stuff
。一旦我向自己证明转义 javascript 是防止此类事情的必要条件,我希望能够转义它并让结果字面上显示<a href="Dangerous Site">Hacker says click for free stuff</a>
,或者以其他任何方式呈现消毒 javascript 看起来像。
1. 您可能需要遵循以下提示:
Rails: access controller instance variable in CoffeeScript or JavaScript asset file
2. 如果你要避免 HTML,你应该转义 HTML,从我读过的内容来看,j render 只会转义 Javascript,并防止 运行,但不能阻止 HTML,就像你举的例子一样。
要用 JavaScript 转义 HTML,请使用这样一个方便的函数:
var entityMap = {
"&": "&",
"<": "<",
">": ">",
'"': '"',
"'": ''',
"/": '/'
};
function escapeHtml(string) {
return String(string).replace(/[&<>"'\/]/g, function (s) {
return entityMap[s];
});
}
为了回答关于转义的第一部分 Javascript 让我们看一下这段代码:
$blogPost = "<%= j render(@blog.content) %>"
现在想象一个用户决定用 DHH 的一句话开始他们的博客 post:
“Workaholics don't actually accomplish more than nonworkaholics.”
现在,由于此上下文中的 Javascript 发生在客户端,因此代码中的 Ruby 将首先被评估。因此,您的 Javascript 现在看起来像这样:
$blogPost = "“Workaholics don't actually accomplish more than nonworkaholics.”"
如您所见,其中有一组额外的引号从字符串中断开。实际引用将被解释器读取为 Javascript,这将中断,因为它是无效的 Javascript。恶意用户可以通过重写他们的博客 post 以包含 Javascript 而不是引用来利用这一点。为了解决这个问题,我们用 j(escape_javascript 的缩写)转义引号,所以:
“Workaholics don't actually accomplish more than nonworkaholics.”
变为:
\"Workaholics don't actually accomplish more than nonworkaholics.\"
现在进入第二部分。您的代码实际上返回 "j render(@blog.content)" 的原因是因为您的那部分代码是 Ruby 并且需要在您的 Javascript 发送到浏览器之前由 ERB 处理。要让 ERB 处理此文件,只需将 .erb 添加到您的文件名中:
assets/javascripts/blogs.coffee.erb
但是,这是一种不好的做法,因为资产中的 Javascript 与您的应用程序处于不同的上下文中,因此我怀疑它不会找到 @blogs 变量。因此,您应该将 blogs.coffee.erb 文件移动到适当的视图文件夹,如下所示:
app/views/blogs/index.coffee.erb
(虽然一旦您将其移至视图中,我相信不再需要 .erb,正如 Rails 暗示的那样)