快速入门:在浏览器中使用 JavaScript v12 SDK 管理 Blob

Azure Blob 存储已经过优化,可以存储大量的非结构化数据。 Blob 是可以保存文本或二进制数据(包括图像、文档、流媒体和存档数据)的对象。 本快速入门介绍如何在浏览器中使用 JavaScript 管理 Blob。 你将上传和列出 Blob,并创建和删除容器。

该示例代码展示了如何使用适用于 JavaScript 的 Azure Blob 存储客户端库完成以下任务:

其他资源:

API 参考 | 库源代码 | 包 (npm) | 示例

先决条件

对象模型

Blob 存储提供了三种类型的资源:

  • 存储帐户
  • 存储帐户中的容器
  • 容器中的 blob

以下图示显示了这些资源之间的关系。

Diagram of Blob storage architecture

在本快速入门中,你将使用以下 JavaScript 类来与这些资源进行交互:

  • BlobServiceClientBlobServiceClient 类可用于操纵 Azure 存储资源和 blob 容器。
  • ContainerClientContainerClient 类可用于操纵 Azure 存储容器及其 blob。
  • BlockBlobClientBlockBlobClient 类可用于操纵 Azure 存储 Blob。

配置用于浏览器访问的存储帐户

若要从 web 浏览器以编程方式访问存储帐户,需要配置 CORS 访问并创建 SAS 连接字符串。

创建 CORS 规则

必须先配置你的帐户来启用跨源资源共享(简称 CORS),然后 Web 应用程序才能从客户端访问 Blob 存储。

在 Azure 门户中,选择你的存储帐户。 若要定义新的 CORS 规则,请导航到“设置”部分并选择“CORS”。 对于本快速入门,请创建完全开放的 CORS 规则:

Azure Blob Storage Account CORS settings

下表描述了每项 CORS 设置,并对用于定义规则的值进行了说明。

设置 说明
允许的源 * 接受一个逗号分隔的列表,其中的域设置为可以接受的域。 将值设置为 * 意味着所有域都可以访问存储帐户。
允许的方法 “DELETE”、“GET”、“HEAD”、“MERGE”、“POST”、“OPTIONS”和“PUT” 列出允许对存储帐户执行操作的 HTTP 谓词。 对于本快速入门,请选择所有可用的选项。
允许的标头 * 定义一个列表,其中包含存储帐户允许的请求标头(包括带前缀的标头)。 将值设置为 * 意味着所有标头都可以进行访问。
公开的标头 * 列出帐户允许的响应标头。 将值设置为 * 意味着帐户可以发送任何标头。
最长时间 86400 浏览器缓存预检 OPTIONS 请求的最长时间(以秒为单位)。 值为 86400 意味着缓存可以保留一整天。

使用此表中的值填写字段后,单击“保存”按钮。

重要

请确保将生产环境中使用的任何设置所公开的针对存储帐户的访问权限降至最低,以便始终能够进行安全的访问。 此处描述的 CORS 设置适用于快速入门,因为快速入门定义的安全策略是宽松的。 但是,不建议对实际环境使用这些设置。

创建 SAS 连接字符串

在浏览器中运行的代码使用共享访问签名 (SAS) 来向 Azure Blob 存储请求授权。 使用 SAS 时,客户端可以在没有帐户访问密钥或连接字符串的情况下授权访问存储资源。 有关 SAS 的详细信息,请参阅使用共享访问签名 (SAS)

按照以下步骤获取 Blob 服务 SAS URL:

  1. 在 Azure 门户中,选择你的存储帐户。
  2. 导航到“安全性 + 网络”部分,并选择“共享访问签名” 。
  3. 查看允许的服务,了解 SAS 令牌将有权访问所有存储帐户服务:
    • Blob
    • 文件
    • 队列
  4. 选择允许的资源类型以包括:
    • 服务
    • 容器
    • 对象
  5. 查看“开始和到期日期/时间”,以了解 SAS 令牌在默认情况下具有有限的生存期。
  6. 向下滚动,然后选择“生成 SAS 和连接字符串”按钮。
  7. 继续向下滚动,找到“Blob 服务 SAS URL”字段
  8. 选择“Blob 服务 SAS URL”字段最右侧的“复制到剪贴板”按钮。
  9. 将复制的 URL 保存到某个位置,以便在后续步骤中使用。

注意

门户返回的 SAS 令牌不包含 URL 查询字符串的分隔符字符 ('?')。 如果将 SAS 令牌追加到资源 URL,请记住在追加 SAS 令牌之前将分隔符字符追加到资源 URL。

创建 JavaScript 项目

