无法访问脚本内 EJS 模板中的 JSON

Not able to access JSON in EJS template inside script

我正在尝试构建一个基于从节点传递到客户端的 JSON 呈现动态图表的网络应用程序。

但是我无法访问 <script> 中的 json 变量。我已经使用

测试了 JSON 对象
console.log(<%= data %>) 

它出现在那里。

我的节点代码如下:

let ltlasJSON = JSON.parse(ltlasData);

app.get("/results", function(req, res){
    var query = req.query.postalCode;
    var url = "http://api.postcodes.io/postcodes/" + query;

    request(url, function(error, response, body){
        if(!error && response.statusCode == 200){
            var data = JSON.parse(body);
            var adminDistrict = data["result"]["codes"]["admin_district"];
            var filtered = ltlasJSON.filter(a=>a.areaCode==adminDistrict);
            res.render("results", {data: filtered});
        }
    }
    );    
});

results.ejs:

<<!DOCTYPE html>
    <!--[if lt IE 7]>      <html class="no-js lt-ie9 lt-ie8 lt-ie7"> <![endif]-->
    <!--[if IE 7]>         <html class="no-js lt-ie9 lt-ie8"> <![endif]-->
    <!--[if IE 8]>         <html class="no-js lt-ie9"> <![endif]-->
    <!--[if gt IE 8]><!-->
    <html class="no-js">
    <!--<![endif]-->

    <head>
        <meta charset="utf-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <title>Engliand Covid-19 </title>
        <meta name="description" content="">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <link rel="stylesheet" href="style.css">
        <!-- Plotly.js -->
        <script src="https://cdn.plot.ly/plotly-latest.min.js"></script>
    </head>

    <body>
        <!--[if lt IE 7]>
            <p class="browsehappy">You are using an <strong>outdated</strong> browser. Please <a href="#">upgrade your browser</a> to improve your experience.</p>
        <![endif]-->


    <h1>Results Page</h1>


    <script>
    var specimenDate = <%= data.areaCode %>
    var cases = <%= data.dailyLabConfirmedCases %>
    var data1 = [
            {
                x: specimenDate,
                y: cases,
                type: 'bar'
            }
        ];
        Plotly.newPlot('myDiv', data);
    </script>
</body>

</html>

我是 node 和 ejs 的新手。最终目标是在 plotly 对象的 x 和 y 变量中传递 JSON(两个字段)的数组。

我在这里看到两个问题:

1) 您将数据错误地传递到前端 javascript。 <%= 总是错误的,因为它编码了 HTML 个实体,但我们在 JS 脚本标签中而不是在常规 HTML 中。相反,您想使用 JSON.stringify 将其作为 JSON 传递,并使用 <%- 来防止 HTML-encoding:

var specimenDate = <%- JSON.stringify(data.areaCode) %>

这仍然有两个问题:首先,JSON.stringify(undefined) 将产生 undefined(而不是字符串),它在 <%- 之后变成空输出,因此您将得到一个语法如果值未定义则出错。其次,包含 </script> 的字符串将逃脱脚本块并造成严重破坏。我建议使用 devalue 而不是 JSON.stringify.

2) 您正在访问 data.areaCode,但我看到 data 实际上来自 filtered,而 filteredArray.prototype.filter 的结果调用,其中 returns 所有匹配元素的数组。然而,您正在访问 areaCode 属性 就好像 data 直接是匹配元素之一,而不是所有匹配元素的数组。

如果你打算在那里有一个数组,你必须遍历它的条目,或者直接访问一个条目,例如 data[0].areaCode(但你还必须确保 data[0] 是始终存在)。

如果这不是故意的,那么你只是使用了错误的数组方法。您可以使用 Array.prototype.find 到 return 第一个匹配项或 undefined 否则。

示例:

const db = [
  { areaCode: 1, text: 'A' },
  { areaCode: 2, text: 'B' },
  { areaCode: 2, text: 'C' }
]

console.log(db.filter(el => el.areaCode === 1)) // [{ areaCode: 1, text: 'A' }]
console.log(db.filter(el => el.areaCode === 2)) // [{ areaCode: 2, text: 'B' },
                                                //  { areaCode: 2, text: 'C' }]
console.log(db.filter(el => el.areaCode === 3)) // []

console.log(db.find(el => el.areaCode === 1)) // { areaCode: 1, text: 'A' }
console.log(db.find(el => el.areaCode === 2)) // { areaCode: 2, text: 'B' }
console.log(db.find(el => el.areaCode === 3)) // undefined