simple-event-cli
v0.8.2
Published
Simple Event 活动管理系统 CLI — 活动 / 报奖 / 投票 / 表单 / CMS / 自定义页面 / DTC 商城(商品+优惠券)全套配置能力
Maintainers
Readme
Simple Event CLI
Simple Event 活动管理系统命令行工具,覆盖活动、报奖、投票、表单、内容、自定义页面、DTC 商城(商品 / 优惠券) 与会员权益配置能力。
功能
- 活动配置管理 — 活动 CRUD、场次、票种、票种-场次绑定、批量折扣、核验通道、活动全貌树形展示
- 销售渠道管理 — 渠道 CRUD(租户全局资源,用于销售跟踪和票种可见性控制)
- 报奖系统管理 — 届次、分组、奖项、轮次、表单配置、身份模板、评委、评分、作品
- CMS 内容管理 — 内容类型、分类(含树形)、内容条目、批量导入
- 自定义页面管理 — 页面 CRUD、组件 Schema 查询,支持 Puck JSON 格式
- 投票活动管理 — 投票活动 CRUD、分类、选项、批量导入、记录查询、统计看板、树形展示(营销互动模块)
- 通用表单管理 — 表单 CRUD、模板列表、从模板 fork(覆盖申报表 / 工作坊 / 调研问卷等场景)
- DTC 商城配置(v0.8.0+)— 商品上架(SKU 矩阵 + 规格 + 参数一次写入)、商品类目(含树形)、规格、系列、SKU 改价/启停、库存调整(含 stock_log 审计)、商品券 + 活动券统一入口(满减 / 折扣 / 现金券三类型 × 商品/活动券两业务)、优惠券包
- 会员权益配置 — 会员身份、权益定义、身份权益绑定,可与虚拟权益 SKU 字段联动
- 图片上传 — 批量上传图片到 CDN,返回 URL(支持 jpg/png/gif/webp)
- 多环境支持 — 通过配置文件或环境变量切换不同环境
- 灵活输出 — 表格(默认)和 JSON 两种输出格式,方便人工查看和程序化调用
安装
npm install -g simple-event-cli快速开始
# 1. 初始化配置(输入 Server URL、API Key、API Secret)
se init
# 2. 验证连接
se whoami
# 3. 查看活动全貌
se events tree <activity-id>
# 4. 查看比赛结构
se awards tree <session-id>
# 5. 查看内容树形结构
se content items tree <type-id>命令一览
全局命令
se init # 交互式初始化配置
se config list # 查看所有配置
se config get <key> # 查看指定配置项
se config set <key> <value> # 修改配置项
se whoami # 验证 API 连接Events 活动管理
# 活动
se events activities {list,get,create,update,delete}
se events activities update-status <id> --status <draft|published|offline>
# 场次
se events sessions list --activity <id>
se events sessions {get,create,update,delete}
# 票种(含渠道可见性配置)
se events tickets list --activity <id>
se events tickets {get,create,update,delete}
# 票种-场次绑定(按场次全量替换)
se events ticket-sessions list --activity <id>
se events ticket-sessions bind --from-json <file>
# 批量折扣
se events discounts get <ticket-id>
se events discounts update <ticket-id> --from-json <file>
# 核验通道(检票入口/出口)
se events channels list --activity <id>
se events channels {get,create,update,delete}
# 活动全貌树形展示
se events tree <activity-id>Channels 销售渠道
# 销售渠道(租户全局资源,用于票种可见性控制)
se channels list [--keyword <text>] [--status <0|1>]
se channels {get,create,update,delete}Awards 报奖系统
# 项目与届次
se awards projects list
se awards sessions {list,get,create,update,delete}
# 分组与奖项
se awards categories {list,create,update,delete}
se awards units {list,get,create,update,delete}
se awards units update-participants <id> --from-json <file>
# 表单配置
se awards forms get <award-id>
se awards forms set <award-id> --from-json <file>
# 轮次与评审
se awards rounds {list,create,update,delete}
se awards identity-templates {list,get,create,update,delete}
se awards judges {list,get,create,update,delete}
# 评分与作品
se awards scores {stats,rankings}
se awards submissions {list,get,export}
# 树形展示
se awards tree <session-id>Content 内容管理
# 内容类型
se content types list [--keyword <text>]
se content types get <type-id>
se content types create --from-json <file>
se content types update <type-id> --from-json <file>
se content types delete <type-id> [-y]
# 内容分类(支持树形)
se content categories list --type <type-id> [--parent-id <id>]
se content categories tree --type <type-id>
se content categories create --from-json <file>
se content categories update <cat-id> --from-json <file>
se content categories delete <cat-id> [-y]
# 内容条目
se content items list --type <type-id> [--category <id>] [--keyword <text>]
se content items get <item-id>
se content items create --from-json <file>
se content items update <item-id> --from-json <file>
se content items delete <item-id> [-y]
se content items tree <type-id> [--published-only]
se content items import --from-json <file> [--dry-run] [-y]Vote 投票活动(营销互动)
# 投票活动
se vote activities list [--keyword <text>] [--status <0-5>]
se vote activities {get,create,update,delete}
se vote activities update-status <id> --status <draft|notStarted|running|ended|paused|cancelled>
# 投票分类(每个活动独立分类集合)
se vote categories list --activity <id>
se vote categories create --activity <id> --name <text> [--sort-order <n>]
se vote categories {update,delete}
se vote categories reorder --from-json <file>
# 投票选项
se vote options list --activity <id> [--category <id>] [--keyword <text>]
se vote options create --activity <id> --name <text> [--image <url>] [--description <text>] [--category <id>]
se vote options {update,delete}
se vote options bulk-import --from-json <file> # JSON 数组入参,不走 Excel
# 投票记录与统计
se vote records list [--activity <id>] [--user <id>]
se vote stats overview <activity-id> # 看板:参与人数、总票数、今日票数、各选项票数
se vote tree <activity-id> # 树形:活动 → 分类 → 选项 + 统计一屏前置条件:调用方 API client 需在管理后台分配 VOTE_MANAGER 权限组,且租户已启用 vote 子功能。
bulk-import JSON 格式:
{
"activity_id": "12345",
"rows": [
{ "category_name": "甜品组", "option_name": "提拉米苏", "description": "经典款", "sort_order": 1, "option_image": "https://..." },
{ "category_name": "甜品组", "option_name": "马卡龙", "description": "", "sort_order": 2, "option_image": "" }
]
}不存在的 category_name 会自动创建,留空则选项归到「未分类」。
Forms 通用表单管理
| 命令 | 说明 |
|---|---|
| se forms list [--title] [--is-open 0\|1] [--form-type 1\|2] [--is-template 0\|1] [--page n] [--page-size n] | 列表(0.7.2 起表格新增「默认」与「所属类型」两列,方便识别哪条表单是某 content_type 的默认报名模板) |
| se forms get <id> | 详情(含 formParams) |
| se forms create --from-json <file> [--title] [--is-open 0\|1] | 从 JSON 创建 |
| se forms update <id> --from-json <file> [-y] | 整体更新 |
| se forms remove <id> [-y] | 软删除 |
| se forms templates [--content-type-id <id>] | 模板列表(平台预设 + 当前租户自建) |
| se forms fork <template-id> --title <text> [--content-type-id <id>] | 从模板 fork |
| se forms mark-as-template <id> [--cancel] [--default] | 标记/取消表单为模板(用于内容报名 form_template_id 引用) |
| se forms field-types [--json] | 查看 admin 真实支持的字段 type 白名单(含 deprecated 与替代建议) |
| se forms field-types refresh | 强制刷新本地 schema 缓存 |
字段类型 schema 校验
se forms create / se forms update 在发送前会自动拉取 admin 真实支持的字段 schema,对 formParams[] 做本地 fail-fast 校验,避免写出 admin 渲染不出来的灰盒。
# 查看当前支持的 formItem / userInfo / deprecated 列表
se forms field-types
# 强制刷新缓存(admin 端 schema 变更后立即同步)
se forms field-types refresh
# 应急绕过(不推荐,admin 升级期间或本地 CLI 校验异常时用)
se forms create --from-json file.json --no-validate- 缓存路径:
~/.se-cache/form-field-schemas-<env>.json,TTL 24h,支持 ETag 续期 - 拉取失败时 CLI 输出警告但不阻断(admin 自验为最终防线)
- 命中未知 type(如
radio、checkbox、date、pdfUpload、imgUpload、videoUpload)会直接报错并给出替代建议(如radio → select (is_multiple: false))
示例 — 工作坊申报表:
# 1. 准备 JSON(formParams 是扁平 FormFieldConfig[] 数组)
cat > /tmp/se_form_workshop.json <<'EOF'
{
"title": "2026 佛山文创周·工作坊申报表",
"form_type": 1,
"isOpen": 0,
"formParams": [
{ "guid": "uf-name", "itemType": "userInfo", "type": "name", "title": "主理人姓名", "needCheck": true },
{ "guid": "ff-theme", "itemType": "formItem", "type": "textarea", "title": "工作坊主题", "needCheck": true }
]
}
EOF
# 2. 创建
se forms create --from-json /tmp/se_form_workshop.json
# 3. 拿到 id 后查看
se forms get <form-id>
# 4. 发布
echo '{"isOpen": 1}' > /tmp/publish.json
se forms update <form-id> --from-json /tmp/publish.json -y更详细字段类型说明见后端 spec 与 simple-event-config skill 的 references/form/。
Shop 商城配置(DTC 商城)
# 商品(products)
se shop products list [--keyword <text>] [--category <id>] [--status 0|1] [--page n] [--page-size n]
se shop products get <id>
se shop products create --from-json <file>
se shop products update <id> --from-json <file> [-y]
se shop products delete <id> [-y]
se shop products status <id> --status <on|off>
se shop products batch-status --ids <id1,id2,...> --status <on|off>
se shop products tree <id> # 商品 → 规格 → SKU 一屏视图
# 商品类目(product-categories)
se shop product-categories list
se shop product-categories tree # 父子层级视图
se shop product-categories create --from-json <file>
se shop product-categories update <id> --from-json <file>
se shop product-categories delete <id> [-y]
# 商品规格(product-specs,活动级共享规格池)
se shop product-specs list
se shop product-specs create --from-json <file>
se shop product-specs update <id> --from-json <file>
se shop product-specs delete <id> [-y]
# 商品系列(product-series,营销聚合)
se shop product-series list
se shop product-series get <id>
se shop product-series create --from-json <file>
se shop product-series update <id> --from-json <file>
se shop product-series delete <id> [-y]
# SKU 管理(不含库存改动)
se shop skus list --product <id>
se shop skus get <id>
se shop skus update <id> --from-json <file> # 改价/启停/排序,不允许改 stock
se shop skus batch-update --product <id> --from-json <file> # { rows: [{ id, price, ... }] }
# 库存调整(独立审计链路)
se shop stock adjust --sku <id> --delta <n> --reason <text> # delta 必须为非零整数
# 优惠券(商品券 / 活动券)
se shop coupons list [--business <shop|activity>] [--status <n>]
se shop coupons get <id>
se shop coupons create --from-json <file> # 万能兜底,需自填 discount_type / online_business_type
se shop coupons create-manjian --business <shop|activity> --from-json <file> # 满减券(discount_type=1)
se shop coupons create-zhekou --business <shop|activity> --from-json <file> # 折扣券(discount_type=2)
se shop coupons create-xianjin --business <shop|activity> --from-json <file> # 现金券(discount_type=3)
se shop coupons update <id> --from-json <file> [-y]
se shop coupons delete <id> [-y]
se shop coupons status <id> --status <on|off>
se shop coupons batch-status --ids <id1,id2,...> --status <on|off>
# 优惠券包
se shop coupon-packages list [--keyword <text>] [--status 0|1] [--page n] [--page-size n]
se shop coupon-packages get <id>
se shop coupon-packages create --from-json <file>
se shop coupon-packages update <id> --from-json <file> [-y]
se shop coupon-packages delete <id> [-y]
se shop coupon-packages status <id> --status <on|off>
se shop coupon-packages batch-status --ids <id1,id2,...> --status <on|off>单位约定(高频踩坑):
- 所有金额字段单位为「分」(非负整数),CLI 在 create/update 前会本地校验
< 100000000防止把元当分传 - 折扣券例外:
discount_value是 10-99 的整数(例 8.5 折 = 85),CLI fail-fast 拦截浮点和越界值 - bigint id 字段(product_id / sku_id / coupon_id 等)一律 string,与后端 apps/api/CLAUDE.md 红线一致
SKU 库存调整规则:
skus update/skus batch-update本地拦截stock字段,强制走stock adjust审计链路skus update/skus batch-update同时拦截lock_stock字段,避免绕过库存审计stock adjust必填--reason,--delta为非零整数(正加负减,0 不允许),后端落审计表- 入库 / 校准等场景统一用
stock adjust,便于回溯
SKU 虚拟权益字段:
{
"coupon_package_id": "优惠券包ID,可为 string / null / 空字符串",
"member_identity_id": "会员身份ID,可为 string / null / 空字符串",
"member_identity_days": 30
}member_identity_id非空时,member_identity_days必须是正整数- 清空会员身份时,
member_identity_id与member_identity_days需要同时清空(null或空字符串语义)
优惠券业务区分(online_business_type):
- 商品券(
online_business_type=1):apply_scope ∈ all / products / categories,apply_ids是商品或类目 id 数组;不接受apply_activity_ids / apply_ticket_map - 活动券(
online_business_type=2):apply_scope ∈ all / specific_activity / specific_ticket,分别用apply_activity_ids数组或apply_ticket_map对象;不接受apply_ids - 3 个
create-*语义糖会自动覆盖discount_type和online_business_type(按--business解析),调用方只关心字段语义;万能create则需自填两者 validity_type二选一:1= 固定区间(start_time + end_time)/2= 领后 N 天(valid_days),CLI 校验互斥字段不同时传
前置条件:调用方 API client 需在管理后台分配 SHOP_MANAGER 权限组(或等价细粒度权限),且租户已启用 shop 子功能。tree / categories tree 等聚合视图依赖后端最新接口(≥ 1.x.x),版本不齐时会回退到平铺列表并提示。
MG 会员权益配置
# 会员身份
se mg identities list [--keyword <text>] [--status 0|1] [--page n] [--page-size n]
se mg identities get <id>
se mg identities create --from-json <file>
se mg identities update <id> --from-json <file> [-y]
se mg identities delete <id> [-y]
# 权益定义
se mg benefits list [--keyword <text>] [--type n] [--status 0|1] [--page n] [--page-size n]
se mg benefits get <id>
se mg benefits create --from-json <file>
se mg benefits update <id> --from-json <file> [-y]
se mg benefits delete <id> [-y]
# 身份权益绑定
se mg identity-benefits list --identity <id>
se mg identity-benefits get <id>
se mg identity-benefits create --identity <id> --benefit <id> [--value <value>] [--sort n]
se mg identity-benefits update <id> --from-json <file> [-y]
se mg identity-benefits delete <id> [-y]se mg identity-benefits add 保留为 create 的 alias。
会员身份 JSON:
{
"name": "VIP 会员",
"code": "vip",
"status": 1,
"sort": 10
}权益定义 JSON:
{
"name": "专属折扣",
"code": "vip_discount",
"type": 2,
"rule": { "discount": 90 },
"status": 1,
"is_show": 1,
"need_activate": 0
}权益 type 表:
| type | 说明 | 常见 rule |
|---:|---|---|
| 1 | 积分倍数 | { "multiplier": 2 } |
| 2 | 专享价格 | { "discount": 90 } |
| 3 | 会员日 | { "weekday": 5 } |
| 4 | 优惠券 | { "coupon_id": "..." } |
| 5 | 优先购买 | { "priority": true } |
| 6 | 生日礼 | { "gift": "..." } |
| 7 | 专属抽奖 | { "activity_id": "..." } |
| 8 | 免邮费 | { "free_shipping": true } |
| 9 | 升级礼 | { "gift": "..." } |
| 10 | 活动门票 | { "ticket_id": "..." } |
身份权益 update JSON:
{
"identity_id": "1234567890",
"benefit_id": "9876543210",
"benefit_value": "30",
"sort": 10
}Pages 自定义页面
# 页面管理
se pages list [--keyword <text>]
se pages get <id> [--output <file>] [--content-only]
se pages create --from-json <file>
se pages update <id> --from-json <file>
# 组件 Schema 查询
se pages components # 列出所有可用组件
se pages components <name> # 查看组件属性详情
se pages components [name] --compact # LLM 友好的紧凑列表(含 legacy type 对照)
# AI 工作流糖
se pages outline <id> [--type <legacy>] # 页面组件概览(每组件一行 id+type+preview)
se pages set-image <pageId> <componentId> --file <local> [--index N]
# 上传 + 替换 src/images[N] 一条命令搞定默认输出 Puck 编辑器格式(PascalCase + 扁平 props);用
--compact看 LLM 友好的紧凑列表(含 legacy snake_case 对照)。 page_content 写入时可传 Puck 格式(推荐)或 legacy 格式,后端 isPuckFormat 自动转换。
AI 工作流提示:
pages components --compact输出 Puck 格式 schema(PascalCase 字段名),AI 写新页面用这套字段pages get --content-only输出 legacy 格式(小写 type、扁平字段),AI 改现有页面看这个- 后端
pages update接受两种格式,自动识别(顶层有root.props→ Puck,否则 legacy) set-image走 legacy 字段直改路径,不触发 Puck 转换,最朴素- AI 改组件单字段(如换图)用
set-image;改组件结构 / 增删组件用update --from-json整页推送
Upload 图片上传
se upload <file...> # 批量上传图片,返回 CDN URL支持 jpg/png/gif/webp,单文件 ≤ 10MB。
通用选项
| 选项 | 说明 |
|------|------|
| --json | JSON 格式输出(默认表格) |
| --env <name> | 临时指定环境 |
| --from-json <file> | 从 JSON 文件读取输入数据 |
| -y, --yes | 跳过危险操作确认 |
| --page <n> | 分页页码 |
| --page-size <n> | 每页条数 |
配置
配置文件位于 ~/.simple-event/config.json,支持多环境。通过 se init 交互式设置,或手动编辑。
环境变量可覆盖配置文件(优先级更高):
export SE_SERVER_URL=https://api.example.com
export SE_API_KEY=your-api-key
export SE_API_SECRET=your-api-secretAI Agent 集成
所有命令加 --json 即可程序化调用,错误也是结构化的 JSON 响应。
退出码:0 = 成功,1 = 业务错误,2 = 网络错误。
详细文档
完整的命令参考、JSON 示例和使用指南请查看 docs/cli-reference.md。
