Storybook 中使用 Vite 构建器时通过 import.meta.env 访问环境变量的完整指南

发布时间:2026/9/8 16:33:16

Storybook 中使用 Vite 构建器时通过 import.meta.env 访问环境变量的完整指南
Storybook 中使用 Vite 构建器时通过 import.meta.env 访问环境变量的完整指南【免费下载链接】storybookStorybook is the industry standard workshop for building, documenting, and testing UI components in isolation项目地址: https://gitcode.com/GitHub_Trending/st/storybook在 Storybook 中带STORYBOOK_前缀的环境变量会注入到预览代码的运行时环境中当使用 Vite 构建器时由于 Vite 不会输出process.env这类 Node.js 全局对象这些变量需要通过import.meta.env来读取。本文基于 Storybook 官方文档的环境变量片段my-component-vite-env-variables.md被 Environment variables 的 “With Vite” 小节引用展开覆盖从配置环境变量、在 Story 中消费的多种写法CSF 3 / Svelte CSF / CSF Next到 Vite 构建器底层如何决定哪些变量能进入客户端代码的完整链路并给出排障方法。为什么 Vite 下要用 import.meta.envStorybook 的环境变量机制是命令行或.env文件中提供的前缀变量如STORYBOOK_会被打包进预览 bundle在预览 JavaScript 代码中随取随用。在 Webpack 构建器下访问入口是process.env而在使用 Vite builder 时process.env这类 Node.js 全局对象不会被输出到产物中因此官方文档明确建议改用import.meta.envOut of the box, Storybook provides a Vite builder, which does not output Node.js globals likeprocess.env. To access environment variables in Storybook (e.g.,STORYBOOK_,VITE_), you can useimport.meta.env.也就是说在 Vite 体系react-vite、vue3-vite、svelte-vite、web-components-vite、preact-vite 等中import.meta.env.STORYBOOK_DATA_KEY与import.meta.env.VITE_CUSTOM_VAR就是读取环境变量的标准方式。第一步如何提供这些环境变量在读取之前先确认变量从哪来。官方文档给出三种供给方式1. 命令行临时注入——启动时前置环境变量STORYBOOK_THEMEred STORYBOOK_DATA_KEY12345 npm run storybook2..env文件——在项目根目录添加.envSTORYBOOK_DATA_KEY123453. 按模式区分的文件——可以使用.env.development和.env.production为开发态 / 构建态提供不同的值。安全红线同样重要环境变量会被直接内联embed进构建产物任何人检查静态文件都能看到值因此绝不能把私钥、API 密钥等敏感信息放入 Storybook 的环境变量中。第二步在 Story 中通过 import.meta.env 消费变量以下是原片段文档继承下来的核心用法把环境变量作为args传入 Story。以 ReactCSF 3TypeScript为例// Replace your-framework with the framework you are using, e.g. react-vite, nextjs, vue3-vite, etc. import type { Meta, StoryObj } from storybook/your-framework; import { MyComponent } from ./MyComponent; const meta { component: MyComponent, } satisfies Metatypeof MyComponent; export default meta; type Story StoryObjtypeof meta; export const ExampleStory: Story { args: { propertyA: import.meta.env.STORYBOOK_DATA_KEY, propertyB: import.meta.env.VITE_CUSTOM_VAR, }, };同一段逻辑在 JavaScriptCSF 3下的写法更简洁export default { component: my-component, }; export const ExampleStory { args: { propertyA: import.meta.env.STORYBOOK_DATA_KEY, propertyB: import.meta.env.VITE_CUSTOM_VAR, }, };Svelte 项目既可以用 CSF 3也可以用 Svelte CSF 的defineMetascript module import { defineMeta } from storybook/addon-svelte-csf; import MyComponent from ./MyComponent.svelte; const { Story } defineMeta({ component: MyComponent, }); /script Story nameExampleStory args{{ propertyA: import.meta.env.STORYBOOK_DATA_KEY, propertyB: import.meta.env.VITE_CUSTOM_VAR, }} /**CSF Next实验性 API**则通过preview.meta/meta.story的工厂形式组织React 示例import preview from ../.storybook/preview; import { MyComponent } from ./MyComponent; const meta preview.meta({ component: MyComponent, }); export const ExampleStory meta.story({ args: { propertyA: import.meta.env.STORYBOOK_DATA_KEY, propertyB: import.meta.env.VITE_CUSTOM_VAR, }, });Vue 项目的 CSF Next 写法同理只是组件导入换成.vue文件import MyComponent from ./MyComponent.vue。无论哪种框架、哪种 CSF 风格模式完全一致import.meta.env.KEY出现在 Story 模块顶层构建时即被静态替换为具体值。这意味着变量在构建时被固化而不是运行时动态拉取。底层原理Vite 构建器如何决定哪些变量进入客户端结合仓库源码可以完整还原import.meta.env背后的处理链路。1. 默认前缀是VITE_和STORYBOOK_。Vite 构建器内置的 storybook:config-plugin 会在配置阶段合并envPrefix如果用户在viteFinal里自定义了envPrefix就在原值基础上追加STORYBOOK_否则直接使用[VITE_, STORYBOOK_]const mergedEnvPrefix existingEnvPrefix ? Array.from( new Set([ ...(Array.isArray(existingEnvPrefix) ? existingEnvPrefix : [existingEnvPrefix]), STORYBOOK_, ]) ) : [VITE_, STORYBOOK_];这一点有对应测试用例佐证vite-config.test.ts 中“should set default envPrefix when no user envPrefix is set”断言结果envPrefix严格等于[VITE_, STORYBOOK_]。2. 环境变量白名单过滤后生成 define 替换规则。运行时插件调用 envs.ts 中的stringifyProcessEnvs它只做两类放行命中内置白名单的键STORYBOOK、BASE_URL、MODE、DEV、PROD、SSR——即 Vite 自带的import.meta.env默认变量或以允许的前缀开头VITE_、STORYBOOK_、或用户envPrefix的键const allowedEnvVariables [ STORYBOOK, BASE_URL, MODE, DEV, PROD, SSR, ]; // 只有白名单值、envPrefix 数组命中的值、或带允许前缀的字符串才会被加入 acc[import.meta.env.${key}] JSON.stringify(value);放行后的变量被写成import.meta.env.KEY JSON.stringify(value)的 define 映射同时还会生成import.meta.env整体对象的映射以支持const { foo } import.meta.env这种解构写法。所以前面 Story 示例中的import.meta.env.STORYBOOK_DATA_KEY最终是被编译期替换成了字面量字符串。3. 变量从哪加载loadEnvs。核心侧的 envs.ts 用lazy-universal-dotenv读取.env系列文件与process.env合并后只保留匹配/^STORYBOOK_/的键并附加NODE_ENV、NODE_PATH、STORYBOOK、PUBLIC_URL等基础变量。注释中还有一个值得注意的细节dotenv的值会覆盖process.env的同名键——“it seems wrong that dotenv overrides process.env, but thats how it has always worked”这是历史行为排障时若发现.env值“赢了”命令行值根因即在此。补充能力head/body 中的 %STORYBOOK_X% 替换除了 JS 代码内访问带STORYBOOK_前缀的变量还可以用在自定义的head/body模板里占位符%STORYBOOK_X%会被直接替换为对应值例如STORYBOOK_THEMEred时%STORYBOOK_THEME%变成red。其实现见 template.ts对每个键值对执行string.replace(new RegExp(%${k}%, g), v)。注意当替换结果被用作 JavaScript 的属性或字符串值时可能需要自行补上引号因为值是被“原样插入”的。官方文档给的例子是link relstylesheet href%STORYBOOK_STYLE_URL% /。构建时build-storybook 会把变量硬编码进产物用build-storybook生成静态 Storybook 时同样可以传入这些环境变量它们会被硬编码hardcode进静态版本。这与前面源码层面“构建期静态替换”的机制互相印证产物中不存在运行时读取环境变量的能力只有替换后的常量。因此不同环境开发 / 生产 / CI需要不同行为时正确做法是分别提供.env.development、.env.production或在构建命令中显式传入而不是指望运行时变化。排障框架专属前缀的变量读不到如果你的变量使用了框架专属前缀例如 Vue 的VUE_APP_Storybook 的 Vite 构建器默认不会放行它们——因为默认前缀只有VITE_和STORYBOOK_。官方文档的排障建议是扩展 Vite 配置、显式配置envPrefix选项让构建器识别你的前缀。对应源码行为也很直白storybook-config-plugin.ts 会把用户配置的envPrefix字符串或数组与STORYBOOK_合并去重所以自定义前缀可以平滑叠加而STORYBOOK_前缀永远生效。另一类常见误用是期望import.meta.env能读到未加任何允许前缀的变量——按 envs.ts 的白名单逻辑这类键在 define 阶段就被过滤掉了产物中自然取不到值。小结供给STORYBOOK_前缀变量可通过命令行、.env、.env.development/.env.production三种方式提供VITE_前缀沿用 Vite 自身机制。读取Vite 构建器下统一用import.meta.env.KEY与 CSF 3 / Svelte CSF / CSF Next 均兼容Webpack 构建器下对应入口是process.env。原理默认envPrefix为[VITE_, STORYBOOK_]见 storybook-config-plugin.ts构建期由 stringifyProcessEnvs 做白名单过滤并静态替换值被硬编码进产物。边界模板 HTML 中可用%STORYBOOK_X%占位符替换敏感信息严禁放入环境变量框架专属前缀需自行扩展envPrefix配置。【免费下载链接】storybookStorybook is the industry standard workshop for building, documenting, and testing UI components in isolation项目地址: https://gitcode.com/GitHub_Trending/st/storybook创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

