Yêu cầu đồng bộ trong Node.js


99

Nếu tôi cần gọi 3 API http theo thứ tự tuần tự, thì mã nào sẽ là giải pháp thay thế tốt hơn cho mã sau:

http.get({ host: 'www.example.com', path: '/api_1.php' }, function(res) { 
  res.on('data', function(d) { 

    http.get({ host: 'www.example.com', path: '/api_2.php' }, function(res) { 
      res.on('data', function(d) { 

        http.get({ host: 'www.example.com', path: '/api_3.php' }, function(res) { 
          res.on('data', function(d) { 


          });
        });
        }
      });
    });
    }
  });
});
}

ngoài việc dọn dẹp nó, tôi không nghĩ bạn có thể làm tốt hơn thế.
hvgotcodes

2
Tại sao họ cần phải theo thứ tự?
Raynos

11
@Raynos Bạn có thể cần một số dữ liệu từ api_1 trước khi bạn biết những gì để gửi đến api_2
andyortlieb

9
Nó đáng nói rằng tương lai là khá bị phản đối, xem xét sử dụng một thư viện mới hơn như Bluebird hoặc Q.
Benjamin Gruenbaum

1
Tiêu đề và câu hỏi mâu thuẫn với nhau. Bạn không mô tả một yêu cầu đồng bộ trong câu hỏi của mình mà là một chuỗi các yêu cầu, thông thường mỗi yêu cầu sẽ xảy ra không đồng bộ. Sự khác biệt lớn - khối lệnh gọi đồng bộ và chuỗi các hành động không đồng bộ không chặn (chặn giao diện người dùng, chặn máy chủ xử lý các yêu cầu khác). Có một câu trả lời bên dưới đề cập đến sync-requestthư viện, đây là câu trả lời hay cho tiêu đề của câu hỏi này, nhưng không phải là câu trả lời cho những gì mã của câu hỏi ngụ ý. Câu trả lời dưới đây về Promises là câu trả lời tốt hơn cho điều đó. Ý bạn là gì?
Jake

Câu trả lời:


69

Sử dụng trả chậm như thế nào Futures.

var sequence = Futures.sequence();

sequence
  .then(function(next) {
     http.get({}, next);
  })
  .then(function(next, res) {
     res.on("data", next);
  })
  .then(function(next, d) {
     http.get({}, next);
  })
  .then(function(next, res) {
    ...
  })

Nếu bạn cần vượt qua phạm vi thì chỉ cần làm điều gì đó như thế này

  .then(function(next, d) {
    http.get({}, function(res) {
      next(res, d);
    });
  })
  .then(function(next, res, d) { })
    ...
  })

Vui lòng thử IcedCoffeScript để cung cấp sự chờ đợi và trì hoãn cho nodejs.
Thanigainathan

Đây có phải là không chặn? Ý tôi là nó đang chặn cho hàm tiếp theo trong dòng nhưng điều này sẽ không chặn việc thực thi các hàm không đồng bộ khác, phải không?
Oktav

1
Có, các phương pháp hoãn lại là không chặn / không đồng bộ.
dvlsg

4
API ES6 Promise hiệu quả nên thay thế này, thậm chí theo các tác giả của "tương lai"
Alexander Mills

Hợp đồng tương lai đã rất cũ và không còn được chấp nhận. Xem q thay thế.
Jim Aho

53

Tôi cũng thích giải pháp của Raynos, nhưng tôi thích một thư viện điều khiển luồng khác.

https://github.com/caolan/async

Tùy thuộc vào việc bạn cần kết quả trong mỗi chức năng tiếp theo, tôi sẽ sử dụng chuỗi, song song hoặc thác nước.

Loạt khi chúng phải được thực thi theo thứ tự, nhưng bạn không nhất thiết cần kết quả trong mỗi lần gọi hàm tiếp theo.

Song song, tương đông nếu chúng có thể được thực thi song song, bạn không cần kết quả từ mỗi hàm trong mỗi hàm song song và bạn cần gọi lại khi tất cả đã hoàn thành.

Waterfall nếu bạn muốn biến đổi các kết quả trong mỗi hàm và chuyển sang phần tiếp theo

endpoints = 
 [{ host: 'www.example.com', path: '/api_1.php' },
  { host: 'www.example.com', path: '/api_2.php' },
  { host: 'www.example.com', path: '/api_3.php' }];

async.mapSeries(endpoints, http.get, function(results){
    // Array of results
});

9
var http = request ('http');
Elle Mundy

