Yahoo Weather API引发“ forEach”错误

时间:2018-08-03 19:41:56

标签: node.js express ejs yahoo-weather-api

我决定继续使用yahoo weather API,以尝试显示位置和天气。

app.js代码:

**请注意,我用“查询”一词取代了api网址位置**

var express = require("express");
var app = express();
var request = require("request");

app.set("view engine", "ejs");


app.get("/", function(req, res){
    res.render("weatherSearch"); 
});

app.get("/results", function(req, res){
   var query = req.query.searchTerm;
   var url = "https://query.yahooapis.com/v1/public/yql?q=select%20*%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text%3D%22"+query+"%22)&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys"

   request(url, function(error, response, body){
            if(!error && response.statusCode == 200){
                var data = JSON.parse(body);
                res.render("results", {data: data});
            }
   });
});


app.listen(process.env.PORT, process.env.IP, function(){
   console.log("Server Connected"); 
});

weatherSearch.ejs:

<h1>Where would you like to check the weather?<h1>

<form action ="/results" method="GET">

    <input type="text" placeholder="Enter the city here!" name="searchTerm">
    <input type="submit">


</form> 

results.ejs

<h1>The Weather is:</h1>

<ul>
    <% data["query"].forEach(function(weather){ %>
    <li>
        <strong>
            <% weather["location"] %>
        </strong>
    </li>
<% }) %>

</ul>

<a href="/">Search Again!</a>

我从控制台收到的错误是:

Server Connected
TypeError: /home/ubuntu/workspace/WeatherSearchAPP/views/results.ejs:4
    2| 
    3| <ul>
 >> 4|     <% data["query"].forEach(function(weather){ %>
    5|     <li>
    6|         <strong>
    7|             <% weather["location"] %>

data.query.forEach is not a function
    at eval (eval at compile (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/ejs/lib/ejs.js:618:12), <anonymous>:11:22)
    at returnedFn (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/ejs/lib/ejs.js:653:17)
    at tryHandleCache (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/ejs/lib/ejs.js:251:36)
    at View.exports.renderFile [as engine] (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/ejs/lib/ejs.js:482:10)
    at View.render (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/express/lib/view.js:135:8)
    at tryRender (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/express/lib/application.js:640:10)
    at EventEmitter.render (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/express/lib/application.js:592:3)
    at ServerResponse.render (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/express/lib/response.js:1008:7)
    at Request._callback (/home/ubuntu/workspace/WeatherSearchAPP/app.js:19:21)
    at Request.self.callback (/home/ubuntu/workspace/WeatherSearchAPP/node_modules/request/request.js:185:22)

yahoo weather api :(当前会以“伦敦”形式显示天气),因此,如果将其复制到网络浏览器中,则会看到大量与伦敦天气有关的信息。

https://query.yahooapis.com/v1/public/yql?q=select%20*%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text%3D%22london%22)&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys

如果有人对我做错的事情有任何建议,将不胜感激!

2 个答案:

答案 0 :(得分:1)

API以{ "query": { ...} }的格式返回数据,将其转换为JSON对象,您最终得到一个query object 而不是数组。从query对象本身看,它似乎确实具有countresults属性(而results属性也看起来像对象)。但是,您的特定查询只会产生一个结果,因此,如果您假设我有多个结果,那么假设这会产生一个数组,则需要结合使用这两个属性来准确地解析数据,例如

const data = JSON.parse(body);
const { count, results } = data.query;
res.render("results", { 
  results: count > 1 ? results : [results]  // wrap in an array of only single result
});

然后您认为

<% results.forEach(...) %>

答案 1 :(得分:-1)

'forEach'是一个数组方法,Yahoo Weather API不在键“ query”下返回数组。每个API不同,每个请求可以产生不同的结构化JSON数据。

如上所述,您可以通过打开此链接来检查Yahoo Weather API响应的结构。例如,如果要访问城市名称,则可以使用

 <%= data.query.results.channel.location.city %>

您将获得未来几天返回的预测数组,您可以在其中使用forEach循环,因为它是一个数组:query.results.channel.item.forecast

在您要遍历JS中的对象的情况下,可以使用for...in循环:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/for...in