You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node.js使用@azure/storage-blob SDK上传Azure Blob存储时出现NoAuthenticationInformation错误求助

解决Azure Blob存储上传时的"NoAuthenticationInformation"错误

看起来你遇到的核心问题是认证方式的混淆,以及代码里的几处小错误,导致上传操作无法正确通过Azure的认证。让我们一步步拆解问题并修复:

问题分析

  1. 错误的认证参数传递:你的createSharedAccessToken函数返回的是SAS令牌字符串,但在createBlob里,你把这个SAS字符串当作SharedKeyCredential实例传给了BlobServiceClient的构造函数。这是完全错误的——BlobServiceClient要么接受SharedKeyCredential对象(用账号名+密钥生成),要么接受包含SAS令牌的完整URL,而不是把SAS单独当作第二个参数。
  2. 未初始化的变量:createSharedAccessToken里的expiresOn变量没有提前声明就直接调用setMinutes,这会导致运行时错误,影响SAS令牌的生成。
  3. 权限可能不足:你传入的权限参数是'c'(对应Create权限),但上传Blob通常需要Create + Write权限(即权限字符'cw'),仅用'c'可能不足以完成上传操作。

修复方案

方案一:直接使用SharedKeyCredential认证(推荐,更简单)

既然你已经有存储账号的密钥,完全不需要生成SAS来完成上传操作,直接用SharedKeyCredential创建客户端即可,这样能避免SAS相关的错误:

const { BlobServiceClient, StorageSharedKeyCredential } = require("@azure/storage-blob");

module.exports.createBlob = (blobName, containerName, blobContent) => { 
  return new Promise(async (resolve, reject) => { 
    try { 
      // 直接用账号名和密钥创建SharedKeyCredential
      const sharedKeyCredential = new StorageSharedKeyCredential(
        process.env.AZURE_BLOB_ACCOUNT, 
        process.env.AZURE_BLOB_KEY
      );
      const blobServiceClient = new BlobServiceClient( 
        `https://${process.env.AZURE_BLOB_ACCOUNT}.blob.core.windows.net`, 
        sharedKeyCredential 
      ); 
      const containerClient = blobServiceClient.getContainerClient(containerName); 
      const blockBlobClient = containerClient.getBlockBlobClient(blobName); 
      // 上传内容,注意blobContent如果是Buffer或字符串都可以,length参数要正确
      const blobResponse = await blockBlobClient.upload(blobContent, Buffer.byteLength(blobContent)); 
      resolve(blobResponse); 
    } catch (err) { 
      console.error("上传错误:", err); 
      reject(err); 
    } 
  }); 
};

// 如果下载需要SAS,可以保留这个函数,但修复其中的错误
module.exports.createSharedAccessToken = (blobName, permission) => { 
  return new Promise((resolve, reject) => { 
    try {
      const sharedKeyCredential = new StorageSharedKeyCredential(
        process.env.AZURE_BLOB_ACCOUNT, 
        process.env.AZURE_BLOB_KEY
      );
      const containerName = process.env.AZURE_CONTAINER_NAME; 
      const startsOn = new Date(); 
      // 初始化expiresOn变量
      const expiresOn = new Date();
      expiresOn.setMinutes(expiresOn.getMinutes() + parseInt(process.env.autoLogoutDuration?.KeyValue || 60)); 
      const blobSAS = generateBlobSASQueryParameters({ 
        containerName, 
        blobName, 
        permissions: BlobSASPermissions.parse(permission), 
        startsOn,
        expiresOn // 必须指定过期时间
      }, sharedKeyCredential).toString(); 
      resolve(decodeURI(blobSAS)); 
    } catch(err) {
      console.error("生成SAS错误:", err);
      reject(err);
    }
  }); 
};

方案二:如果必须使用SAS上传

如果你确实需要通过SAS令牌来完成上传,需要正确构造包含SAS的URL来创建客户端:

const { BlobServiceClient, generateBlobSASQueryParameters, BlobSASPermissions, StorageSharedKeyCredential } = require("@azure/storage-blob");

module.exports.createBlob = (blobName, containerName, blobContent) => { 
  return new Promise(async (resolve, reject) => { 
    try { 
      const sasToken = await this.createSharedAccessToken(blobName, 'cw'); // 确保权限包含Create和Write
      // 构造包含SAS的Blob服务URL
      const sasUrl = `https://${process.env.AZURE_BLOB_ACCOUNT}.blob.core.windows.net?${sasToken}`;
      const blobServiceClient = new BlobServiceClient(sasUrl); 
      const containerClient = blobServiceClient.getContainerClient(containerName); 
      const blockBlobClient = containerClient.getBlockBlobClient(blobName); 
      const blobResponse = await blockBlobClient.upload(blobContent, Buffer.byteLength(blobContent)); 
      resolve(blobResponse); 
    } catch (err) { 
      console.error("上传错误:", err); 
      reject(err); 
    } 
  }); 
};

// 修复后的createSharedAccessToken
module.exports.createSharedAccessToken = (blobName, permission) => { 
  return new Promise((resolve, reject) => { 
    try {
      const sharedKeyCredential = new StorageSharedKeyCredential(
        process.env.AZURE_BLOB_ACCOUNT, 
        process.env.AZURE_BLOB_KEY
      );
      const containerName = process.env.AZURE_CONTAINER_NAME; 
      const startsOn = new Date(); 
      const expiresOn = new Date();
      expiresOn.setMinutes(expiresOn.getMinutes() + parseInt(process.env.autoLogoutDuration?.KeyValue || 60)); 
      const blobSAS = generateBlobSASQueryParameters({ 
        containerName, 
        blobName, 
        permissions: BlobSASPermissions.parse(permission), 
        startsOn,
        expiresOn
      }, sharedKeyCredential).toString(); 
      resolve(decodeURI(blobSAS)); 
    } catch(err) {
      console.error("生成SAS错误:", err);
      reject(err);
    }
  }); 
};

关键修改说明

  • 纠正认证方式:不再把SAS令牌当作SharedKeyCredential传递,而是要么直接用账号密钥创建SharedKeyCredential,要么把SAS拼到服务URL里。
  • 修复未定义变量:初始化expiresOn变量,避免运行时错误。
  • 调整权限:上传时使用'cw'权限(Create + Write),确保有足够的权限完成上传操作。
  • 正确计算内容长度:使用Buffer.byteLength(blobContent)来获取字符串或Buffer的正确字节长度,避免上传时的长度不匹配问题。

内容的提问来源于stack exchange,提问作者Setanjan Roy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.01 02:29:08