美国版 App 登录接口说明
概述
美国版移动端认证由 food-labeling-us 模块的 UsAppAuthAppService 提供,采用 ABP 约定式动态 API。宿主统一前缀为 /api/app,建议以 Swagger 为准核对路径(本地示例:http://localhost:19001/swagger,搜索 UsAppAuth)。
| 说明 | 内容 |
|---|---|
| 账号标识 | 使用 User.Email(邮箱)登录,邮箱比对忽略大小写 |
| 密码 | 与 Web 共用 User 表,校验方式与 RBAC AccountManager 一致(盐值 + MD5Helper.SHA2Encode) |
| 权限 | App 登录不校验角色/权限(允许“未配置权限”的账号登录);H5 管理端再按 RBAC 权限控制 |
| 验证码 | 当配置 Rbac:EnableCaptcha 为 true 时,需先拉取图形验证码,本接口入参传 uuid、code;未开启时可传空或不传 |
接口 1:App 登录
签发 Access Token、Refresh Token,并返回当前用户在 userlocation 中绑定的门店列表(关联 location 表详情)。
HTTP
- 方法:
POST - 路径:
/api/app/us-app-auth/login - Content-Type:
application/json - 鉴权:无需登录(匿名)
请求体参数(UsAppLoginInputVo)
| 参数名(JSON) | 类型 | 必填 | 说明 |
|---|---|---|---|
email |
string | 是 | 登录邮箱,对应数据库 User.Email |
password |
string | 是 | 明文密码 |
uuid |
string | 条件 | 图形验证码 UUID;开启验证码时必填 |
code |
string | 条件 | 图形验证码;开启验证码时必填 |
传参示例(请求 Body)
未开启图形验证码时:
{
"email": "admin@example.com",
"password": "123456"
}
开启图形验证码时(需与系统验证码接口返回的 uuid、用户输入的验证码一致):
{
"email": "test@example.com",
"password": "您的密码",
"uuid": "验证码接口返回的 uuid",
"code": "用户看到的验证码"
}
响应体(UsAppLoginOutputDto)
| 字段(JSON) | 类型 | 说明 |
|---|---|---|
token |
string | 访问令牌(Bearer),后续业务接口放在 Header Authorization: Bearer {token} |
refreshToken |
string | 刷新令牌(与系统账号体系一致,用于刷新 access token,具体用法与 Web 一致) |
locations |
array | 绑定门店列表,元素见下表 |
locations[] 元素(UsAppBoundLocationDto)
| 字段(JSON) | 类型 | 说明 |
|---|---|---|
id |
string | 门店主键(Guid 字符串) |
locationCode |
string | 业务编码,如 LOC-1 |
locationName |
string | 门店名称 |
fullAddress |
string | 拼接后的完整地址(街道、城市、州、邮编等;无数据时可能为 "无") |
state |
bool | 门店是否启用 |
响应示例
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"refreshToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"locations": [
{
"id": "a2696b9e-2277-11f1-b4c6-00163e0c7c4f",
"locationCode": "LOC-1",
"locationName": "Downtown Kitchen",
"fullAddress": "123 Main St, New York, NY 10001",
"state": true
}
]
}
常见错误提示(业务异常文案)
- 邮箱或密码为空:
请输入合理数据! - 邮箱在库中不存在(未删除且启用用户中无匹配邮箱):
登录失败!邮箱不存在! - 密码错误:
登录失败!用户名或密码错误!(与UserConst.Login_Error一致) - 验证码错误(开启验证码时):
验证码错误
接口 2:获取当前账号绑定门店
无需重新登录即可刷新 userlocation 绑定门店列表(例如切换门店前先同步列表)。
HTTP
- 方法:
GET - 路径:
/api/app/us-app-auth/my-locations - 鉴权:需要登录,请求头携带
Authorization: Bearer {token}(使用接口 1 返回的token)
请求参数
无 Query / Body 参数;用户身份由 JWT 解析。
传参示例
GET /api/app/us-app-auth/my-locations HTTP/1.1
Host: localhost:19001
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
若前端统一约定 GET 使用 data 封装,可自行在客户端组装;本接口服务端不读取额外 Query 参数。
响应体
与登录接口中 locations 相同:UsAppBoundLocationDto[](数组)。
响应示例
[
{
"id": "a2696b9e-2277-11f1-b4c6-00163e0c7c4f",
"locationCode": "LOC-1",
"locationName": "Downtown Kitchen",
"fullAddress": "123 Main St, New York, NY 10001",
"state": true
}
]
常见错误
- 未登录或 Token 无效:按网关/ABP 返回 401 及统一错误体
- 无用户上下文:
用户未登录
接口 3:我的资料(My Profile)
用于「My Profile」页展示:全名、邮箱、电话、员工号、角色。
HTTP
- 方法:
GET - 路径:
/api/app/us-app-auth/my-profile(以 Swagger 中UsAppAuth为准) - 鉴权:需要登录(
Authorization: Bearer {token})
请求参数
无。
响应体(UsAppMyProfileOutputDto)
| 字段(JSON) | 类型 | 说明 |
|---|---|---|
fullName |
string | User.Name,无则 Nick,再无则 UserName |
email |
string | User.Email;空为 "无" |
phone |
string | 由 User.Phone(long)格式化为可读字符串;10 位数字按 +1 (555) 123-4567 形式;无则 "无" |
employeeId |
string | 当前取 User.UserName(可与业务约定为工号/登录名) |
roleDisplay |
string | 多角色 Role.RoleName 按 OrderNum 排序后以英文逗号拼接;无角色为 "无" |
primaryRoleCode |
string \ | null |
接口 4:修改密码(Change Password)
与 User.JudgePassword / BuildPassword 一致:校验当前密码后写入新盐值哈希。
HTTP
- 方法:
POST - 路径:
/api/app/us-app-auth/change-password - Content-Type:
application/json - 鉴权:需要登录
请求体(UsAppChangePasswordInputVo)
| 字段(JSON) | 类型 | 必填 | 说明 |
|---|---|---|---|
currentPassword |
string | 是 | 当前明文密码 |
newPassword |
string | 是 | 新密码 |
confirmNewPassword |
string | 是 | 必须与 newPassword 完全一致 |
新密码复杂度(与原型「Password Requirements」一致)
- 至少 8 位
- 至少 1 个大写字母、1 个小写字母
- 至少 1 个数字
- 至少 1 个非字母数字字符(特殊字符)
请求示例
{
"currentPassword": "OldPass1!",
"newPassword": "NewPass9@x",
"confirmNewPassword": "NewPass9@x"
}
响应
成功时 HTTP 200,无业务体要求(ABP 可能返回空对象);失败为业务异常文案。
常见错误
- 未登录:
用户未登录 - 当前密码错误:与登录失败一致(
UserConst.Login_Error文案) - 新密码与确认不一致:
新密码与确认密码不一致 - 新密码与当前相同:
新密码不能与当前密码相同 - 不满足复杂度:如
新密码至少 8 位、新密码需包含大写字母等
接口 5:门店详情(Location)
用于移动端「Location」页:店名、完整地址、门店电话、营业时间占位、店长姓名与电话。仅当当前 JWT 用户在 userlocation 中绑定该门店时可查(与接口 1、2 的门店范围一致)。
HTTP
- 方法:
GET - 路径:
/api/app/us-app-auth/location-detail(以 Swagger 中UsAppAuth→GetLocationDetail为准;locationId一般为 Query 参数) - 鉴权:需要登录(
Authorization: Bearer {token})
请求参数
| 参数名 | 位置 | 类型 | 必填 | 说明 |
|---|---|---|---|---|
locationId |
Query | string | 是 | 门店主键,Guid 字符串(与 locations[].id 一致) |
传参示例
GET /api/app/us-app-auth/location-detail?locationId=a2696b9e-2277-11f1-b4c6-00163e0c7c4f HTTP/1.1
Host: localhost:19001
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
响应体(UsAppLocationDetailOutputDto)
| 字段(JSON) | 类型 | 说明 |
|---|---|---|
locationId |
string | 门店主键 |
locationName |
string | 门店名称;空为 "无" |
fullAddress |
string | 与登录接口相同的地址拼接规则;无有效片段为 "无" |
storePhone |
string | location.Phone 去首尾空格;空为 "无" |
operatingHours |
string | 当前 location 表无营业时间字段,固定返回 "无"(后续若落库可再对接) |
managerName |
string | 在同店 userlocation 绑定用户中,取角色 RoleCode / RoleName(忽略大小写)包含 manager 的第一人展示姓名(Name → Nick → UserName);无匹配为 "无" |
managerPhone |
string | 同上用户的 User.Phone(long)按与「我的资料」相同的可读格式;无电话为 "无" |
响应示例
{
"locationId": "a2696b9e-2277-11f1-b4c6-00163e0c7c4f",
"locationName": "Downtown Store",
"fullAddress": "123 Main St, New York, NY 10001",
"storePhone": "(212) 555-0100",
"operatingHours": "无",
"managerName": "Jane Doe",
"managerPhone": "+1 (555) 123-4567"
}
常见错误(业务异常文案)
- 未登录:
用户未登录 locationId非法或空:无效的门店标识- 当前用户未绑定该门店:
当前账号未绑定该门店,无法查看 - 门店已删或不存在:
门店不存在或已删除
与其他登录方式的区别
| 场景 | 说明 |
|---|---|
| Web 管理端 | 仍使用 RBAC AccountService.PostLoginAsync,一般为人 userName + 密码 |
| 美国版 App | 仅本模块 /api/app/us-app-auth/login 使用 邮箱 + 密码 |
两者共用同一 User 表与 JWT 体系;App 端需保证账号已维护 Email 字段,否则无法通过邮箱登录。