相关新闻

GitHub趋势周报:前端沉淀经验,AI Agent加速落地

GitHub趋势周报:前端沉淀经验,AI Agent加速落地

2026/9/8 16:33:16

如果你跟我一样,每周一上午打开 GitHub Trending 已经成了肌肉记忆,那你应该也发现了:这周榜单前排几乎被前端和 AI 两个方向包场。但这次跟前几周有明显区别——前端霸榜的仓库不再是什么新框架的新 demo,而是一批“经验整理型”…

CPython selectors 模块深入解析:基于 I/O 多路复用的高效 I/O 事件分发机制

CPython selectors 模块深入解析:基于 I/O 多路复用的高效 I/O 事件分发机制

2026/9/8 16:33:16

CPython selectors 模块深入解析:基于 I/O 多路复用的高效 I/O 事件分发机制 【免费下载链接】cpython The Python programming language 项目地址: https://gitcode.com/GitHub_Trending/cp/cpython 本文以 CPython 标准库的 selectors 模块(Doc…

opencode实战指南:从安装配置到多模型路由的终端AI编程助手

opencode实战指南:从安装配置到多模型路由的终端AI编程助手

2026/9/8 16:33:16

如果你过去一年被 Claude Code 这类 AI 编程代理撩得心痒,又不想被单一模型绑死,opencode 应该在你的关注列表里。opencode 是一个开源 AI 编程助手,和 Claude Code、Codex 走的是同一条路线:在终端里用自然语言让 AI 读代码、改代…