创建名为 blob-quickstart-v12 的 JavaScript 应用程序。

  1. 在控制台窗口(例如 cmd、PowerShell 或 Bash)中,为项目创建新目录。

    mkdir blob-quickstart-v12
    
  2. 切换到新创建的 blob-quickstart-v12 目录。

    cd blob-quickstart-v12
    
  3. 创建 package.json。

    npm init -y
    
  4. 在 Visual Studio Code 中打开项目:

    code .
    

为 blob 存储安装 npm 包

  1. 在 Visual Studio Code 终端中,安装 Azure 存储 npm 包:

    npm install @azure/storage-blob
    
  2. 安装捆绑程序包以捆绑浏览器的文件和包:

    npm install parcel
    

    如果计划使用不同的捆绑程序,请详细了解捆绑 AZURE SDK

配置浏览器捆绑

  1. 在 Visual Studio Code 中打开 package.json 文件,并在添加 browserlist。 此 browserlist 针对三个流行浏览器的最新版本。 现在,完整的 package.json 文件应如下所示:
"browserslist": [
  "last 1 Edge version",
  "last 1 Chrome version",
  "last 1 Firefox version",
  "last 1 safari version",
  "last 1 webkit version"
],
  1. 添加“开始”脚本以捆绑网站:
"scripts": {
  "start": "parcel ./index.html"
},

创建 HTML 文件

  1. 创建 index.html 并添加以下 HTML 代码:
<!-- index.html -->
<!DOCTYPE html>
<html>

<body>
    <button id="create-container-button">Create container</button>
    <button id="select-button">Select and upload files</button>
    <input type="file" id="file-input" multiple style="display: none;" />
    <button id="list-button">List files</button>
    <button id="delete-button">Delete selected files</button>
    <button id="delete-container-button">Delete container</button>
    <p><b>Status:</b></p>
    <p id="status" style="height:160px; width: 593px; overflow: scroll;" />
    <p><b>Files:</b></p>
    <select id="file-list" multiple style="height:222px; width: 593px; overflow: scroll;" />
</body>

<script type="module" src="./index.js"></script>

</html>

删除 Javascript 文件

从项目目录中执行以下操作:

  1. 创建名为 index.js 的新文件。
  2. 添加 Azure 存储 npm 包。
const { BlobServiceClient } = require("@azure/storage-blob");

声明 UI 元素的字段

为用户交互添加 DOM 元素:

const createContainerButton = document.getElementById("create-container-button");
const deleteContainerButton = document.getElementById("delete-container-button");
const selectButton = document.getElementById("select-button");
const fileInput = document.getElementById("file-input");
const listButton = document.getElementById("list-button");
const deleteButton = document.getElementById("delete-button");
const status = document.getElementById("status");
const fileList = document.getElementById("file-list");

const reportStatus = message => {
    status.innerHTML += `${message}<br/>`;
    status.scrollTop = status.scrollHeight;
}

此代码声明每个 HTML 元素的字段,并实现一个 reportStatus 函数来显示输出。

添加存储帐户信息

index.js 文件的末尾添加以下代码,以便访问你的存储帐户。 请将 <placeholder> 替换为你之前生成的 Blob 服务 SAS URL。 在 index.js 文件的末尾添加以下代码。

// Update <placeholder> with your Blob service SAS URL string
const blobSasUrl = "<placeholder>";

创建客户端对象

创建 BlobServiceClientContainerClient 对象,以连接到存储帐户。 在 index.js 文件的末尾添加以下代码。

// Create a new BlobServiceClient
const blobServiceClient = new BlobServiceClient(blobSasUrl);

// Create a unique name for the container by 
// appending the current time to the file name
const containerName = "container" + new Date().getTime();

// Get a container client from the BlobServiceClient
const containerClient = blobServiceClient.getContainerClient(containerName);

创建和删除存储容器

在网页上选择相应的按钮时会创建和删除存储容器。 在 index.js 文件的末尾添加以下代码。

const createContainer = async () => {
    try {
        reportStatus(`Creating container "${containerName}"...`);
        await containerClient.create();
        reportStatus(`Done.`);
    } catch (error) {
        reportStatus(error.message);
    }
};

const deleteContainer = async () => {
    try {
        reportStatus(`Deleting container "${containerName}"...`);
        await containerClient.delete();
        reportStatus(`Done.`);
    } catch (error) {
        reportStatus(error.message);
    }
};

createContainerButton.addEventListener("click", createContainer);
deleteContainerButton.addEventListener("click", deleteContainer);

列出 Blob

选择“列出文件”按钮时,会列出存储容器的内容。 在 index.js 文件的末尾添加以下代码。

const listFiles = async () => {
    fileList.size = 0;
    fileList.innerHTML = "";
    try {
        reportStatus("Retrieving file list...");
        let iter = containerClient.listBlobsFlat();
        let blobItem = await iter.next();
        while (!blobItem.done) {
            fileList.size += 1;
            fileList.innerHTML += `<option>${blobItem.value.name}</option>`;
            blobItem = await iter.next();
        }
        if (fileList.size > 0) {
            reportStatus("Done.");
        } else {
            reportStatus("The container does not contain any files.");
        }
    } catch (error) {
        reportStatus(error.message);
    }
};

