a
This commit is contained in:
parent
3bac042273
commit
66d68e319f
|
|
@ -39,10 +39,8 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
])
|
||||
|
||||
const isAdmin = (currentUser?.role || '') === 'admin'
|
||||
const globalStrategyAccountId = parseInt(String(configMeta?.global_strategy_account_id || '1'), 10) || 1
|
||||
const isGlobalStrategyAccount = isAdmin && currentAccountId === globalStrategyAccountId
|
||||
|
||||
// 预设方案配置
|
||||
|
||||
// 预设方案配置(必须在函数定义之前)
|
||||
const presets = {
|
||||
swing: {
|
||||
name: '波段回归(推荐)',
|
||||
|
|
@ -184,6 +182,104 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
}
|
||||
}
|
||||
|
||||
// 所有函数定义(必须在 useEffect 之前)
|
||||
const loadUsers = async () => {
|
||||
try {
|
||||
const list = await api.getUsers()
|
||||
setUsers(Array.isArray(list) ? list : [])
|
||||
} catch (error) {
|
||||
setMessage('加载用户列表失败: ' + (error.message || '未知错误'))
|
||||
} finally {
|
||||
setLoading(false)
|
||||
}
|
||||
}
|
||||
|
||||
const loadAccounts = async () => {
|
||||
try {
|
||||
const list = await api.getAccounts()
|
||||
setAccounts(Array.isArray(list) ? list : [])
|
||||
} catch (error) {
|
||||
console.error('加载账号列表失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
const loadConfigMeta = async () => {
|
||||
try {
|
||||
const m = await api.getConfigMeta()
|
||||
setConfigMeta(m || null)
|
||||
} catch (e) {
|
||||
setConfigMeta(null)
|
||||
}
|
||||
}
|
||||
|
||||
const loadConfigs = async () => {
|
||||
try {
|
||||
const data = await api.getConfigs()
|
||||
setConfigs(data)
|
||||
} catch (error) {
|
||||
console.error('Failed to load configs:', error)
|
||||
}
|
||||
}
|
||||
|
||||
const loadSystemStatus = async () => {
|
||||
try {
|
||||
const res = await api.getTradingSystemStatus()
|
||||
setSystemStatus(res)
|
||||
} catch (error) {
|
||||
// 静默失败
|
||||
}
|
||||
}
|
||||
|
||||
const loadBackendStatus = async () => {
|
||||
try {
|
||||
const res = await api.getBackendStatus()
|
||||
setBackendStatus(res)
|
||||
} catch (error) {
|
||||
// 静默失败
|
||||
}
|
||||
}
|
||||
|
||||
// 检测当前配置匹配哪个预设方案
|
||||
const detectCurrentPreset = () => {
|
||||
if (!configs || Object.keys(configs).length === 0) return null
|
||||
|
||||
for (const [presetKey, preset] of Object.entries(presets)) {
|
||||
let match = true
|
||||
for (const [key, expectedValue] of Object.entries(preset.configs)) {
|
||||
const currentConfig = configs[key]
|
||||
if (!currentConfig) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
|
||||
let currentValue = currentConfig.value
|
||||
if (key.includes('PERCENT') || key.includes('PCT')) {
|
||||
if (PCT_LIKE_KEYS.has(key)) {
|
||||
currentValue = currentValue <= 0.05 ? currentValue * 100 : currentValue
|
||||
} else {
|
||||
currentValue = currentValue * 100
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof expectedValue === 'number' && typeof currentValue === 'number') {
|
||||
if (Math.abs(currentValue - expectedValue) > 0.01) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
} else if (currentValue !== expectedValue) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
return presetKey
|
||||
}
|
||||
}
|
||||
|
||||
return null
|
||||
}
|
||||
|
||||
useEffect(() => {
|
||||
loadUsers()
|
||||
loadAccounts()
|
||||
|
|
@ -199,7 +295,8 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
}, 3000)
|
||||
return () => clearInterval(timer)
|
||||
}
|
||||
}, [])
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
}, [isAdmin])
|
||||
|
||||
const loadUsers = async () => {
|
||||
try {
|
||||
|
|
@ -346,46 +443,6 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
}
|
||||
}
|
||||
|
||||
// 预设方案函数
|
||||
const detectCurrentPreset = () => {
|
||||
if (!configs || Object.keys(configs).length === 0) return null
|
||||
|
||||
for (const [presetKey, preset] of Object.entries(presets)) {
|
||||
let match = true
|
||||
for (const [key, expectedValue] of Object.entries(preset.configs)) {
|
||||
const currentConfig = configs[key]
|
||||
if (!currentConfig) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
|
||||
let currentValue = currentConfig.value
|
||||
if (key.includes('PERCENT') || key.includes('PCT')) {
|
||||
if (PCT_LIKE_KEYS.has(key)) {
|
||||
currentValue = currentValue <= 0.05 ? currentValue * 100 : currentValue
|
||||
} else {
|
||||
currentValue = currentValue * 100
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof expectedValue === 'number' && typeof currentValue === 'number') {
|
||||
if (Math.abs(currentValue - expectedValue) > 0.01) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
} else if (currentValue !== expectedValue) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
return presetKey
|
||||
}
|
||||
}
|
||||
|
||||
return null
|
||||
}
|
||||
|
||||
const applyPreset = async (presetKey) => {
|
||||
const preset = presets[presetKey]
|
||||
|
|
@ -518,10 +575,45 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
return a.key.localeCompare(b.key)
|
||||
})
|
||||
|
||||
// 临时获取当前配置以检测预设
|
||||
const tempConfigs = data || {}
|
||||
let detectedPreset = null
|
||||
for (const [presetKey, preset] of Object.entries(presets)) {
|
||||
let match = true
|
||||
for (const [key, expectedValue] of Object.entries(preset.configs)) {
|
||||
const currentConfig = tempConfigs[key]
|
||||
if (!currentConfig) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
let currentValue = currentConfig.value
|
||||
if (key.includes('PERCENT') || key.includes('PCT')) {
|
||||
if (PCT_LIKE_KEYS.has(key)) {
|
||||
currentValue = currentValue <= 0.05 ? currentValue * 100 : currentValue
|
||||
} else {
|
||||
currentValue = currentValue * 100
|
||||
}
|
||||
}
|
||||
if (typeof expectedValue === 'number' && typeof currentValue === 'number') {
|
||||
if (Math.abs(currentValue - expectedValue) > 0.01) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
} else if (currentValue !== expectedValue) {
|
||||
match = false
|
||||
break
|
||||
}
|
||||
}
|
||||
if (match) {
|
||||
detectedPreset = presetKey
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
const snapshot = {
|
||||
fetched_at: now.toISOString(),
|
||||
note: 'display_value 对 PERCENT/PCT 做了百分比换算;敏感字段可选择脱敏/明文。',
|
||||
preset_detected: detectCurrentPreset(),
|
||||
preset_detected: detectedPreset,
|
||||
system_status: systemStatus ? {
|
||||
running: !!systemStatus.running,
|
||||
pid: systemStatus.pid || null,
|
||||
|
|
@ -577,7 +669,17 @@ const GlobalConfig = ({ currentUser }) => {
|
|||
}
|
||||
}
|
||||
|
||||
const currentPreset = detectCurrentPreset()
|
||||
// 计算全局策略账号ID(依赖 configMeta)
|
||||
const globalStrategyAccountId = React.useMemo(() => {
|
||||
return parseInt(String(configMeta?.global_strategy_account_id || '1'), 10) || 1
|
||||
}, [configMeta])
|
||||
|
||||
const isGlobalStrategyAccount = isAdmin && currentAccountId === globalStrategyAccountId
|
||||
|
||||
// 计算当前预设(在 render 时计算,依赖 configs)
|
||||
const currentPreset = React.useMemo(() => {
|
||||
return detectCurrentPreset()
|
||||
}, [configs])
|
||||
|
||||
const handleCreateUser = async () => {
|
||||
if (!newUser.username || !newUser.password) {
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user