STM32四旋翼无人机飞控系统开发:从姿态解算到PID控制

STM32四旋翼无人机飞控系统开发:从姿态解算到PID控制

2026/9/8 17:33:19

简介:一套基于STM32单片机的四轴无人机控制系统完整代码包,面向嵌入式开发学习者、无人机爱好者、电子设计竞赛队伍及本科毕业设计人群。方案覆盖硬件结构搭建、系统建模、硬件模块设计、传感器数据采集、姿态检测融合算法、控制算法设计以及环境下的程序…

机器人操作中的In-Context Learning:原理、技术路线与工程实践解析

机器人操作中的In-Context Learning:原理、技术路线与工程实践解析

2026/9/8 17:33:19

做机器人操作研究的人,最近肯定都有同一个感受:打开arXiv,十个做learning的组有五个在讨论In-Context Learning(ICL)怎么用在机器人上,从VIMA、RT-2聊到OpenVLA,再到最近的π0,每篇都…

怎样在自己 Windows 电脑上搭 gitea

怎样在自己 Windows 电脑上搭 gitea

2026/9/8 17:33:19

Gitea 是轻量自托管 Git 代码托管系统,对标 GitLab,内存占用小,支持代码仓库、Issue、PR、Wiki、CI Actions、团队权限管理,适合内网军工 / 项目团队部署使用。Windows 本地搭建 Gitea两种方案:Docker Desktop&#xf…

Angular DevTools 完全使用指南:安装打开、应用检测机制、组件调试与性能剖析

Angular DevTools 完全使用指南:安装打开、应用检测机制、组件调试与性能剖析

2026/9/8 17:33:19

Angular DevTools 完全使用指南:安装打开、应用检测机制、组件调试与性能剖析 【免费下载链接】angular Deliver web apps with confidence 🚀 项目地址: https://gitcode.com/GitHub_Trending/an/angular Angular DevTools 是 Angular 官方为 An…

FPGA测控程序开发实战:从框架搭建到时序收敛的关键经验

FPGA测控程序开发实战:从框架搭建到时序收敛的关键经验

2026/9/8 17:33:19

做FPGA开发这些年,我经手过不少测控类的项目,从简单的传感器采集到多通道同步控制系统都有涉及。说实话,测控程序和纯通信或图像处理类的FPGA设计有本质区别——它更像是在写一套“实时操作系统”,只是这个系统跑在硬件逻辑上&…

QT手写MQTT客户端:协议详解与工程实践指南

QT手写MQTT客户端:协议详解与工程实践指南

2026/9/8 17:23:19

