Commit fd57d73d by luoqi

fix(web): 模拟登录对话框分清两套权限 —— 角色=功能,选谁/哪级=数据范围

原文案把数据权限说得像跟着角色("看自己的/看本团队所有任务"其实是 view_own/view_all
功能权限,却像在描述数据范围)。点透两轴(正交):
- 顶部加一句:① 角色=能做什么(功能);② 选谁/哪级=能看哪些诊所品牌(数据权限,跟角色无关)
- ① 标题 "登录权限(角色)" → "角色 · 能做什么(功能权限)";角色 desc 改成纯功能口径
- 集团按钮 "集团·X 身份" → "数据范围 · 集团级 …… 角色沿用上方「X」"(数据范围与角色解耦)
- ② "选客服" → "数据范围 · 选客服 = 该客服的诊所(诊所级)+ 上方角色"

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
parent aefe33ed
...@@ -40,9 +40,9 @@ const TENANTS: { slug: BrandSlug; nameZh: string; tone: string }[] = [ ...@@ -40,9 +40,9 @@ const TENANTS: { slug: BrandSlug; nameZh: string; tone: string }[] = [
]; ];
const ROLES: { key: UserRole; nameZh: string; desc: string }[] = [ const ROLES: { key: UserRole; nameZh: string; desc: string }[] = [
{ key: 'staff', nameZh: '员工', desc: '执行客服 · 看自己的召回任务' }, { key: 'staff', nameZh: '员工', desc: '执行 / 认领 · 工作台默认只看自己名下' },
{ key: 'leader', nameZh: '主管', desc: '看本团队所有任务 · 可指派 / 回收' }, { key: 'leader', nameZh: '主管', desc: '可指派 / 回收 · 能看团队全部任务' },
{ key: 'admin', nameZh: '管理员', desc: '全部权限 · 含后台管理' }, { key: 'admin', nameZh: '管理员', desc: '全部功能 · 含后台管理' },
]; ];
// 降级网格的演示人名(需与后端 auth.service.MOCK_NAMES 一致)— 话术自报家门会用到 // 降级网格的演示人名(需与后端 auth.service.MOCK_NAMES 一致)— 话术自报家门会用到
...@@ -142,7 +142,12 @@ export function MockLoginDialog({ open }: { open: boolean }) { ...@@ -142,7 +142,12 @@ export function MockLoginDialog({ open }: { open: boolean }) {
</span> </span>
</DialogTitle> </DialogTitle>
<DialogDescription className="text-[12px]"> <DialogDescription className="text-[12px]">
生产环境会接宿主 SSO,这里是<strong>开发 / 试部署</strong>的快速通道。请选一个身份进入工作台: 生产环境会接宿主 SSO,这里是<strong>开发 / 试部署</strong>的快速通道。
<br />
<span className="text-slate-500">
两件事分开选:<strong>① 角色</strong>=能做什么操作(功能权限);
<strong>② 选谁 / 哪级</strong>=能看哪些诊所品牌(数据权限,跟角色无关)。
</span>
</DialogDescription> </DialogDescription>
</DialogHeader> </DialogHeader>
...@@ -150,7 +155,9 @@ export function MockLoginDialog({ open }: { open: boolean }) { ...@@ -150,7 +155,9 @@ export function MockLoginDialog({ open }: { open: boolean }) {
<div className="grid gap-3 pt-1"> <div className="grid gap-3 pt-1">
{/* ① 登录权限(角色)*/} {/* ① 登录权限(角色)*/}
<div> <div>
<div className="mb-1.5 text-[12px] font-medium text-slate-600">① 登录权限(角色)</div> <div className="mb-1.5 text-[12px] font-medium text-slate-600">
① 角色 · 能做什么(功能权限)
</div>
<div className="grid grid-cols-3 gap-2"> <div className="grid grid-cols-3 gap-2">
{ROLES.map((r) => ( {ROLES.map((r) => (
<button <button
...@@ -169,14 +176,14 @@ export function MockLoginDialog({ open }: { open: boolean }) { ...@@ -169,14 +176,14 @@ export function MockLoginDialog({ open }: { open: boolean }) {
</button> </button>
))} ))}
</div> </div>
{/* 集团级登录:数据范围 = 全部品牌全部诊所(sourceUnits=[] 不限)*/} {/* 数据范围·集团级:全部品牌全部诊所(sourceUnits=[] 不限);角色沿用①所选 */}
<button <button
type="button" type="button"
onClick={() => pickGroup(role)} onClick={() => pickGroup(role)}
disabled={!!busy} disabled={!!busy}
className="mt-2 w-full rounded-md border border-dashed border-amber-300 bg-amber-50/40 px-2.5 py-1.5 text-left text-[11.5px] text-amber-800 transition-colors hover:border-amber-400 disabled:opacity-50" className="mt-2 w-full rounded-md border border-dashed border-amber-300 bg-amber-50/40 px-2.5 py-1.5 text-left text-[11.5px] text-amber-800 transition-colors hover:border-amber-400 disabled:opacity-50"
> >
以「集团 · {roleNameZh(role)}」身份登录 —— 看<strong>全部品牌全部诊所</strong>(跨品牌,数据权限最上一层) 数据范围 · <strong>集团级</strong> —— 看<strong>全部品牌全部诊所</strong>(跨品牌,最上一层)。角色沿用上方「{roleNameZh(role)}」。
</button> </button>
</div> </div>
...@@ -184,7 +191,7 @@ export function MockLoginDialog({ open }: { open: boolean }) { ...@@ -184,7 +191,7 @@ export function MockLoginDialog({ open }: { open: boolean }) {
<div className="rounded-lg border border-slate-100 p-3"> <div className="rounded-lg border border-slate-100 p-3">
<div className="mb-2 flex items-center justify-between"> <div className="mb-2 flex items-center justify-between">
<div className="text-[12px] font-medium text-slate-600"> <div className="text-[12px] font-medium text-slate-600">
选客服 — 以其真实身份 + 上面的「{roleNameZh(role)}」权限登录 数据范围 · 选客服 = <strong>该客服的诊所</strong>(诊所级)+ 上方「{roleNameZh(role)}」角色
</div> </div>
<span className="text-[10.5px] text-slate-500">{csUsers.length} 位在岗 · 近 12 月</span> <span className="text-[10.5px] text-slate-500">{csUsers.length} 位在岗 · 近 12 月</span>
</div> </div>
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment