在Ruby on Rails的HTML视图中如何调用JavaScript函数?
现有代码的基础问题
- 按钮
onclick属性写的是调用myfunction(),但你实际定义的函数名是collapse,函数名不匹配本身就会调用失败。 - Rails默认开启Turbo(旧版本为Turbolinks),且JS打包后默认是模块级作用域,内联
onclick访问不到局部定义的函数,同时如果JS加载时机早于DOM渲染,事件绑定也会失效。
方案1:非侵入式JS绑定(推荐)
这种写法不需要加内联onclick,符合Rails的最佳实践,兼容性更好。
- 调整JS代码,适配Turbo的加载逻辑,将代码放入
app/javascript/application.js(或单独导入到该文件的自定义JS文件):
// 监听Turbo页面加载完成事件,兼容全量刷新和局部跳转场景 document.addEventListener("turbo:load", () => { const coll = document.getElementsByClassName("collapsible"); for (let i = 0; i < coll.length; i++) { coll[i].addEventListener("click", function() { this.classList.toggle("active"); const content = this.nextElementSibling; content.style.display = content.style.display === "block" ? "none" : "block"; }); } })
如果你用的是Rails 6及之前的Turbolinks版本,把监听事件名改成turbolinks:load即可。
2. 视图中的按钮直接去掉onclick属性即可:
<button type="button" class="collapsible">Expand content</button>
方案2:保留内联onclick写法
如果你一定要用内联onclick的方式,需要把函数挂载到全局window对象上,让内联脚本可以访问到:
- 修改JS代码:
// 挂载到window对象,暴露到全局作用域 window.collapse = () => { const coll = document.getElementsByClassName("collapsible"); for (let i = 0; i < coll.length; i++) { coll[i].addEventListener("click", function() { this.classList.toggle("active"); const content = this.nextElementSibling; content.style.display = content.style.display === "block" ? "none" : "block"; }); } }
- 修改按钮的
onclick属性,调用正确的函数名:
<button type="button" onclick="collapse()" class="collapsible">Expand content</button>
注意如果项目开启了内容安全策略(CSP),需要额外配置允许内联脚本,否则依然会被拦截,因此不推荐该方案。
内容的提问来源于stack exchange,提问作者Anonymous
相关产品推荐
相关产品推荐