简介:这是一份基于Qt框架从零实现的MQTT客户端工程源码,适合想深入理解MQTT协议底层细节、或需要在Qt项目中接入物联网云平台的开发者。作者未采用任何现成第三方MQTT库,而是完全对照MQTT协议手册自行编写网络通信与报文逻辑,已完…

中国人民大学杨琳团队《Nature Communications》 | 全球潮汐湿地土壤有机碳时空格局与环境驱动:一项2009-2020年的全球评估

中国人民大学杨琳团队《Nature Communications》 | 全球潮汐湿地土壤有机碳时空格局与环境驱动:一项2009-2020年的全球评估

2026/9/7 20:21:46

本文首发于“生态学者”!从“湿地面积”到“土壤碳密度”:为什么需要重新认识潮汐湿地蓝碳变化?潮汐湿地位于陆地与海洋的交汇地带,包括红树林、盐沼和潮滩,是全球重要的蓝碳生态系统。其土壤能够长期储存大量有机碳&a…

adb抓包

adb抓包

2026/9/8 4:55:53

前言 本文介绍如何通过 tcpdump 在 Android 手机上抓取网络数据包,并在电脑端使用 Wireshark 进行分析。适用于需要排查 App 网络请求、分析接口调用或调试网络问题的开发与测试场景。1. 手机要有 root 权限2. 下载 tcpdump3. adb push C:\Users\zhangkuixun\Downlo…

大模型推理镜像极简瘦身:从 25GB 巨无霸到 3GB 精简镜像实战

大模型推理镜像极简瘦身:从 25GB 巨无霸到 3GB 精简镜像实战

2026/9/7 8:03:37

大模型推理镜像极简瘦身:从 25GB 巨无霸到 3GB 精简镜像实战 在云原生基础设施中,容器镜像体积直接决定了服务的部署速度与弹性扩容敏捷度。对于传统的 Go / Java 微服务,镜像体积通常被严格控制在 50MB 到 200MB 以内,拉取镜像只…

芯片良率波动可视化:动画拆解工艺因果,重建客户信任

芯片良率波动可视化:动画拆解工艺因果,重建客户信任

2026/9/8 0:02:30

芯片这个行业有个不太被人摆到台面上、但几乎每天都在发生的场景:客户拿着一条良率曲线截图问你,这批货的良率怎么掉了三个点,是不是工艺出问题了,产生的不良会不会流到他们产线上去。你解释了半天,客户似懂非懂&#…

PyTorch DataLoader参数冲突:sampler与shuffle互斥的根源与正确写法

PyTorch DataLoader参数冲突:sampler与shuffle互斥的根源与正确写法

2026/9/8 0:02:30

ValueError: sampler option is mutually exclusive with shuffle,这个报错我在 PyTorch 的 DataLoader 上至少见过几十次了,而且很有意思的是,它经常不是新手专属——很多写了好几年模型的老手,在从单机改成自定义采样器&#xf…

中国车企再破谣言,GAC吉利零跑获欧盟安全五星

中国车企再破谣言,GAC吉利零跑获欧盟安全五星

2026/9/8 0:02:30

有人可能在网上开着皮卡拍视频,声称中国电动车不仅性能不如美国大排量车型,安全性也堪忧。然而事实恰恰相反,GAC、吉利和零跑最新推出的电动车型在极为严苛的欧盟新车安全评鉴(Euro NCAP)测试中全部斩获满分。就在特斯…

远程协作的工作台整理

远程协作的工作台整理

2026/9/8 4:23:39

远程协作的工作台整理远程协作的核心不是再加一个工具,而是让交接信息足够完整。异步任务要写明目标、输入位置、完成标准和需要决策的人。 工作台的最小配置 将日程、待办、代码和沟通入口收拢到少数固定位置;通知按紧急程度分层。工作台不需要模仿办公…

持续集成 流水线自动化与 声明式交付 实践:原型怎样变成可用功能

持续集成 流水线自动化与 声明式交付 实践:原型怎样变成可用功能

2026/9/8 3:19:39

持续集成 流水线自动化与 声明式交付 实践:原型怎样变成可用功能分类:[AI/大模型]细分主题:AI 增强型 CI/CD 流水线自动化与 GitOps 实践:Agent 工作流、工具调用与任务拆解:从原型到生产的验收清单很多团队在尝试用大…

容器编排 生产环境运维与排障实战:复盘记录怎样真正派上用场

容器编排 生产环境运维与排障实战:复盘记录怎样真正派上用场

2026/9/8 4:00:23

容器编排 生产环境运维与排障实战:复盘记录怎样真正派上用场分类:[工程技术]细分主题:Kubernetes 生产环境运维与排障实战:可复制的项目复盘模板与决策记录大部分团队的事故复盘报告,最后都变成了躺在 Confluence 或钉…