Files
hfb_sys/frontend/src/features/seller/composables/usePublishDraft.ts
T

142 lines
4.5 KiB
TypeScript

import type { ChargeMode, QuantityKey, ScreenshotKey } from '@/features/listings/api/listingOptions'
import type { PublishDraft, PublishForm } from '@/types/publish'
export function defaultPublishForm(): PublishForm {
return {
server_region: '',
face_owner: '',
haf_coin_amount: '',
rank_level: '',
secret_kd: '',
fire_level: '',
daily_loss_m: 10,
accelerated_sale_ratio: '',
season_insurance: '',
stamina_level: '',
load_level: '',
login_method: '',
online_start: '',
online_end: '',
ban_record: '',
common_regions: [],
deposit_amount: '',
remark: '',
}
}
export function buildPublishDraft(options: {
form: PublishForm
quantityValues: Record<QuantityKey, number>
quantityModes: Record<QuantityKey, ChargeMode>
screenshotFiles: Record<ScreenshotKey, string[]>
selectedSkins: string[]
}): PublishDraft {
return {
form: {
...options.form,
common_regions: [...options.form.common_regions],
},
quantityValues: { ...options.quantityValues },
quantityModes: { ...options.quantityModes },
screenshotFiles: cloneScreenshotFiles(options.screenshotFiles),
selectedSkins: [...options.selectedSkins],
}
}
export function readPublishDraft(draftKey: string) {
const raw = localStorage.getItem(draftKey)
if (!raw) return null
try {
const draft = JSON.parse(raw) as Partial<PublishDraft>
return {
form: normalizeDraftForm(draft.form),
quantityValues: normalizeNumberRecord(draft.quantityValues),
quantityModes: normalizeQuantityModes(draft.quantityModes),
screenshotFiles: normalizeScreenshotFiles(draft.screenshotFiles),
selectedSkins: Array.isArray(draft.selectedSkins)
? draft.selectedSkins.filter((skin): skin is string => typeof skin === 'string')
: [],
}
} catch {
localStorage.removeItem(draftKey)
return null
}
}
export function writePublishDraft(draftKey: string, draft: PublishDraft) {
const nextValue = JSON.stringify(draft)
if (localStorage.getItem(draftKey) === nextValue) return
localStorage.setItem(draftKey, nextValue)
}
export function removePublishDraft(draftKey: string) {
localStorage.removeItem(draftKey)
}
export function clearRecord(record: Record<string, unknown>) {
for (const key of Object.keys(record)) delete record[key]
}
function normalizeDraftForm(value: unknown): PublishForm {
const next = defaultPublishForm()
if (!isRecord(value)) return next
for (const key of Object.keys(next) as Array<keyof PublishForm>) {
if (key === 'common_regions') continue
const draftValue = value[key]
if (draftValue !== undefined) next[key] = draftValue as never
}
next.common_regions = Array.isArray(value.common_regions)
? value.common_regions.filter((region): region is string => typeof region === 'string')
: []
// 默认使用参考比例:如果草稿中的 accelerated_sale_ratio 是 0 或未设置,重置为空字符串
if (!next.accelerated_sale_ratio || next.accelerated_sale_ratio === 0) {
next.accelerated_sale_ratio = ''
}
if (next.haf_coin_amount === 0) next.haf_coin_amount = ''
if (String(next.secret_kd).trim() === '0') next.secret_kd = ''
if (next.fire_level === 0) next.fire_level = ''
return next
}
function normalizeNumberRecord(value: unknown) {
const record: Record<string, number> = {}
if (!isRecord(value)) return record
for (const [key, item] of Object.entries(value)) {
const parsed = Number(item)
if (Number.isFinite(parsed)) record[key] = parsed
}
return record
}
function normalizeScreenshotFiles(value: unknown) {
const record: Record<string, string[]> = {}
if (!isRecord(value)) return record
for (const [key, item] of Object.entries(value)) {
if (typeof item === 'string') {
record[key] = item ? [item] : []
continue
}
if (Array.isArray(item)) {
record[key] = item.filter((url): url is string => typeof url === 'string' && Boolean(url))
}
}
return record
}
function cloneScreenshotFiles(value: Record<string, string[]>) {
return Object.fromEntries(Object.entries(value).map(([key, urls]) => [key, [...urls]]))
}
function normalizeQuantityModes(value: unknown) {
const record: Record<string, ChargeMode> = {}
if (!isRecord(value)) return record
for (const [key, item] of Object.entries(value)) {
if (item === '赠送' || item === '收费') record[key] = item
}
return record
}
function isRecord(value: unknown): value is Record<string, unknown> {
return typeof value === 'object' && value !== null
}