首页 > 解决方案 > 无法理解与 Promise 和范围相关的错误

问题描述

我正在为我配置为 js 学习练习的粒子光子开发一个小型 Web 前端。

我有一个错误,我不知道为什么。

在代码的前面,我使用粒子脚本登录https://docs.particle.io/reference/javascript/#with-username-password

var particle = new Particle();
var token;

particle.login({username: 'user@email.com', password: 'pass'}).then(
  function(data) {
    token = data.body.access_token;
  },
  function (err) {
    console.log('Could not log in.', err);
  }
);

在这个例子中,我使用particle.login(),然后立即使用.then。它工作得很好,我得到了我期望的令牌。

接下来我想列出我所有的设备,我使用文档中的示例代码来执行此操作:

var devicesPr = particle.listDevices({ auth: token });

devicesPr.then(
  function(devices){
    console.log('Devices: ', devices);
  },
  function(err) {
    console.log('List devices call failed: ', err);
  }
);

这也很完美。没问题。

这是我的问题:

我心想“哎呀,我为什么不干脆摆脱这个 var devicesPr 并立即调用它”。所以我尝试:

particle.listDevices({auth: token}).then(
    function(devices){
        console.log('Devices: ', devices);
    },
    function(err) {
        console.log('List of devices call failed: ', err);
    }
);

现在我收到一条错误消息:

init.js:23 List of devices call failed:  {statusCode: 400, errorDescription: "HTTP error 400 from /v1/devices - The access token was not found", error: Error: Unsuccessful HTTP response
    at Request.<anonymous> (http://cdn.jsdelivr.net/particle-api-j…, body: {…}}
init.js:11 API call completed on promise resolve: API KEY

所以我注意到,在生成身份验证令牌之前似乎正在执行对设备列表的请求。我认为这是有可能的,因为 Promise 的文档不断提到它们是异步的。

我只是很困惑,为什么当我先将其设为变量然后调用 .then 时我看不到相同的可能错误?如果我首先将承诺存储到变量中,它是否知道等待身份验证令牌存在?

谢谢!

我运行它时的完整故障代码:

"use strict";

//var Particle = require('particle-api-js');
var particle = new Particle();
var token;


particle.login({username: 'MYEMAIL', password:'MYPASSWORD'}).then(
  function(data){
    token = data.body.access_token;
    console.log('API call completed on promise resolve: ', token);
  },
  function(err) {
    console.log('API call completed on promise fail: ', err);
  }
);

particle.listDevices({auth: token}).then(
    function(devices){
        console.log('Devices: ', devices);
    },
    function(err) {
        console.log('List of devices call failed: ', err);
    }
);

标签: javascriptparticle.io

解决方案


您没有listDevicestokenget from链接particle.login- 您正在调用particle.listDevices synchronously,之前token已被填充。获取令牌的请求可能已经发送,但是.then填充的异步token肯定还没有运行。

取而代之的是,在 之后使用.then链接,如下所示:listDevicesparticle.login

var particle = new Particle();
particle.login({username: 'MYEMAIL', password:'MYPASSWORD'})
  .then(data => {
    const token = data.body.access_token;
    console.log('API call completed on promise resolve: ', token);
    // Return the listDevices promise so `.then` can be called on it below:
    return particle.listDevices({auth: token});
  })
  .catch(err => console.log('API call completed on promise fail: ', err))
  .then(devices => console.log('Devices: ', devices))
  .catch(console.log('List of devices call failed: ', err));

推荐阅读