7
Hả. example.com thực sự là một miền được thiết kế cho loại điều này. Chà.
woppl

Mã async.series không hoạt động, ít nhất là với async v0.2.10. series () chỉ nhận tối đa hai đối số và sẽ thực thi các phần tử của đối số đầu tiên dưới dạng hàm, do đó, async gây ra lỗi khi cố gắng thực thi các đối tượng dưới dạng hàm.
nắp

1
Bạn có thể làm điều gì đó tương tự như những gì dự định với mã này bằng forEachAsync ( github.com/FuturesJS/forEachAsync ).
nắp

Điều này thực hiện chính xác những gì tôi muốn. Cảm ơn bạn!
aProperFox 21/09/15

33

Bạn có thể làm điều này bằng cách sử dụng thư viện Common Node của tôi :

function get(url) {
  return new (require('httpclient').HttpClient)({
    method: 'GET',
      url: url
    }).finish().body.read().decodeToString();
}

var a = get('www.example.com/api_1.php'), 
    b = get('www.example.com/api_2.php'),
    c = get('www.example.com/api_3.php');

3
tào lao, Tôi upvoted nghĩ nó sẽ làm việc và nó không :(require(...).HttpClient is not a constructor
moeiscool

30

đồng bộ-yêu cầu

Cho đến nay, cách dễ nhất mà tôi đã tìm thấy và sử dụng là sync-request và nó hỗ trợ cả nút và trình duyệt!

var request = require('sync-request');
var res = request('GET', 'http://google.com');
console.log(res.body.toString('utf-8'));

Vậy đó, không cần cấu hình điên rồ, không cần cài đặt lib phức tạp, mặc dù nó có dự phòng lib. Chỉ hoạt động. Tôi đã thử các ví dụ khác ở đây và bị bối rối khi có nhiều thiết lập bổ sung để thực hiện hoặc cài đặt không hoạt động!

Ghi chú:

Ví dụ mà sync-request sử dụng không hoạt động tốt khi bạn sử dụng res.getBody(), tất cả những gì get body làm là chấp nhận mã hóa và chuyển đổi dữ liệu phản hồi. res.body.toString(encoding)Thay vào đó chỉ cần làm .


Tôi thấy rằng yêu cầu đồng bộ hóa rất chậm .. Tôi đã kết thúc bằng cách sử dụng một github.com/dhruvbird/http-sync khác , nhanh hơn 10 lần trong trường hợp của tôi.
Filip Spiridonov

tôi đã không có bất kỳ chạy chậm cho nó. Quá trình này sinh ra một quá trình con. Hệ thống của bạn sử dụng bao nhiêu CPU và bạn đang sử dụng phiên bản nút nào? Tôi muốn biết để xác định xem mình có cần chuyển đổi hay không.
jemiloii

Tôi đồng ý với Filip, điều này là chậm.
Rambo7

Điều tương tự mà tôi đã hỏi flip nhưng không nhận được phản hồi: Hệ thống của bạn sử dụng bao nhiêu cp và bạn đang sử dụng phiên bản nút nào?
jemiloii

Điều này sử dụng một lượng lớn CPU, không được khuyến khích sử dụng trong sản xuất.
moeiscool

20

Tôi sẽ sử dụng một hàm đệ quy với một danh sách các apis

var APIs = [ '/api_1.php', '/api_2.php', '/api_3.php' ];
var host = 'www.example.com';

function callAPIs ( host, APIs ) {
  var API = APIs.shift();
  http.get({ host: host, path: API }, function(res) { 
    var body = '';
    res.on('data', function (d) {
      body += d; 
    });
    res.on('end', function () {
      if( APIs.length ) {
        callAPIs ( host, APIs );
      }
    });
  });
}

callAPIs( host, APIs );

chỉnh sửa: phiên bản yêu cầu

var request = require('request');
var APIs = [ '/api_1.php', '/api_2.php', '/api_3.php' ];
var host = 'www.example.com';
var APIs = APIs.map(function (api) {
  return 'http://' + host + api;
});

function callAPIs ( host, APIs ) {
  var API = APIs.shift();
  request(API, function(err, res, body) { 
    if( APIs.length ) {
      callAPIs ( host, APIs );
    }
  });
}

callAPIs( host, APIs );

chỉnh sửa: phiên bản request / async

var request = require('request');
var async = require('async');
var APIs = [ '/api_1.php', '/api_2.php', '/api_3.php' ];
var host = 'www.example.com';
var APIs = APIs.map(function (api) {
  return 'http://' + host + api;
});

async.eachSeries(function (API, cb) {
  request(API, function (err, res, body) {
    cb(err);
  });
}, function (err) {
  //called when all done, or error occurs
});

Đây là phương pháp tôi đã sử dụng vì tôi có một danh sách thay đổi các yêu cầu phải thực hiện (600 mục và ngày càng tăng). Điều đó nói rằng, có vấn đề với mã của bạn: sự kiện 'dữ liệu' sẽ được phát ra nhiều lần cho mỗi yêu cầu nếu đầu ra API lớn hơn kích thước phân đoạn. Bạn muốn "đệm" dữ liệu như vậy: var body = ''; res.on ('data', function (data) {body + = data;}). on ('end', function () {callback (body); if (APIs.length) callAPIs (host, APIs);} );
Ankit Aggarwal

Đã cập nhật. Tôi chỉ muốn chỉ ra cách vấn đề có thể trở nên đơn giản / linh hoạt hơn thông qua đệ quy. Cá nhân tôi luôn sử dụng mô-đun yêu cầu cho loại việc này vì nó cho phép bạn dễ dàng bỏ qua nhiều lần gọi lại.
Generalhenry

@generalhenry, tôi sẽ làm như thế nào nếu muốn sử dụng mô-đun yêu cầu? Bạn có thể cung cấp đoạn mã đạt được yêu cầu ở trên không?
Scotty

Tôi đã thêm phiên bản yêu cầu và phiên bản yêu cầu / không đồng bộ.
generalhenry

5

Có vẻ như các giải pháp cho vấn đề này là không bao giờ kết thúc, đây là một giải pháp nữa :)

