2016-06-16 6 views
0

チップで私を助けることができます:D。ここに私のコードです:私のnodejsスクリプトで何かが間違っています

const request = require('request'); 
const cheerio = require('cheerio'); 

function getUrls(url) { 
    const baseUrl = 'https://unsplash.com'; 
    let urls = []; 
    request(url, (err, res, body) => { 
     if (!err && res.statusCode === 200) { 
      const $ = cheerio.load(body, { normalizeWhitespace: false, xmlMode: false, decodeEntities: true }); 
      $('.photo.qa-photo a').each((i, e) => { 
       const lnk = $(e).attr('href'); 
       if (lnk.indexOf('@') === -1 && lnk.indexOf('download') === -1) { 
        urls.push(baseUrl + lnk); 
       } 
      }); 
     } 
    }); 
    return urls; 
} 

function getImages(arr) { 
    let images = []; 
    for (const url of arr) { 
     request(url, (err, res, body) => { 
      if (!err && res.statusCode === 200) { 
       const $ = cheerio.load(body, { normalizeWhitespace: false, xmlMode: false, decodeEntities: true }); 
       $('script').each((i, e) => { 
        if (i === 4) { 
         let img = $(e).text(); 
         img = img.substring(img.indexOf('full') + 7, img.indexOf('regular') - 3); 
         images.push(img); 
        } 
       }); 
      } else { 
       console.log(err, res.statusCode); 
      } 
     }); 
    } 
    return images; 
} 

console.log(getImages(getUrls('https://unsplash.com/search?utf8=%E2%9C%93&keyword=life&button='))); 

別に機能がうまく働いているが、私は両方の機能を結合したい場合はまず機能が作業を終えるが、私は返される配列を参照してくださいカント私に空の配列を示したにconsole.log、なぜ?私の英語のために申し訳ありません。 この小さなプログラムで、私はunsplash.comから完全に20画像のURLを取得したい Tyを事前に。

+0

[非同期呼び出しからの応答を返すにはどうすればよいですか?](http://stackoverflow.com/questions/14220321/how-do-i-return-the-response-from-an-asynchronous-コール) –

答えて

0

JavaScriptは非同期言語です。ここでは、getImages関数がgetUrls関数が終了するのを待つことがありません。

getImages関数でコールバックまたは約束を使用する必要がありますので、getUrlsを待ちます。コールバック

コールバックの

Hereの少しのチュートリアルは、JavaScriptで本当に重要な概念であり、私は強くあなたはそれがどのように動作するかを学ぶお勧めします。あなたの人生を楽にします。約束は同じです。

は、ここで私はそれをテストしていないあなたのコード

const request = require('request'); 
const cheerio = require('cheerio'); 

// callback is the function to be called when this one finishes 
function getUrls(url, callback) { 
    const baseUrl = 'https://unsplash.com'; 
    let urls = []; 
    request(url, (err, res, body) => { 
     if (!err && res.statusCode === 200) { 
      const $ = cheerio.load(body, { normalizeWhitespace: false, xmlMode: false, decodeEntities: true }); 
      $('.photo.qa-photo a').each((i, e) => { 
       const lnk = $(e).attr('href'); 
       if (lnk.indexOf('@') === -1 && lnk.indexOf('download') === -1) { 
        urls.push(baseUrl + lnk); 
       } 
      }); 
     } 
    }); 
    //Notice the call to callback. 
    callback(urls); 
} 
function getImages(arr) { 
    let images = []; 
    for (const url of arr) { 
     request(url, (err, res, body) => { 
      if (!err && res.statusCode === 200) { 
       const $ = cheerio.load(body, { normalizeWhitespace: false, xmlMode: false, decodeEntities: true }); 
       $('script').each((i, e) => { 
        if (i === 4) { 
         let img = $(e).text(); 
         img = img.substring(img.indexOf('full') + 7, img.indexOf('regular') - 3); 
         images.push(img); 
        } 
       }); 
      } else { 
       console.log(err, res.statusCode); 
      } 
     }); 
    } 
    return images; 
} 

console.log(getUrls('https://unsplash.com/search?utf8=%E2%9C%93&keyword=life&button=', function(urls){getImages(urls)})); 

との一例だが、それは仕事をしたり、十分近いはずです。

+0

なぜdownvote? – ChandlerBing42

+0

このコードには少しの例がありますか? –

+0

あなたは行き​​ます。私はあなたのコードを使用しました。しかし、してください、単にそれをunsingの代わりに何を理解しようとします。コールバック/約束はJSのバックボーンです。 – ChandlerBing42

0

Bacauseリクエスト関数は非同期的に呼び出します。そのため、親関数(getUrls、getImages)は配列が埋め込まれる前に戻ります。コールバックを使用する必要があります。

+0

少しのサンプルを提供できますか?もちろんこのコードで) –

関連する問題