Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/426.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 函数内部未更新全局变量_Javascript_Node.js - Fatal编程技术网

Javascript 函数内部未更新全局变量

Javascript 函数内部未更新全局变量,javascript,node.js,Javascript,Node.js,给定以下代码 var base64 = '' const AWS = require('aws-sdk') let awsConfig = { 'region': 'us-west-2', 'endpoint': 'http://dynamodb.us-west-2.amazonaws.com', 'accessKeyId': 'ABCDEFGHIJKLMANOPQRSTUVWXYZ', 'secretAccessKey': 'ABCDABSDJFGJALGJADSLGJALKD

给定以下代码

var base64 = ''
const AWS = require('aws-sdk')
let awsConfig = {
  'region': 'us-west-2',
  'endpoint': 'http://dynamodb.us-west-2.amazonaws.com',
  'accessKeyId': 'ABCDEFGHIJKLMANOPQRSTUVWXYZ',
  'secretAccessKey': 'ABCDABSDJFGJALGJADSLGJALKDJGALKSDJGLA'
}

AWS.config.update(awsConfig)

let docClient = new AWS.DynamoDB.DocumentClient()

let fetchOneByKey = function () {
  var params = {
    TableName: 'test',
    Key: {
      'key1': 'abc'
    }
  }
  docClient.get(params, function (err, data) {
    if (err) {
      console.log('test::fetchOneByKey::error - ' + err)
    } else {
      base64 = data.Item.b.toString('base64')
    }
  })
}

fetchOneByKey()
console.log(base64)
出于某种原因,我的变量
base64
不打印任何内容。这很奇怪,因为当我执行
console.log(data.Item.b.toString('base64')
时,它会打印
base64
字符串,所以我知道数据肯定不是空的

由于某些原因,我的变量没有得到更新,我也不知道为什么。我显然在调用函数
fetchOneByKey()
,因此理论上
base64
应该得到更新,但它没有得到更新。

docClient.get()
是异步的。通过调用
console.log()
调用函数后,在从DB读取完成之前立即执行该函数,因此不会更新变量

在此处调用console.log(base64)

else {
  base64 = data.Item.b.toString('base64')
  console.log(base64)
}
如果您想摆脱回调并使用承诺,那么可以使用。使用它,您可以将其转换为承诺,并与
async/await
一起使用,或者与
一起使用。then()

或者你也可以手工做出承诺

let fetchOneByKey = function () {
  var params = {
    TableName: 'test',
    Key: {
      'key1': 'abc'
    }
  }
  return new Promise((resolve, reject) => {
    docClient.get(params, function (err, data) {
      if (err) {
        console.log('test::fetchOneByKey::error - ' + err)
        reject(err)
      } else {
        base64 = data.Item.b.toString('base64')
        resolve(base64)
      }
    })
  }
}
然后您可以说
base64=wait fetchOneByKey();
或者,如果您不在
async
函数中,则可以执行
fetchOneByKey()。然后(base64=>console.log(base64))

编辑: 正如@AZ_u所提到的,
aws sdk
支持承诺

let fetchOneByKey = async function () {
  var params = {
    ...
  }
  const data = await docClient.get(params).promise();
  base64 = data.Item.b.toString('base64');
  return base64
}
docClient.get()
是异步的。通过在调用函数后立即调用
console.log()
,可以在从数据库读取完成之前执行该函数,因此不会更新变量

在此处调用console.log(base64)

else {
  base64 = data.Item.b.toString('base64')
  console.log(base64)
}
如果您想摆脱回调并使用承诺,那么可以使用。使用它,您可以将其转换为承诺,并与
async/await
一起使用,或者与
一起使用。then()

或者你也可以手工做出承诺

let fetchOneByKey = function () {
  var params = {
    TableName: 'test',
    Key: {
      'key1': 'abc'
    }
  }
  return new Promise((resolve, reject) => {
    docClient.get(params, function (err, data) {
      if (err) {
        console.log('test::fetchOneByKey::error - ' + err)
        reject(err)
      } else {
        base64 = data.Item.b.toString('base64')
        resolve(base64)
      }
    })
  }
}
然后您可以说
base64=wait fetchOneByKey();
或者,如果您不在
async
函数中,则可以执行
fetchOneByKey()。然后(base64=>console.log(base64))

编辑: 正如@AZ_u所提到的,
aws sdk
支持承诺

let fetchOneByKey = async function () {
  var params = {
    ...
  }
  const data = await docClient.get(params).promise();
  base64 = data.Item.b.toString('base64');
  return base64
}


您正试图在调用
docClient.get()之前记录
base64
变量
运行。您的
控制台.log
不在分配
base64
的回调范围内。变量已更新,但您正在更新之前读取值。@Tyleroper如何确保更新发生,以便更新我的var?任何依赖于
docClient.get()结果的内容
应在回调内启动,或在
等待结果后启动。您正在尝试在
docClient.get()的回调之前记录
base64
变量
运行。您的
控制台.log
不在分配
base64
的回调范围内。变量已更新,但您正在更新之前读取值。@Tyleroper如何确保更新发生,以便更新我的var?任何依赖于
docClient.get()结果的内容
应该在回调中启动,或者在等待结果之后启动。是的,我知道这是可行的,但我想在函数外部使用该变量。@Dinero使用promisify并将该回调变成承诺。然后可以使用async/await或将其链接到。然后()你能编辑和显示吗?我从来没有使用过我编辑过的。你现在能试试吗?
aws sdk
已经提供了承诺包装器。因此不需要单独的
新承诺…
。是的,我知道这是可行的,但我想在函数之外使用该变量。@Dinero使用promisify并将该回调变成承诺。然后你可以使用async/wait or您可以将其链接到。然后()您可以编辑和显示吗?我从未使用过我编辑过的。您现在可以尝试吗?
aws sdk
已经提供了承诺包装器。因此不需要单独的
新承诺…