// do it once.
sync(fs, 'readFile')

// now use it anywhere in both sync or async ways.
var data = fs.readFile(__filename, 'utf8')

http://alexeypetrushin.github.com/synchronize


Mặc dù thư viện bạn đã liên kết CÓ cung cấp giải pháp cho vấn đề của OP, trong ví dụ của bạn, fs.readFile luôn đồng bộ hóa.
Eric

1
Không, bạn có thể cung cấp lệnh gọi lại một cách rõ ràng và sử dụng nó như phiên bản không đồng bộ nếu bạn muốn.
Alex Craft,

1
ví dụ cho các yêu cầu http, không phải giao tiếp hệ thống tệp.
Seth

5

Một khả năng khác là thiết lập một cuộc gọi lại để theo dõi các tác vụ đã hoàn thành:

function onApiResults(requestId, response, results) {
    requestsCompleted |= requestId;

    switch(requestId) {
        case REQUEST_API1:
            ...
            [Call API2]
            break;
        case REQUEST_API2:
            ...
            [Call API3]
            break;
        case REQUEST_API3:
            ...
            break;
    }

    if(requestId == requestsNeeded)
        response.end();
}

Sau đó, chỉ cần gán một ID cho mỗi ID và bạn có thể thiết lập các yêu cầu của mình cho những tác vụ nào phải hoàn thành trước khi đóng kết nối.

const var REQUEST_API1 = 0x01;
const var REQUEST_API2 = 0x02;
const var REQUEST_API3 = 0x03;
const var requestsNeeded = REQUEST_API1 | REQUEST_API2 | REQUEST_API3;

Được rồi, nó không đẹp. Nó chỉ là một cách khác để thực hiện các cuộc gọi tuần tự. Thật không may là NodeJS không cung cấp các lệnh gọi đồng bộ cơ bản nhất. Nhưng tôi hiểu sự thu hút đối với sự không đồng bộ là gì.


4

sử dụng tuần tự.

sudo npm install sequenty

hoặc là

https://github.com/AndyShin/sequenty

rất đơn giản.

var sequenty = require('sequenty'); 

function f1(cb) // cb: callback by sequenty
{
  console.log("I'm f1");
  cb(); // please call this after finshed
}

function f2(cb)
{
  console.log("I'm f2");
  cb();
}

sequenty.run([f1, f2]);

bạn cũng có thể sử dụng một vòng lặp như sau:

var f = [];
var queries = [ "select .. blah blah", "update blah blah", ...];

for (var i = 0; i < queries.length; i++)
{
  f[i] = function(cb, funcIndex) // sequenty gives you cb and funcIndex
  {
    db.query(queries[funcIndex], function(err, info)
    {
       cb(); // must be called
    });
  }
}

sequenty.run(f); // fire!

3

Sử dụng thư viện yêu cầu có thể giúp giảm thiểu vấn đề:

var request = require('request')