listButton.addEventListener("click", listFiles);

此代码调用 ContainerClient.listBlobsFlat 函数,然后使用迭代器检索返回的每个 BlobItem 的名称。 对于每个 BlobItem,它会使用 name 属性值更新“文件”列表。

将 blob 上传到容器中

选择“选择并上传文件”按钮时,会将文件上传到存储容器。 在 index.js 文件的末尾添加以下代码。

const uploadFiles = async () => {
    try {
        reportStatus("Uploading files...");
        const promises = [];
        for (const file of fileInput.files) {
            const blockBlobClient = containerClient.getBlockBlobClient(file.name);
            promises.push(blockBlobClient.uploadBrowserData(file));
        }
        await Promise.all(promises);
        reportStatus("Done.");
        listFiles();
    }
    catch (error) {
            reportStatus(error.message);
    }
}

selectButton.addEventListener("click", () => fileInput.click());
fileInput.addEventListener("change", uploadFiles);

此代码将“Select and upload files”按钮连接到隐藏的 元素。 按钮 click 事件会触发文件输入 click 事件,并显示文件选取器。 选择文件并关闭对话框之后,将发生 input 事件并调用 uploadFiles 函数。 此函数创建一个 BlockBlobClient 对象,然后针对所选的每个文件调用仅限浏览器的 uploadBrowserData 函数。 每个调用返回一个 Promise。 每个 Promise 将添加到列表中,这样就可以等待它们集中到一起,实现文件并行上传。

删除 Blob

选择“删除选定的文件”按钮时,会从存储容器中删除文件。 在 index.js 文件的末尾添加以下代码。

const deleteFiles = async () => {
    try {
        if (fileList.selectedOptions.length > 0) {
            reportStatus("Deleting files...");
            for (const option of fileList.selectedOptions) {
                await containerClient.deleteBlob(option.text);
            }
            reportStatus("Done.");
            listFiles();
        } else {
            reportStatus("No files selected.");
        }
    } catch (error) {
        reportStatus(error.message);
    }
};

deleteButton.addEventListener("click", deleteFiles);

此代码调用 ContainerClient.deleteBlob 函数,以删除列表中选定的每个文件。 然后,它会调用前面所示的 listFiles 来刷新 Files 列表的内容。

运行代码

  1. 从 Visual Studio Code 终端运行应用。

    npm start
    

    此过程将绑定文件并启动 web 服务器。

  2. 使用以下 URL 通过浏览器访问网站:

    http://localhost:1234
    

步骤 1:创建容器

  1. 在 Web 应用中,选择“创建容器”。 状态将指示已创建了一个容器。
  2. 在 Azure 门户中,验证容器是否已创建。 选择存储帐户。 在“Blob 服务”下,选择“容器”。 验证是否显示了新容器。 (可能需要选择“刷新”。)

步骤 2:将 blob 上传到容器

  1. 在本地计算机上,创建并保存一个测试文件,例如 test.txt。
  2. 在 Web 应用中,选择“选择并上传文件”。
  3. 浏览到测试文件,然后选择“打开”。 状态将指示文件已上传,并已检索到文件列表。
  4. 在 Azure 门户中,选择前面创建的新容器的名称。 验证是否显示了测试文件。

步骤 3:删除 blob

  1. 在 Web 应用中,在“文件”下,选择测试文件。
  2. 选择“删除选定的文件”。 状态将指示该文件已删除,并且容器不包含任何文件。
  3. 在 Azure 门户中选择“刷新”。 验证是否显示了“找不到任何 Blob”。

步骤 4:删除容器

  1. 在 Web 应用中,选择“删除容器”。 状态将指示容器已删除。
  2. 在 Azure 门户中,选择门户窗格左上角的“帐户名> | 容器”链接。
  3. 选择“刷新”。 新容器随即消失。
  4. 关闭 Web 应用。

使用存储模拟器

本快速入门在 Azure 云中创建了一个容器和 blob。 你还可以使用 Azure Blob 存储 npm 包,在 Azure 存储模拟器上本地创建这些资源以用于开发和测试。

清理资源

  1. 完成本快速入门后,请删除 blob-quickstart-v12 目录。
  2. 如果已完成对 Azure 存储资源的使用,请使用下列任一方法移除资源组:

后续步骤

本快速入门介绍了如何使用 JavaScript 上传、列出和删除 Blob。 此外,还介绍了如何创建和删除 Blob 存储容器。

有关教程、示例、快速入门和其他文档,请访问: