taj-consumer-ui
v0.1.9
Published
Shared uni-app consumer UI components for TAJ applications
Readme
taj-consumer-ui
用于 TAJ uni-app 项目的公共源码组件包。
安装
pnpm add taj-consumer-ui使用方需要安装兼容版本的 vue 与 @wot-ui/ui。
使用
<script setup lang="ts">
import TajBusinessStatus from 'taj-consumer-ui/business-status'
</script>
<template>
<TajBusinessStatus
business-hours='{"days":[1,2,3,4,5],"end":"23:00","mode":"CUSTOM","start":"10:00"}'
business-hours-label="营业时间"
/>
</template>组件目录遵循 Wot UI 的命名方式:
components/
├── taj-business-status/
│ ├── index.scss
│ ├── taj-business-status.vue
│ └── types.ts
├── taj-goods-item/
│ ├── index.scss
│ ├── taj-goods-item.vue
│ └── types.ts
├── taj-order-item/
│ ├── index.scss
│ ├── taj-order-item.vue
│ └── types.ts
├── taj-store-appointment-popup/
│ ├── index.scss
│ ├── taj-store-appointment-popup.vue
│ └── types.ts
└── taj-store-info/
├── index.scss
├── taj-store-info.vue
└── types.ts也可以按组件路径引入:
import TajBusinessStatus from 'taj-consumer-ui/components/taj-business-status/taj-business-status.vue'营业时间工具也可以单独引用:
import { isWithinBusinessHours } from 'taj-consumer-ui'商品骨架
TajGoodsItem 只负责商品行布局,不接收业务数据。内容由 cover、title、tags、subtitle、sold、price、origin-price、discount 和 action 插槽提供。标题前默认展示“超值团”标签;可通过 show-deal-tag、deal-tag-text 配置,或使用 deal-tag 插槽完全覆盖。
<script setup lang="ts">
import TajGoodsItem from 'taj-consumer-ui/goods-item'
</script>
<template>
<TajGoodsItem custom-class="package-item" @click="handleBuy">
<template #cover>
<image class="package-cover" :src="goods.cover" mode="aspectFill" />
</template>
<template #title>
{{ goods.title }}
</template>
<template #tags>
<wd-tag v-for="tag in goods.tags" :key="tag.text" size="small">
{{ tag.text }}
</wd-tag>
</template>
<template #subtitle>
{{ goods.subtitle }}
</template>
<template #sold>
{{ goods.soldText }}
</template>
<template #price>
¥{{ goods.price }}
</template>
<template #origin-price>
¥{{ goods.originPrice }}
</template>
<template #discount>
{{ goods.discount }}
</template>
<template #action>
抢购
</template>
</TajGoodsItem>
</template>
<style>
.package-cover {
width: 100%;
height: 100%;
}
.package-item {
--xyj-goods-item-title-color: #202124;
--xyj-goods-item-price-color: #e85d04;
--xyj-goods-item-action-bg: #e85d04;
--xyj-goods-item-action-color: #ffffff;
}
</style>所有视觉变量均提供默认值,可按页面覆盖。常用变量包括:
--xyj-goods-item-title-color--xyj-goods-item-deal-tag-bg--xyj-goods-item-deal-tag-icon-color--xyj-goods-item-deal-tag-text-color--xyj-goods-item-subtitle-color--xyj-goods-item-sold-color--xyj-goods-item-price-color--xyj-goods-item-origin-price-color--xyj-goods-item-discount-color--xyj-goods-item-action-bg--xyj-goods-item-action-color
默认促销标签使用 Carbon 图标。使用方需安装 @iconify-json/carbon,在 UnoCSS 中加载 Carbon collection,并扫描组件包源码:
export default defineConfig({
content: {
filesystem: [
'node_modules/taj-consumer-ui/**/*.{vue,ts}',
],
},
presets: [
presetIcons({
collections: {
carbon: () => import('@iconify-json/carbon/icons.json').then(module => module.default),
},
}),
],
})门店信息卡片
TajStoreInfo 展示门店名称、营业时间、地址、快捷操作和停车指引。组件只回传交互事件,地图、电话、路由等业务逻辑由使用方处理。
<script setup lang="ts">
import TajStoreInfo from 'taj-consumer-ui/store-info'
const actions = [
{ key: 'navigate', label: '地图', iconClass: 'i-carbon:send-alt text-lg' },
{ key: 'call', label: '电话', iconClass: 'i-carbon:phone text-lg' },
]
</script>
<template>
<TajStoreInfo
store-name="示例门店"
business-hours="09:00-22:00"
address="示例地址"
guide-text="停车场入口位于大楼西侧"
:actions="actions"
@detail="handleDetail"
@guide="handleGuide"
@action="handleAction"
/>
</template>订单列表项
TajOrderItem 只负责订单卡片的展示与详情事件。订单状态枚举仍由使用方维护,并在传入组件前转换为 status-label、status-type 和 active-price,避免公共组件依赖具体业务状态。
<script setup lang="ts">
import TajOrderItem from 'taj-consumer-ui/order-item'
const order = {
title: '精品洗鞋套餐',
statusLabel: '待使用',
statusType: 'primary' as const,
activePrice: true,
}
</script>
<template>
<TajOrderItem
:title="order.title"
:status-label="order.statusLabel"
:status-type="order.statusType"
service-type="到店服务"
time-label="下单时间"
time="2026-08-09 20:30"
price="39.90"
:active-price="order.activePrice"
@detail="handleDetail"
/>
</template>常用视觉变量包括:
--xyj-order-item-bg--xyj-order-item-radius--xyj-order-item-shadow--xyj-order-item-title-color--xyj-order-item-meta-color--xyj-order-item-price-color--xyj-order-item-price-inactive-color--xyj-order-item-button-color--xyj-order-item-button-border-color
门店预约弹窗
TajStoreAppointmentPopup 负责预约表单、日期选择和输入校验,不依赖项目 API、登录状态或状态管理。校验通过后仅触发 confirm,接口请求由使用方执行。
<script setup lang="ts">
import type {
StoreAppointmentConfirmPayload,
StoreAppointmentPopupExpose,
} from 'taj-consumer-ui'
import { ref } from 'vue'
import TajStoreAppointmentPopup from 'taj-consumer-ui/store-appointment-popup'
const popupRef = ref<StoreAppointmentPopupExpose>()
const submitting = ref(false)
function openAppointment() {
popupRef.value?.open('store-id', '示例门店')
}
async function handleConfirm(payload: StoreAppointmentConfirmPayload) {
submitting.value = true
try {
await submitAppointment({
storeId: payload.storeId,
arrivalTimestamp: payload.arrivalTimestamp,
peopleCount: payload.peopleCount,
contactPhone: payload.contactPhone,
remark: payload.remark,
})
popupRef.value?.close()
}
finally {
submitting.value = false
}
}
</script>
<template>
<button @click="openAppointment">
预约
</button>
<TajStoreAppointmentPopup
ref="popupRef"
:submitting="submitting"
@confirm="handleConfirm"
/>
</template>confirm 参数包含:
storeId:调用open()时传入的门店 IDstoreName:调用open()时传入的门店名称arrivalTimestamp:用户选择日期的时间戳peopleCount:衣物件数contactPhone:会员手机号remark:可选备注
组件不会自动关闭。接口成功后由外部调用 popupRef.value?.close();提交期间通过 submitting 禁止重复确认并显示提交中文字。
常用视觉变量包括:
--xyj-store-appointment-title-color--xyj-store-appointment-subtitle-color--xyj-store-appointment-label-color--xyj-store-appointment-value-color--xyj-store-appointment-placeholder-color--xyj-store-appointment-textarea-bg--xyj-store-appointment-confirm-bg--xyj-store-appointment-confirm-color
发布
本包发布到 npm 官方公共仓库。即使本机默认使用淘宝镜像,登录、查询和发布命令也必须显式指定 https://registry.npmjs.org/。
1. 进入项目并确认环境
cd /Users/pengxiongkun/Documents/extra-income/xyj/wx-group/taj-consumer-ui
node --version
pnpm --versionNode.js 版本必须满足 package.json 中的 engines 要求,pnpm 建议使用项目声明的版本。
2. 查询线上版本
发布前先确认当前 npm 最新版本,避免重复发布:
npm view taj-consumer-ui version --registry=https://registry.npmjs.org/
npm view taj-consumer-ui versions --json --registry=https://registry.npmjs.org/npm 不允许覆盖已发布的同名同版本包。每次发布都必须先更新 package.json 的 version。
可根据变更范围选择版本升级命令:
# 修复或小幅兼容更新,例如 0.1.7 -> 0.1.8
npm version patch --no-git-tag-version
# 新增向后兼容功能,例如 0.1.7 -> 0.2.0
npm version minor --no-git-tag-version
# 存在不兼容修改,例如 0.1.7 -> 1.0.0
npm version major --no-git-tag-version如果已经手动修改过 package.json 的版本号,则不需要再执行 npm version。
3. 登录 npm 官方源
本机默认 registry 可能是 registry.npmmirror.com,因此不要直接执行不带 registry 的 npm login。
npm login --auth-type=web --registry=https://registry.npmjs.org/浏览器验证完成后检查登录身份:
pnpm publish:whoami也可以直接执行完整命令:
npm whoami --registry=https://registry.npmjs.org/命令必须输出正确的 npm 用户名。如果返回 401 Unauthorized,说明登录凭证无效或已过期,需要重新登录。
4. 发布前检查
先检查工作区,避免把临时文件、密钥或错误版本发布出去:
git status --short
git diff --check执行类型检查和 npm 压缩包内容预览:
pnpm publish:check该命令等价于:
pnpm type-check
pnpm pack:check重点确认 npm pack --dry-run 输出中包含新增组件、类型、样式、README.md、index.ts 和 global.d.ts,且不包含 .env、Token、日志或其他敏感文件。
5. 发布公共包
确认版本号、登录身份和打包内容无误后执行:
pnpm publish:public该命令等价于:
npm publish --access public --registry=https://registry.npmjs.org/如果 npm 账号启用了双重验证,发布过程中可能要求输入一次性验证码。按提示输入当前 OTP 即可。
6. 验证发布结果
npm view taj-consumer-ui version --registry=https://registry.npmjs.org/
npm view taj-consumer-ui@最新版本号 dist --registry=https://registry.npmjs.org/例如验证 0.1.7:
npm view [email protected] version --registry=https://registry.npmjs.org/
npm view [email protected] dist --registry=https://registry.npmjs.org/常见错误
Public registration is not allowed:登录时使用了淘宝镜像。重新执行带 npm 官方 registry 的登录命令。401 Unauthorized:npm 登录凭证已失效,重新登录官方源。- 发布时返回
404 Not Found - PUT,但旧版本可查询:通常也是发布凭证失效。先执行pnpm publish:whoami,确认身份后重试。 EOTP:账号开启了双重验证,需要提供 OTP,或使用允许发布的 granular access token。EPUBLISHCONFLICT:当前版本已经发布,先升级package.json版本号。403 Forbidden:账号没有该包的发布权限,或 npm 账号安全策略未满足发布要求。
本包为公开源码包,禁止发布 API 密钥、Token、环境变量、内部接口凭证及用户数据。