request({ uri: 'http://api.com/1' }, function(err, response, body){
    // use body
    request({ uri: 'http://api.com/2' }, function(err, response, body){
        // use body
        request({ uri: 'http://api.com/3' }, function(err, response, body){
            // use body
        })
    })
})

Nhưng để đạt được sự tuyệt vời tối đa, bạn nên thử một số thư viện luồng điều khiển như Step - nó cũng sẽ cho phép bạn song song hóa các yêu cầu, giả sử rằng nó có thể chấp nhận được:

var request = require('request')
var Step    = require('step')

// request returns body as 3rd argument
// we have to move it so it works with Step :(
request.getBody = function(o, cb){
    request(o, function(err, resp, body){
        cb(err, body)
    })
}

Step(
    function getData(){
        request.getBody({ uri: 'http://api.com/?method=1' }, this.parallel())
        request.getBody({ uri: 'http://api.com/?method=2' }, this.parallel())
        request.getBody({ uri: 'http://api.com/?method=3' }, this.parallel())
    },
    function doStuff(err, r1, r2, r3){
        console.log(r1,r2,r3)
    }
)

3

Kể từ năm 2018 và sử dụng các mô-đun ES6 và Promises, chúng ta có thể viết một hàm như vậy:

import { get } from 'http';

export const fetch = (url) => new Promise((resolve, reject) => {
  get(url, (res) => {
    let data = '';
    res.on('end', () => resolve(data));
    res.on('data', (buf) => data += buf.toString());
  })
    .on('error', e => reject(e));
});

và sau đó trong một mô-đun khác

let data;
data = await fetch('http://www.example.com/api_1.php');
// do something with data...
data = await fetch('http://www.example.com/api_2.php');
// do something with data
data = await fetch('http://www.example.com/api_3.php');
// do something with data

Mã cần được thực thi trong ngữ cảnh không đồng bộ (sử dụng asynctừ khóa)


2

Có rất nhiều thư viện luồng điều khiển - Tôi thích conseq (... vì tôi đã viết nó.) Ngoài ra, on('data')có thể kích hoạt nhiều lần, vì vậy hãy sử dụng thư viện trình bao bọc REST như trình phục hồi .

Seq()
  .seq(function () {
    rest.get('http://www.example.com/api_1.php').on('complete', this.next);
  })
  .seq(function (d1) {
    this.d1 = d1;
    rest.get('http://www.example.com/api_2.php').on('complete', this.next);
  })
  .seq(function (d2) {
    this.d2 = d2;
    rest.get('http://www.example.com/api_3.php').on('complete', this.next);
  })
  .seq(function (d3) {
    // use this.d1, this.d2, d3
  })

2

Điều này đã được trả lời tốt bởi Raynos. Tuy nhiên, đã có những thay đổi trong thư viện trình tự kể từ khi câu trả lời được đăng.

Để trình tự hoạt động, hãy nhấp vào liên kết sau: https://github.com/FuturesJS/sequence/tree/9daf0000289954b85c0925119821752fbfb3521e .

Đây là cách bạn có thể làm cho nó hoạt động sau khi npm install sequence:

var seq = require('sequence').Sequence;
var sequence = seq.create();

seq.then(function call 1).then(function call 2);

1

Đây là phiên bản @ andy-shin của tôi tuần tự với các đối số trong mảng thay vì chỉ mục:

function run(funcs, args) {
    var i = 0;
    var recursive = function() {
        funcs[i](function() {
            i++;
            if (i < funcs.length)
                recursive();
        }, args[i]);
    };
    recursive();
}

1

... 4 năm sau ...

Đây là một giải pháp ban đầu với khung công tác Danf (bạn không cần bất kỳ mã nào cho những thứ này, chỉ cần một số cấu hình):

// config/common/config/sequences.js

'use strict';

module.exports = {
    executeMySyncQueries: {
        operations: [
            {
                order: 0,
                service: 'danf:http.router',
                method: 'follow',
                arguments: [
                    'www.example.com/api_1.php',
                    'GET'
                ],
                scope: 'response1'
            },
            {
                order: 1,
                service: 'danf:http.router',
                method: 'follow',
                arguments: [
                    'www.example.com/api_2.php',
                    'GET'
                ],
                scope: 'response2'
            },
            {
                order: 2,
                service: 'danf:http.router',
                method: 'follow',
                arguments: [
                    'www.example.com/api_3.php',
                    'GET'
                ],
                scope: 'response3'
            }
        ]
    }
};

