ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

深入解析 Wasp 项目结构:从 `wasp new` 生成的目录到 `main.wasp` 声明式配置

深入解析 Wasp 项目结构:从 `wasp new` 生成的目录到 `main.wasp` 声明式配置 深入解析 Wasp 项目结构从wasp new生成的目录到main.wasp声明式配置【免费下载链接】waspThe batteries-included full-stack framework for the AI era. Develop JS/TS web apps (React, Node.js, and Prisma) using declarative code that abstracts away complex full-stack features like auth, background jobs, RPC, email sending, end-to-end type safety, single-command deployment, and more.项目地址: https://gitcode.com/GitHub_Trending/wa/wasp创建完一个新的 Wasp 项目后摆在开发者面前的是一套经过精心设计的目录结构。这套结构与普通 React Node.js 项目最大的区别在于它引入了一个声明式核心——main.wasp或main.wasp.ts文件。本指南以 Wasp 0.16 版教程的 TodoApp 为例逐文件拆解 Wasp 项目的目录职责、JavaScript 与 TypeScript 的切换方式并深入到本仓库中的 TodoApp 示例源码examples/tutorials/TodoApp 与 examples/tutorials/TodoAppTs讲清 Wasp 是如何依据main.wasp中的声明自动生成数据库、服务端与客户端之间通信以及 React 路由等底层代码的。读完本文你将能够熟练读懂任意 Wasp 项目的目录结构并具备独立编写app、route、page声明的基础能力。一、wasp new生成的标准目录结构在教程上一节创建新项目中执行wasp new TodoApp后你会得到一个与下面完全一致的文件布局. ├── .gitignore ├── main.wasp # Your Wasp code goes here. ├── schema.prisma # Your Prisma schema goes here. ├── package.json # Your dependencies and project info go here. ├── public # Your static files (e.g., images, favicon) go here. ├── src # Your source code (TS/JS/CSS/HTML) goes here. │ ├── Main.css │ ├── MainPage.jsx │ ├── vite-env.d.ts │ └── waspLogo.png ├── tsconfig.json ├── vite.config.ts ├── .waspignore └── .wasproot这份结构把你写的代码和Wasp 生成的代码清晰地分离开来。这里的你的代码指的就是上图中列出的这些文件与之相对的是 Wasp 在wasp start、wasp build等命令执行后自动生成的代码通常输出到.wasp/out目录。1.1 目录与文件的职责划分main.wasp整个应用的定义文件也是 Wasp 一切魔法的源头。你在其中用 Wasp DSL 声明 app、route、page、query、action 等核心组件Wasp 据此生成数据库访问层、前后端通信、React 路由等大量代码。这是全项目最重要的文件下一节会重点展开。schema.prisma使用 Prisma 语法定义数据库 schema 的位置。本仓库示例中的 examples/tutorials/TodoApp/schema.prisma 给出了一个典型的写法——datasource db声明数据库 providergenerator client指定prisma-client-js随后定义User与Task两个 model。教程后面章节会专门讲解 Prisma 的使用。package.json存放你的依赖与项目信息。本仓库中的 examples/tutorials/TodoApp/package.json 展示了真实 Wasp 项目的依赖面貌react、react-dom、react-router作为运行依赖vite、typescript、prisma、playwright/test等作为开发依赖并通过workspaces将.wasp/out/*与.wasp/out/sdk/wasp纳入工作区管理——这正是Wasp 生成的 SDK 也能被 IDE 识别的底层机制之一。public静态资源目录例如图片、favicon 等会被原样提供给客户端。src你的源码目录可以放 TS/JS/CSS/HTML。注意Wasp 不强制你按客户端、服务端分目录——你完全可以自由组织代码结构甚至让某个目录同时包含客户端与服务端文件。tsconfig.json、vite-env.d.ts、.wasproot等这些文件的作用是帮助 Wasp 和 IDEVSCode 等提升开发体验为代码提供自动补全、IntelliSense 与错误提示。vite.config.ts用于配置 Vite——Wasp 选择的构建工具。在本教程中你不会改动它。如果将来需要自定义 Vite 行为可参考文档 自定义 Vite 配置。.waspignore声明哪些文件/目录在 Wasp 生成代码时应被忽略避免无关文件干扰构建。1.2 JavaScript 与 TypeScript如何切换Wasp 默认创建的项目使用 JavaScript。wasp new生成的主页文件是src/MainPage.jsx。如果你想改用 TypeScript只需要手动将文件名改为src/MainPage.tsx然后重启wasp start即可。这里有两个关键点值得强调无需修改main.wasp。声明文件里的component: import { MainPage } from src/MainPage使用的是标准 JS import 语法src是 Wasp 提供的指向src目录的别名它与具体是.jsx还是.tsx无关——Wasp 会自行解析实际文件扩展名。JS 与 TS 可以混用。Wasp 对 JavaScript 和 TypeScript 开箱即用你完全可以在项目中混合使用两种语言按自己的偏好选择。改名后的 TS 版目录结构如下仅MainPage.jsx变为MainPage.tsx. ├── .gitignore ├── main.wasp # Your Wasp code goes here. ├── schema.prisma # Your Prisma schema goes here. ├── package.json # Your dependencies and project info go here. ├── public # Your static files (e.g., images, favicon) go here. ├── src # Your source code (TS/JS/CSS/HTML) goes here. │ ├── Main.css │ ├── MainPage.tsx # Renamed from MainPage.jsx │ ├── vite-env.d.ts │ └── waspLogo.png ├── tsconfig.json ├── vite.config.ts ├── .waspignore └── .wasproot从本仓库的示例可以得到一致的印证JS 版 examples/tutorials/TodoApp/src 下是MainPage.jsx、LoginPage.jsx、SignupPage.jsx、actions.js、queries.js而 TS 版 examples/tutorials/TodoAppTs/src 下则是对应的MainPage.tsx、LoginPage.tsx、SignupPage.tsx、actions.ts、queries.ts——目录骨架完全相同只有文件扩展名不同。二、组织代码的推荐姿势按特性Feature而非按层Wasp 让你可以自由组织代码没有必须把客户端文件和服务端文件分开放进不同目录的强制要求。官方推荐的做法是按特性feature垂直组织代码——即把某个功能涉及的前端、后端、数据库相关代码放在一起。不过考虑到本教程的 TodoApp 文件数量很少目前只有一两个页面和少量逻辑完全没有必要引入复杂的目录结构教程选择把一切都放在根src目录下保持简单。这个原则同样适用于你的真实项目起步阶段先保持简单等代码量上来后再按特性拆分。三、main.wasp你的应用定义文件main.wasp是整个项目中最核心的文件它定义了应用的中心组件Wasp 会基于它替你完成大量繁重工作。它本质上是一系列声明declarations的列表每条声明定义应用的一部分。:::tip 进阶选项Wasp TS 配置早期预览特性 如果你愿意也可以用main.wasp.ts代替main.wasp来定义 Wasp 配置。本仓库中 examples/tutorials/TodoApp/main.wasp.ts 就是这种写法的真实示例——它通过wasp.sh/spec包导出app({...})对象把 route、page、query、action 统一放在spec数组中声明。 :::3.1 默认main.wasp的完整内容wasp new生成的默认main.waspJS 版如下app TodoApp { wasp: { version: {latestWaspVersion} // Pins the version of Wasp to use. }, title: TodoApp // Used as the browser tab title. Note that all strings in Wasp are double quoted! } route RootRoute { path: /, to: MainPage } page MainPage { // We specify that the React implementation of the page is exported from // src/MainPage.jsx. This statement uses standard JS import syntax. // Use src to reference files inside the src folder. component: import { MainPage } from src/MainPage }TypeScript 版与 JS 版几乎完全一致唯一的区别是component指向src/MainPage时实际解析到src/MainPage.tsxapp TodoApp { wasp: { version: {latestWaspVersion} // Pins the version of Wasp to use. }, title: TodoApp // Used as the browser tab title. Note that all strings in Wasp are double quoted! } route RootRoute { path: /, to: MainPage } page MainPage { // We specify that the React implementation of the page is exported from // src/MainPage.tsx. This statement uses standard JS import syntax. // Use src to reference files inside the src folder. component: import { MainPage } from src/MainPage }对照本仓库的 TS 配置示例examples/tutorials/TodoAppTs/main.wasp.ts可以看到同样声明了三类核心内容app应用名TodoApp、wasp.version、title、routeRootRoute指向/、pageMainPage对应MainPage组件此外还多了auth、query、action等声明——这些在教程后续章节会逐步引入。3.2 三种核心声明类型这份文件里使用了三种声明类型它们共同构成了 Wasp 应用的骨架app应用的顶层配置信息。包括wasp.version锁定要使用的 Wasp 版本保证团队与部署环境的一致性title用作浏览器标签页标题。注意 Wasp 中所有字符串都必须使用双引号还可以配置head自定义head标签、auth认证方式等高级选项。route描述每个页面应该从哪个路径path访问以及渲染哪个页面。例如route RootRoute { path: /, to: MainPage }表示访问根路径/时渲染MainPage。page定义一个网页以及页面加载时要渲染的 React 组件。component字段使用标准 JS import 语法引用src目录下的文件src是 Wasp 提供的内置别名。这三者配合的逻辑是route决定URL 长什么样page决定渲染什么组件。下一节教程页面与路由会详细展开 route 和 page 如何协同构建 Web 应用。四、main.wasp背后的生成机制它如何驱动整个应用理解了声明之后一个自然的问题是这些声明到底是如何变成可运行代码的从本仓库的源码与示例可以还原出这条链路解析与校验waspc编译器Haskell 实现位于 waspc/src读取main.wasp先经过 waspc/src/Wasp/Analyzer 的解析与类型检查再通过 waspc/src/Wasp/AppSpec 将声明转换为内部的 AppSpec 数据结构。生成代码Generator 模块waspc/src/Wasp/Generator根据 AppSpec 渲染出完整的全栈工程输出到.wasp/out。这里包含数据库访问层Prisma Client 的封装、服务端 Express/Node 代码、客户端 React 路由与页面挂载逻辑等。构建与运行wasp start启动开发服务器客户端、服务端、数据库默认 SQLite见 examples/tutorials/TodoApp/schema.prisma 中的provider sqlite三端同时就绪浏览器打开http://localhost:3000即可看到占位页面。也就是说开发者只写声明 少量业务代码Wasp 负责把数据库、server-client 通信、React 路由这些繁琐且容易出错的样板代码批量生成出来。这正是 examples/tutorials/TodoApp/src/MainPage.jsx 中MainPage组件可以直接从wasp/client/operations导入useQuery、createTask等操作的原因——这些看似魔法的导入实际指向的都是 Wasp 基于main.wasp声明生成的 SDK 代码。五、验证与延伸routepage的实际工作方式最后我们用教程下一节页面与路由的内容做一次收束因为这正是main.wasp中 route 和 page 声明的直接延伸默认的RootRoute指向/渲染src/MainPage.{jsx,tsx}导出的命名组件新增页面只需再写一组routepage声明例如route HelloRoute { path: /hello/:name, to: HelloPage }——路径参数语法与 React Router 一致组件内可用useParams读取name对应地在src下创建HelloPage.{jsx,tsx}并export同名组件即可。这套声明驱动的心智模型一旦建立后续引入实体Entity、查询Query、操作Action、认证Auth时你会发现自己始终在做同一件事在main.wasp里加一条声明在src里写对应的实现函数。本仓库中的 examples/tutorials/TodoApp/src/queries.js 和 examples/tutorials/TodoApp/src/actions.js 就是最好的范例——getTasks、createTask、updateTask各自通过context.entities访问 Prisma 模型并在main.wasp.ts中通过query(...)、action(...)注册实现服务端能力与声明文件的完整闭环。至此你已经完整掌握了 Wasp 项目的目录结构与声明式核心。下一步就可以跟随教程进入页面与路由的实际编码环节了。【免费下载链接】waspThe batteries-included full-stack framework for the AI era. Develop JS/TS web apps (React, Node.js, and Prisma) using declarative code that abstracts away complex full-stack features like auth, background jobs, RPC, email sending, end-to-end type safety, single-command deployment, and more.项目地址: https://gitcode.com/GitHub_Trending/wa/wasp创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表