2016-08-01 3 views
0

Я студент CS с сильным фоном Java, а javascript - это сложный, но забавный опыт, пока я не столкнулся с ситуацией, когда я пытался использовать свои собственные модули для возврата значений, требующих, чтобы программа дождалась завершения некоторой процедуры перед возвратом. Как правильно использовать модули узлов


Пока никто из форумов, на который я опубликовал этот вопрос, не смог дать реальное исправление кода этой проблеме, они сослались на меня, чтобы прочитать другие материалы, которые не связаны с проблемой.
Кто-нибудь, пожалуйста, прочитает код и предоставит правильное стандартное решение проблемы, с которой я столкнулся? Вот код, простое серверное приложение узлов, app.js и погодный модуль weatherApp.js, который использует предоставленный пользователем почтовый индекс и возвращает прогноз погоды в этом районе.

вот код:
weatherApp.js

// The required modules. 
var http = require("http"); 
var https = require("https"); 


    //result object 
    var resultSet = { 
     googleRequestUrl:"", 
     forecastIOrequest:"", 
     latitude :"", 
     longitude:"", 
     localInfo:"", 
     weather:"", 
     humidity:"", 
     pressure:"", 
     time:"" 
    }; 

    //print out error messages 
    function printError(error){ 
     console.error(error.message); 
    } 

    //Forecast API required information: 
    //key for the forecast IO app 
    var forecast_IO_Key = "bb9aac7c57877f8f5fab339e3b55669a"; 
    var forecast_IO_Web_Adress = "https://api.forecast.io/forecast/"; 


    //Create Forecast request string function 
    function createForecastRequest(latitude, longitude){ 
     var request = forecast_IO_Web_Adress + forecast_IO_Key + "/" 
          + latitude +"," + longitude; 
     return request; 
    } 

    //Google GEO API required information: 
    //Create Google Geo Request 
    var google_GEO_Web_Adress = "https://maps.googleapis.com/maps/api/geocode/json?address="; 

    function createGoogleGeoMapRequest(zipCode){ 
     var request = google_GEO_Web_Adress+zipCode + "&sensor=false"; 
     return request; 
    } 


    // 1- Need to request google for geo locations using a given zip 
    function connectToGoogleGEO(zipCode, afterCallback){ 
     var googleRequest = https.get(createGoogleGeoMapRequest(zipCode), function(response){ 
      //saving the Google request URL 
      resultSet.googleRequestUrl = createGoogleGeoMapRequest(zipCode); 
      var body = ""; 
      var status = response.statusCode; 
      //a- Read the data. 
      response.on("data", function(chunk){ 
       body+=chunk; 
      }); 
      //b- Parse the data. 
      response.on("end", function(){ 
       if(status === 200){ 
        try{ 
         var googleReport = JSON.parse(body); 
         resultSet.latitude = googleReport.results[0].geometry.location.lat; 
         resultSet.longitude = googleReport.results[0].geometry.location.lng; 

      resultSet.localInfo = googleReport.results[0].address_components[0].long_name + ", " + 
            googleReport.results[0].address_components[1].long_name + ", " + 
            googleReport.results[0].address_components[2].long_name + ", " + 
            googleReport.results[0].address_components[3].long_name + ". "; 
            // callback to forecast IO. 

         afterCallback(resultSet.latitude, resultSet.longitude); 
        }catch(error){ 
         printError(error.message); 
        }finally{ 
        // nothing here 
        } 
       }else{ 
        printError({message: "Error with GEO API"+http.STATUS_CODES[response.statusCode]}) 
       } 
      }); 
     }); 
    } 

    function connectToForecastIO(latitude,longitude){ 
     var forecastRequest = https.get(createForecastRequest(latitude,longitude),function(response){ 
      resultSet.forecastIOrequest = createForecastRequest(latitude,longitude); 
      var body = ""; 
      var status = response.statusCode; 
      //read the data 
      response.on("data", function(chunk){ 
       body+=chunk; 
      }); 
      //parse the data 
      response.on("end", function(){ 
       try{ 
        var weatherReport = JSON.parse(body); 
        resultSet.weather = weatherReport.currently.summary; 
        resultSet.humidity = weatherReport.currently.humidity; 
        resultSet.temperature = weatherReport.currently.temperature; 
        resultSet.pressure = weatherReport.currently.pressure; 
        resultSet.time = weatherReport.currently.time; 
       }catch(error){ 
        printError(error.message); 
       }finally{ 
        console.log(resultSet); 

       } 
      }); 
     });  
    } 


    function get(zipCode){ 
     var results = connectToGoogleGEO(zipCode, connectToForecastIO); 
     return results; 
    } 

    //define the name of the outer module. 
    module.exports.get = get; 

