feat: add DRATIO type for dynamic ratio rules

- When download reaches threshold (GB), ratio must meet minRatio

- Card header: \u4e0b\u8f7d\u91cf \u2265 XGB \u65f6\u5206\u4eab\u7387 \u2265 Y \u2192 \u5c01\u53f7/\u5220\u9664\u8d26\u53f7

- Card body: download threshold input + required ratio input

- Preset: 100GB download, 1.0 ratio
This commit is contained in:
mediabot-pt
2026-07-06 22:13:52 +08:00
parent b5a8dfa3b8
commit d1570fb80b

View File

@@ -90,6 +90,7 @@
<el-option v-for="x in typeOptions" :key="x.value" :label="x.label" :value="x.value" />
</el-select>
<span v-if="rule.type==='TASK'" class="rule-fixed-text">考核周期 {{ rule.threshold }}天</span>
<span v-else-if="rule.type==='DRATIO'" class="rule-fixed-text">下载量 ≥ {{ rule.threshold }}GB 时分享率 ≥ {{ rule.minRatio }}</span>
<span v-else class="rule-fixed-text">{{ metricLabel(rule.metric) }} {{ condLabel(rule.condition) }} {{ rule.threshold }}{{ rule.unit || '' }}</span>
<span class="then-arrow">→</span>
<span style="color:#f56c6c;font-weight:600;font-size:13px">封号/删除账号</span>
@@ -122,6 +123,20 @@
</div>
</template>
<!-- DRATIO 动态分享率 -->
<template v-else-if="rule.type==='DRATIO'">
<div class="field-row">
<span class="field-label">下载量阈值</span>
<el-input v-model.number="rule.threshold" size="small" type="number" placeholder="GB" @input="sync" style="width:100px" />
<span class="field-hint">GB(达到此下载量后检查分享率)</span>
</div>
<div class="field-row">
<span class="field-label">要求分享率</span>
<el-input v-model.number="rule.minRatio" size="small" type="number" :step="0.1" placeholder="分享率" @input="sync" style="width:100px" />
<span class="field-hint">(分享率低于此值则封号/删除账号)</span>
</div>
</template>
<!-- 非 TASK:普通规则 -->
<template v-else>
<div class="field-row">
@@ -184,6 +199,7 @@ const typeOptions = [
{ value: 'HD', label: 'H&R' },
{ value: 'RATIO', label: '分享率' },
{ value: 'TASK', label: '新人考核' },
{ value: 'DRATIO', label: '动态分享率' },
]
const condOptions = [
{ value: 'GT', label: '大于' },
@@ -237,6 +253,10 @@ const onTypeChange = (rule) => {
}
rule.threshold = rule.threshold || 30
rule.unit = '天'
} else if (rule.type === 'DRATIO') {
rule.threshold = rule.threshold || 100
rule.minRatio = rule.minRatio || 1.0
rule.unit = 'GB'
} else {
const d = typeDefaults[rule.type]
if (d) { rule.metric = d.metric; rule.condition = d.condition; rule.unit = d.unit }
@@ -259,6 +279,8 @@ const presets = [
{ name:'H&R 封号', type:'HD', metric:'hnr_count', threshold:5, unit:'次', condition:'GTE', description:'H&R违规次数达到5次即封号' },
// 新人考核
{ name:'新人考核', type:'TASK', threshold:30, unit:'天', description:'新注册用户需在考核周期内完成各项要求' },
// 动态分享率
{ name:'动态分享率', type:'DRATIO', threshold:100, minRatio:1.0, unit:'GB', description:'下载量达到阈值时分享率不低于要求值' },
]
const presetCategories = [
@@ -267,10 +289,12 @@ const presetCategories = [
{ title:'流量监控', items: presets.filter(p => p.type === 'TRAFFIC') },
{ title:'H&R 惩罚', items: presets.filter(p => p.type === 'HD') },
{ title:'新人考核', items: presets.filter(p => p.type === 'TASK') },
{ title:'分享率', items: presets.filter(p => p.type === 'DRATIO') },
]
const presetDesc = (p) => {
if (p.type === 'TASK') return `考核周期 ${p.threshold||30} 天,需满足上传/下载/魔力值/做种积分/做种时间要求`
if (p.type === 'DRATIO') return `下载量 ≥ ${p.threshold||100}GB 时分享率 ≥ ${p.minRatio||1.0}`
const condLabel = condOptions.find(c => c.value === p.condition)?.label || p.condition
const appLabel = applicableOptions.find(a => a.value === p.applicable)?.label || ''
return `${metricOptions.find(m=>m.value===p.metric)?.label||p.metric} ${condLabel} ${p.threshold}${p.unit||''}${appLabel?' ('+appLabel+')':''}`