# common-page-create-spec ## 适用范围 - 涉及新增通用页面、列表页、详情页、表单页、页面占位页时必读。 - 涉及页面目录落点、接口接入、本地路由/远程路由选择、菜单配置、`curl` 联调时必读。 ## 创建主链路 - 先判定页面是否需要登录后访问、菜单展示、角色授权、默认首页、keep-alive;再决定走本地路由还是远程路由。 - 页面源码默认放在 `src/view/`;页面私有子组件放在 `src/view//components`。 - 页面请求统一放在 `src/api/.js`;插件页面请求统一放在 `src/plugin//api/.js`。 - 页面只负责编排、生命周期和页面局部状态;不要在页面内直写 axios,也不要把单页临时状态默认上提到 `pinia`。 ## 路由接入规则 ```mermaid flowchart LR A["新增页面"] --> B{"是否需要登录后菜单/权限/默认首页?"} B -- "否" --> C["本地路由: src/router/index.js"] B -- "是" --> D["远程路由: 后台 menu + 前端动态注入"] C --> E["同步检查 src/permission.js 白名单与跳转"] D --> F["同步检查菜单权限、keep-alive、defaultRouter"] ``` - 本地路由:仅用于登录页、初始化页、公开页、扫码页、明确不依赖后台菜单的工具页。入口固定 `src/router/index.js`,并同步检查 `src/permission.js` 白名单和未登录跳转。 - 远程路由:用于登录后业务页、需要左侧菜单、角色授权、默认首页、按钮权限、keep-alive 的页面。路由来源是 `/menu/getMenu`,前端在 `src/pinia/modules/router.js` 中拉取后动态注入。 - 远程路由的 `component` 只允许写 `view/...` 或 `plugin/...` 字符串;对应文件必须真实存在,且能被 `src/utils/asyncRouter.js` 命中。 - 远程路由的 `component` 不要写成 `/src/view/...`、Windows 反斜杠路径或别名导入字符串;当前动态映射只认相对 `src` 的正斜杠路径。 - 页面需要承载子路由时,父页面必须是 `router-view` 占位页;不要把普通内容页直接拿来做父级容器。 - `meta.defaultMenu` 只用于明确需要脱离常规 `layout` 承载的基础页面;普通业务页默认保持 `false`。 ## 菜单与页面最小约定 - 页面目录命名跟随现有业务语义,页面入口优先 `src/view//index.vue`。 - 远程路由最小字段必须保证:`name` 唯一、`path` 稳定、`component` 可映射、`meta.title` 可展示。 - `name` 使用唯一英文标识;改名时必须同步检查菜单高亮、keep-alive、`defaultRouter` 和页面标题。 - `path` 默认与 `name` 同步;只有明确需要参数化路径时才额外拼接,不要把查询条件硬塞进路由 path。 - 需要缓存页签时设置 `meta.keepAlive`;需要进入后自动关闭 tab 时设置 `meta.closeTab`。 - 页面进入菜单体系后,新增菜单不等于可访问;还必须补角色授权,否则页面可能存在但用户不可见。 ## curl 联调案例 - 联调地址默认取 `VITE_BASE_API`;认证头遵循 `src/utils/request.js` 当前约定:`Content-Type`、`x-token`、`x-user-id`。 - 页面业务接口先用 `curl` 跑通,再落 `src/api/*`;不要先在页面里硬编码请求排查接口。 ```bash curl --location --request POST "$BASE_URL/example/list" \ --header "Content-Type: application/json" \ --header "x-token: " \ --header "x-user-id: " \ --data-raw "{\"page\":1,\"pageSize\":10}" ``` ```bash curl --location --request POST "$BASE_URL/menu/addBaseMenu" \ --header "Content-Type: application/json" \ --header "x-token: " \ --header "x-user-id: " \ --data-raw "{\"path\":\"demoPage\",\"name\":\"DemoPage\",\"component\":\"view/demoPage/index.vue\",\"parentId\":0,\"hidden\":false,\"sort\":10,\"meta\":{\"title\":\"Demo 页面\",\"icon\":\"House\",\"keepAlive\":false,\"closeTab\":false,\"defaultMenu\":false},\"parameters\":[],\"menuBtn\":[]}" ``` - 新增远程路由后,至少回查一次 `/menu/getMenu` 返回中是否已包含目标菜单,再排查前端注入问题。 ## 常见错误 - 只创建了 `src/view` 页面文件,没有补本地路由或远程菜单配置。 - 该走远程路由的业务页被塞进本地路由,导致菜单、角色权限、默认首页链路失效。 - 远程路由 `component` 写错路径格式,导致 `asyncRouter.js` 找不到页面组件。 - 页面里直接写 axios 请求或直接拼 token,绕过 `src/api` 和 `src/utils/request.js`。 - 改了路由 `name/path`,没有同步检查 `keepAlive`、菜单高亮、`defaultRouter` 和未登录跳转。