在流星中运行以下(简化的)代码时,我遇到了意外的行为:
import { HTTP } from 'meteor/http';
Fiber = Npm.require('fibers');
let x = {};
Fiber(function() {
x.a = 1;
let result = HTTP.get('https://jsonplaceholder.typicode.com/posts/1');
x.a = 2;
console.log('fiber finished!');
}).run();
console.log(x);
输出:
{ a: 1 }
fiber finished!
HTTP.get 根据其文档(应该是)同步的。我尝试使用另一个库而不是meteor/http,但得到了相同的结果。
看起来,当到达 HTTP 请求时,纤程内的执行就会停止,并在纤程外继续执行。只有在纤维外部完成后,它才会返回以完成在纤维内部开始的工作。
发生什么事了?如果没有上下文切换,如何在 Fiber 内发出 HTTP 请求?
2021年,纤维已停产:
更新 [2021 年 4 月 13 日] - Fibers 与 Nodejs v16.0.0 或更高版本不兼容。不幸的是,v8 提交 dacc2fee0f 是一个重大更改,解决方法并不简单。
2023 年,我编写了 [sync-request-curl](https://www.npmjs.com/package/sync-request-curl,这将有助于发送同步 HTTP 请求。
您可以安装该库
npm install sync-request-curl
sync-request-curl 包含原始 sync-request 中功能的子集,但利用 node-libcurl 以获得更好的性能和 NodeJS 的附加 libcurl 选项。
这是 GET 请求的基本用例:
// import request from 'sync-request-curl';
const request = require('sync-request-curl');
const response = request('GET', 'https://ipinfo.io/json');
console.log('Status Code:', response.statusCode);
console.log('body:', response.body.toString());
请查阅文档以获取更多示例。
在您的示例中,您可以按如下方式重写代码:
const request = require('sync-request-curl');
let x = {};
const makeRequest = () => {
x.a = 1;
const url = 'https://jsonplaceholder.typicode.com/posts/2';
const response = request('GET', url);
const json = JSON.parse(response.body.toString());
x.a = 2;
console.log('sync-request-curl finished:', json);
};
makeRequest();
console.log(x);
这给出了预期的结果:
sync-request-curl finished: {
userId: 1,
id: 2,
title: 'qui est esse',
body: 'est rerum tempore vitae\n' +
'sequi sint nihil reprehenderit dolor beatae ea dolores neque\n' +
'fugiat blanditiis voluptate porro vel nihil molestiae ut reiciendis\n' +
'qui aperiam non debitis possimus qui neque nisi nulla'
}
{ a: 2 }
希望这有帮助:)。