Sử dụng cùng một ordergiá trị cho các hoạt động bạn muốn được thực hiện song song.

Nếu bạn muốn ngắn hơn nữa, bạn có thể sử dụng quy trình thu thập:

// config/common/config/sequences.js

'use strict';

module.exports = {
    executeMySyncQueries: {
        operations: [
            {
                service: 'danf:http.router',
                method: 'follow',
                // Process the operation on each item
                // of the following collection.
                collection: {
                    // Define the input collection.
                    input: [
                        'www.example.com/api_1.php',
                        'www.example.com/api_2.php',
                        'www.example.com/api_3.php'
                    ],
                    // Define the async method used.
                    // You can specify any collection method
                    // of the async lib.
                    // '--' is a shorcut for 'forEachOfSeries'
                    // which is an execution in series.
                    method: '--'
                },
                arguments: [
                    // Resolve reference '@@.@@' in the context
                    // of the input item.
                    '@@.@@',
                    'GET'
                ],
                // Set the responses in the property 'responses'
                // of the stream.
                scope: 'responses'
            }
        ]
    }
};

Hãy xem tổng quan về khuôn khổ để biết thêm thông tin.


1

Tôi hạ cánh ở đây vì tôi cần giới hạn tỷ lệ http.request (~ 10k truy vấn tổng hợp cho tìm kiếm đàn hồi để xây dựng báo cáo phân tích). Sau đây chỉ làm nghẹt máy của tôi.

for (item in set) {
    http.request(... + item + ...);
}

Các URL của tôi rất đơn giản nên điều này có thể không áp dụng cho câu hỏi ban đầu nhưng tôi nghĩ rằng nó vừa có khả năng áp dụng được vừa đáng để viết ở đây cho những độc giả gặp vấn đề tương tự như của tôi và những người muốn có một giải pháp không thư viện JavaScript tầm thường.

Công việc của tôi không phụ thuộc vào thứ tự và cách tiếp cận đầu tiên của tôi để kết thúc điều này là bọc nó trong một tập lệnh shell để phân đoạn nó (vì tôi mới làm quen với JavaScript). Đó là chức năng nhưng không đạt yêu cầu. Cuối cùng, giải pháp JavaScript của tôi là làm như sau:

var stack=[];
stack.push('BOTTOM');

function get_top() {
  var top = stack.pop();
  if (top != 'BOTTOM')
    collect(top);
}

function collect(item) {
    http.request( ... + item + ...
    result.on('end', function() {
      ...
      get_top();
    });
    );
}

for (item in set) {
   stack.push(item);
}

get_top();