А вот код сервера:
app.js

var express = require("express"); 
var weatherApp = require("./weatherApp.js"); 
var path = require("path"); 
var http = require("http"); 
var app = express(); 

//creating routes 
//The home 
app.get("/", function(req, res){ 
    res.redirect("/weather"); 
}); 
app.get("/weather", function(req, res){ 
    res.sendFile(path.join(__dirname + "/index.html")); 
}); 
//------------------------------------------------------ 
//The resources, css, web js files, images etc. 
app.get("/StyleSheets/style.css", function(req, res){ 
    res.sendFile(path.join(__dirname + "/StyleSheets/style.css")); 
}); 
app.get("/webScripts/app.js", function(req, res){ 
    res.sendFile(path.join(__dirname + "/webScripts/app.js")); 
}); 
app.get("/webImages/swirl_pattern.png", function(req, res){ 
    res.sendFile(path.join(__dirname + "/webImages/swirl_pattern.png")); 
}); 
//------------------------------------------------------- 
//other requests 

app.get("/zipcode.do", function(req, res){ 
    var zipcode = req.query["zipcode"]; 
    var response = "No report Available"; 

    function getReport(zipCode, callback){ 
     response = weatherApp.get(req.query["zipcode"]); 
    } 
    getReport(zipcode,()=>{ 
     res.send("<p>" + response+ "</p>"); 
    }); 
}); 

//any other entry thats not listed as a valid to request 
app.get("/:title", function(req,res){ 
    var title = req.param.title; 
    if(title === undefined){ 
     var status = res.status(503); 
     res.send("This page does not exists" + '"' + http.STATUS_CODES[503] + '"'); 
    }else{ 
     res.send(title); 
    } 
}); 

app.listen(3000, function(){ 
    console.log("Server running at port: 3000") 
}); 


Основной вопрос я Имею прямо сейчас:

  1. Программа не возвращает ничего из модуля, даже если конечный console.log в модуле погоды печатает правый объект resultSet.
  2. Сервер не ожидает возвращения модуля и продолжает печатать данные.

Может кто-то обеспечить рабочее исправление на любой из этих проблем, я был бы очень благодарен, Это действительно препятствует мой прогресс и сломался мой боевой дух немного :(

ответ

0

Ваша проблема заключается в том, что вы используете асинхронный . функции, как если бы они были синхронны

это может быть не только вопрос здесь, но эта функция особенно проблематична:

function get(zipCode){ 
    var results = connectToGoogleGEO(zipCode, connectToForecastIO); 
    return results; 
} 

connectToGoogleGEO() звонки the asynchronous https.get() function и не возвращает данные, которые извлекаются из Google. Вам необходимо переписать код, чтобы он не ожидал, что данные будут возвращены функцией. Вместо этого вам необходимо передать обратный вызов, который будет обрабатывать данные.

Позаботьтесь о том, когда вы вызываете асинхронные функции и как работают их обратные вызовы. Это принципиально при работе с Node.js

 Смежные вопросы

  • Нет связанных вопросов^_^