在 HTML 页面中包含隐藏数据以供 javascript 处理
Posted
技术标签:
【中文标题】在 HTML 页面中包含隐藏数据以供 javascript 处理【英文标题】:Including hidden data in an HTML page for javascript to process 【发布时间】:2011-06-12 07:59:25 【问题描述】:我从数据库中的数据生成了一个复杂的 html 摘要报告,该报告可能是数据库中可能有 200,000 行的摘要。用户可以单击链接来请求 Excel 版本。
当他们执行 JS 脚本时,会提取报告的关键组件并将它们填充到隐藏 iframe 中的表单中。此表单提交给生成报告的 Excel 版本(不包括图形等)的服务器端脚本。
由于报表的计算复杂且“成本高”,因此不要再次运行它们来创建 Excel 版本是有意义的,因为所有数据都已经在页面上。此外,一旦加载,用户可能已经自定义了报告,我也可以使用 JS 将这些首选项传递给表单,以便 Excel 文档也反映它们。
我这样做的方法是为报告的每个组件包括以下内容,这些组件将传输到 Excel 版本中的一行。我劫持了一个不被使用的 HTML 标签。
<code id="xl_row_211865_2_x" class="rowlabel">Musicals40%28.6%6</code>
上面的代码元素是 HTML 报告中下面一行的摘要,它成为 Excel 文档中的一行,包括标签和各种数据元素。一份报告中可能有一千个或更多这样的元素。
由于数据包含文本,我不得不使用 之类的东西作为字段分隔符,因为这不太可能出现在报告中的任何真实文本中。我在 CSS 中将
code
设置为 display:none。
当用户想要报告的 Excel 版本时,JS 代码会在 HTML 中搜索任何 <code>
元素并将其 className 和 innerHTML 放入表单中。 className 指示如何在 Excel 中格式化该行,然后将数据放入 Excel 行的相邻单元格中。
HTML 报告显示一个百分比基数(他们可以在它们之间切换),但用户在请求 Excel 版本时的偏好是同时包含两者。
有更好的方法吗?
(因为这是一个复杂的网络应用程序的一部分,所以没有用户会关闭 CSS 或缺少 javascript,否则他们不会走到这一步) 补充:我不能使用 HTML5,因为用户通常是使用 IE6 等旧浏览器的公司
【问题讨论】:
这在服务器上的成本有多大(实际上)。在服务器上执行此操作是否会更容易/更易于维护,并且在页面的初始加载中没有数千个可能未使用的代码标签? 我不知道这是否可能,但它似乎对我有用:将 JSON 对象保留为全局变量?还是隐藏在某个地方?并且在请求时,将 JSON 发送到 excel 解析器? 报告中的行是 HTML 还是图像?如果它们是 HTML,您的 javascript 可以从中提取信息,而不是将其再次存储在不同的额外标签中。 【参考方案1】:您可以尝试新 html5 功能localStorage,而不是使用隐藏的html 字段,也就是说,如果您确定您的用户使用仅最新 现代浏览器。
无论如何,对您的代码的改进是将数据实际存储为JSON
格式:
而不是
Musicals40%28.6%6
你会使用类似的东西
"label": "Musicals",
"percentage1": 40,
"percentage2": 28.6,
"otherLabel": 6
这样,您可以通过评估 (eval) 或 解析 (JSON.parse
) 隐藏元素的 innerHTML 来构建 javascript 对象,这比您解释自己的花括号协议更快。
【讨论】:
我们的用户都在大公司,很多人还在使用IE6!所以恐怕 HTML 5 解决方案已经出来了 这是一个很好的观点,但我觉得有点疯狂的是在网络浏览器中以任何方式存储 200k 记录的事实。本地存储、数据属性或任何解决方案。在客户端机器中需要多少内存(本地存储在 HDD 中,数据属性在内存中?)。 @Matias 它存储在一个文件中,但我相信文件的位置和类型完全取决于浏览器开发人员。在这里顶一下:forums.devnetwork.net/viewtopic.php?f=68&t=118547【参考方案2】:标准解决方案:
1) 使用 Javascript 数据块:
<script>
var mydata =
'Musicals': ['6','40%','28.6%'],
"That's Life": ['2','13.2%','0.5%'],
...etc....
</script>
2) 使用元素属性: (更多信息请参见http://ejohn.org/blog/html-5-data-attributes/)
<div class='my_data_row' data-name='Musicals' data-col1='6' data-col2='40%' data-col3='26.6%'>
...然后根据需要使用Javascript加载属性。
当数据与相关元素相关时,将使用第二个选项。您通常不希望将其用于将在其他地方使用的数据;我想说,在您的情况下,简单的 Javascript 数据块将是一个更好的解决方案。
如果您确实按照第二个选项使用数据属性,请注意在属性上使用“data-”前缀。这是一个 HTML5 规范,它将用户定义的属性与普通的 HTML 属性分开。有关详细信息,请参阅链接页面。
【讨论】:
#2 已退出,因为这些人经常使用旧浏览器。 #1 会很困难,因为数据是在构建报告时生成的,因此需要在整个报告中添加内联 JS 代码才能添加到数组或其他东西中,我宁愿避免这种情况 @derekcohen - 属性数据在旧浏览器中确实有效。使用“data-”前缀只是一种标准化人们已经使用的技术的方法。 @derekcohen - 和 #1:HTML 中的内联 JS 代码和 HTML 中的内联<code>
元素有什么区别?每个块中的一行 JSON 代码不会是很大的开销。【参考方案3】:
使用新的数据属性
http://www.javascriptkit.com/dhtmltutors/customattributes.shtml
<div data-row="[["Musicals",40,28.6,6], ...]">
div 可以是TD
标记或TR
标记或已与该行相关的任何其他相关标记,而&quot;
是转义的"
。
这使得数据隐藏在视图中,并确保有标准的解决方案来处理数据。
对于编码数据,我建议使用JSON,因为这也是一个易于使用的标准。
【讨论】:
【参考方案4】:我想以更好的方式解决这个问题的方法是将这些结果保存在服务器中的一些临时 XML 文件中,在浏览器中显示内容,当用户请求 Excel 版本时,您只需要获取时间 XML。
看看 Linq-to-XML,因为它流畅的编程风格可以帮助您在几行中读取 XML 文件,然后创建这样的 Excel 文件。
另一种解决方案是将您的对象集合序列化为 JSON 并使用 DataContractJsonSerializer 反序列化它们。这将使临时文件的大小比 XML 方法小。
【讨论】:
以上是关于在 HTML 页面中包含隐藏数据以供 javascript 处理的主要内容,如果未能解决你的问题,请参考以下文章
如何在我的 Django 500.html 页面中包含堆栈跟踪?
无法在 PHP/HTML 页面中包含 Vue 模块:SyntaxError: import not found: VueNativeSock