Nó giống như đệ quy lẫn nhau giữa thu thậpget_top . Tôi không chắc nó có hiệu lực không vì hệ thống không đồng bộ và hàm thu thập hoàn tất với lệnh gọi lại được lưu trữ cho sự kiện lúc bật. ('End' .

Tôi nghĩ rằng nó là đủ chung để áp dụng cho câu hỏi ban đầu. Nếu, giống như kịch bản của tôi, trình tự / tập hợp được biết, tất cả các URL / khóa có thể được đẩy lên ngăn xếp trong một bước. Nếu chúng được tính khi bạn tiếp tục, hàm on ('end' có thể đẩy url tiếp theo lên ngăn xếp ngay trước get_top () . Nếu có, kết quả có ít lồng hơn và có thể dễ dàng cấu trúc lại khi API bạn đang gọi những thay đổi.

Tôi nhận ra rằng điều này tương đương với phiên bản đệ quy đơn giản của @ generalhenry ở trên (vì vậy tôi đã ủng hộ điều đó!)


0

Yêu cầu siêu

Đây là một mô-đun đồng bộ khác dựa trên yêu cầu và sử dụng các lời hứa. Sử dụng siêu đơn giản, hoạt động tốt với các bài kiểm tra mocha.

npm install super-request

request("http://domain.com")
    .post("/login")
    .form({username: "username", password: "password"})
    .expect(200)
    .expect({loggedIn: true})
    .end() //this request is done 
    //now start a new one in the same session 
    .get("/some/protected/route")
    .expect(200, {hello: "world"})
    .end(function(err){
        if(err){
            throw err;
        }
    });

0

Mã này có thể được sử dụng để thực hiện một loạt các lời hứa một cách đồng bộ & tuần tự, sau đó bạn có thể thực thi mã cuối cùng của mình trong .then()cuộc gọi.

const allTasks = [() => promise1, () => promise2, () => promise3];

function executePromisesSync(tasks) {
  return tasks.reduce((task, nextTask) => task.then(nextTask), Promise.resolve());
}

executePromisesSync(allTasks).then(
  result => console.log(result),
  error => console.error(error)
);

0

Tôi thực sự có được chính xác những gì bạn (và tôi) muốn, mà không cần sử dụng sự chờ đợi, Hứa hẹn hoặc bao gồm bất kỳ thư viện (bên ngoài) nào (ngoại trừ thư viện của chúng tôi).

Đây là cách thực hiện:

Chúng ta sẽ tạo một mô-đun C ++ để đi với node.js và chức năng mô-đun C ++ đó sẽ thực hiện yêu cầu HTTP và trả về dữ liệu dưới dạng một chuỗi và bạn có thể sử dụng trực tiếp bằng cách thực hiện:

var myData = newModule.get(url);

BẠN ĐÃ SN SÀNG để bắt đầu?

Bước 1: Tạo một thư mục mới ở một nơi khác trên máy tính của bạn, chúng tôi chỉ sử dụng thư mục này để xây dựng tệp module.node (được biên dịch từ C ++), bạn có thể di chuyển nó sau.

Trong thư mục mới (tôi đặt của tôi trong mynewFolder / src cho tổ chức-ness):

npm init

sau đó

npm install node-gyp -g

bây giờ tạo 2 tệp mới: 1, được gọi là something.cpp và đặt mã này vào đó (hoặc sửa đổi nếu bạn muốn):

#pragma comment(lib, "urlmon.lib")
#include <sstream>
#include <WTypes.h>  
#include <node.h>
#include <urlmon.h> 
#include <iostream>
using namespace std;
using namespace v8;

Local<Value> S(const char* inp, Isolate* is) {
    return String::NewFromUtf8(
        is,
        inp,
        NewStringType::kNormal
    ).ToLocalChecked();
}

Local<Value> N(double inp, Isolate* is) {
    return Number::New(
        is,
        inp
    );
}

const char* stdStr(Local<Value> str, Isolate* is) {
    String::Utf8Value val(is, str);
    return *val;
}

double num(Local<Value> inp) {
    return inp.As<Number>()->Value();
}

Local<Value> str(Local<Value> inp) {
    return inp.As<String>();
}

Local<Value> get(const char* url, Isolate* is) {
    IStream* stream;
    HRESULT res = URLOpenBlockingStream(0, url, &stream, 0, 0);

    char buffer[100];
    unsigned long bytesReadSoFar;
    stringstream ss;
    stream->Read(buffer, 100, &bytesReadSoFar);
    while(bytesReadSoFar > 0U) {
        ss.write(buffer, (long long) bytesReadSoFar);
        stream->Read(buffer, 100, &bytesReadSoFar);
    }
    stream->Release();
    const string tmp = ss.str();
    const char* cstr = tmp.c_str();
    return S(cstr, is);
}

void Hello(const FunctionCallbackInfo<Value>& arguments) {
    cout << "Yo there!!" << endl;

    Isolate* is = arguments.GetIsolate();
    Local<Context> ctx = is->GetCurrentContext();

    const char* url = stdStr(arguments[0], is);
    Local<Value> pg = get(url,is);

    Local<Object> obj = Object::New(is);
    obj->Set(ctx,
        S("result",is),
        pg
    );
    arguments.GetReturnValue().Set(
       obj
    );

}

void Init(Local<Object> exports) {
    NODE_SET_METHOD(exports, "get", Hello);
}

NODE_MODULE(cobypp, Init);

Bây giờ hãy tạo một tệp mới trong cùng một thư mục được gọi something.gypvà đặt (một cái gì đó giống như) trong đó:

{
   "targets": [
       {
           "target_name": "cobypp",
           "sources": [ "src/cobypp.cpp" ]
       }
   ]
}

Bây giờ trong tệp package.json, hãy thêm: "gypfile": true,

Bây giờ: trong bảng điều khiển, node-gyp rebuild

Nếu nó đi qua toàn bộ lệnh và nói "ok" ở cuối mà không có lỗi, bạn (gần như) tốt để tiếp tục, nếu không, hãy để lại nhận xét ..

Nhưng nếu nó hoạt động thì hãy truy cập build / Release / cobypp.node (hoặc bất cứ thứ gì nó được gọi cho bạn), sao chép nó vào thư mục node.js chính của bạn, sau đó trong node.js:

var myCPP = require("./cobypp")
var myData = myCPP.get("http://google.com").result;
console.log(myData);

..

response.end(myData);//or whatever
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.