308 lines
10 KiB
Python
308 lines
10 KiB
Python
# -*- coding: utf-8 -*-
|
||
|
||
def widget_pricing(rows):
|
||
"""
|
||
核心汇算部件价格逻辑
|
||
"""
|
||
# 初始化资源字典
|
||
resources = {
|
||
"cpu": {},
|
||
"memory": {},
|
||
"disk": {},
|
||
"gpu": {}
|
||
}
|
||
|
||
# 处理查询结果并填充资源字典
|
||
for row in rows:
|
||
resource_type, model, unit_price, resource_unit, stock = row
|
||
if model == 'STANDARD':
|
||
model = 'STANDARD'
|
||
else:
|
||
model = model.strip()
|
||
|
||
if resource_type in resources:
|
||
resources[resource_type][model] = {
|
||
"unit_price": float(unit_price),
|
||
"resource_unit": resource_unit,
|
||
"stock": int(stock)
|
||
}
|
||
|
||
# 将资源字典转换为 JSON 字符串
|
||
return json.dumps(resources, indent=4)
|
||
|
||
def apply_discount(price, duration):
|
||
"""折扣策略"""
|
||
if duration >= 720: # 使用超过30天
|
||
return price * 0.9 # 9折优惠
|
||
return price
|
||
|
||
def get_memory_price(amount):
|
||
"""内存阶梯定价"""
|
||
if amount <= 4096: # 4GB以下
|
||
return 0.00012 # 较高单价
|
||
return 0.0001 # 量大优惠
|
||
|
||
|
||
def calculate_price(request_data, RESOURCE_PRICING, DURATION_FACTOR):
|
||
"""
|
||
计算多种资源组合的总价格
|
||
返回计算结果,包含总价和各资源明细
|
||
"""
|
||
# 初始化结果
|
||
result = {
|
||
"total_price": 0.0,
|
||
"currency": "元",
|
||
"price_details": [],
|
||
"status": True,
|
||
"message": "汇算正常"
|
||
}
|
||
|
||
# 获取资源配置
|
||
resources = request_data.get("resources", [])
|
||
if not resources:
|
||
result["status"] = False
|
||
result["message"] = "异常:请求中必须包含资源信息"
|
||
return result
|
||
|
||
# 获取使用时长并转换为小时
|
||
duration = request_data.get("duration", 1)
|
||
duration_unit = request_data.get("duration_unit", "小时")
|
||
duration_hours = duration * DURATION_FACTOR.get(duration_unit, 1)
|
||
result["duration"] = duration
|
||
result["duration_unit"] = duration_unit
|
||
# 遍历计算每种资源的价格
|
||
for resource in resources:
|
||
resource_type = resource.get("type")
|
||
amount = resource.get("amount", 0)
|
||
|
||
if not resource_type or amount <= 0:
|
||
continue
|
||
|
||
try:
|
||
# 获取资源定价信息
|
||
if resource_type in ["cpu", "gpu", "disk", "memory"]:
|
||
# 需要查询型号的部件类型
|
||
model = resource.get("model")
|
||
if not model:
|
||
raise ValueError(f"{resource_type} 必须指定部件型号/系列")
|
||
if not RESOURCE_PRICING.get(resource_type):
|
||
raise ValueError(f"没有该类型组件")
|
||
resource_info = RESOURCE_PRICING[resource_type].get(model)
|
||
if not resource_info:
|
||
raise ValueError(f"无效的 {resource_type} 部件型号: {model}")
|
||
resource_name = f"{resource_type} {model}"
|
||
else:
|
||
raise ValueError(f"不支持的资源类型: {resource_type}")
|
||
|
||
# 检查库存
|
||
if resource_info["stock"] < amount:
|
||
raise ValueError(f'{resource_name} 库存不足 (库存: {resource_info["stock"]}, 请求: {amount})')
|
||
|
||
# 计算价格
|
||
unit_price = resource_info["unit_price"]
|
||
subtotal = unit_price * float(amount) * float(duration_hours)
|
||
|
||
# 更新总价和明细
|
||
result["total_price"] += subtotal
|
||
result["price_details"].append({
|
||
"resource_name": resource_name,
|
||
"resource_type": resource_type,
|
||
"amount": amount,
|
||
"resource_unit": resource_info["resource_unit"],
|
||
"unit_price": unit_price,
|
||
"duration": duration,
|
||
"duration_unit": duration_unit,
|
||
"subtotal": round(subtotal, 2)
|
||
})
|
||
|
||
except Exception as e:
|
||
# 记录错误并继续处理其他资源
|
||
result["price_details"].append({
|
||
"resource_type": resource_type,
|
||
"error": str(e)
|
||
})
|
||
if result["status"] == True:
|
||
result["status"] = False
|
||
result["message"] = str(e)
|
||
|
||
# 结果格式化
|
||
result["total_price"] = round(result["total_price"], 2)
|
||
|
||
return result
|
||
|
||
|
||
# 使用示例
|
||
if __name__ == "__main__":
|
||
# RESOURCE_PRICING = widget_pricing()
|
||
# 模拟资源定价数据(包含多种资源类型和型号)
|
||
RESOURCE_PRICING2 = {
|
||
# CPU 资源(按核计价,不同型号单价不同)
|
||
"cpu": {
|
||
"AMD EPYC 7542 32-Core Processor":
|
||
{"unit_price": 0.8, "resource_unit": "核", "stock": 100},
|
||
"INTEL(R) XEON(R) PLATINUM 8582C":
|
||
{"unit_price": 1.5, "resource_unit": "核", "stock": 50},
|
||
"STANDARD":
|
||
{"unit_price": 2.2, "resource_unit": "核", "stock": 0}
|
||
},
|
||
# 内存资源(按 Mi 计价,统一单价
|
||
"memory": {
|
||
"Kingston FURY": # 高性能-便宜
|
||
{"unit_price": 0.0001, "resource_unit": "Mi", "stock": 1048576}, # 1024 Gi / 1TB
|
||
"Crucial P-series": # 性能一般-价格一般
|
||
{"unit_price": 0.0005, "resource_unit": "Mi", "stock": 1048576},
|
||
"Samsung DDR4 DIMMs": # 高性能-贵
|
||
{"unit_price": 0.005, "resource_unit": "Mi", "stock": 1048576},
|
||
"STANDARD":
|
||
{"unit_price": 0.0004, "resource_unit": "Mi", "stock": 0}, # Kyy自营
|
||
},
|
||
# 云盘资源(按 Gi 计价,不同类型单价不同)
|
||
"disk": {
|
||
"DATA": # 共享数据盘
|
||
{"unit_price": 0.01, "resource_unit": "Gi", "stock": 20480}, # 20 TiB
|
||
"SYS": # 系统盘
|
||
{"unit_price": 0.005, "resource_unit": "Gi", "stock": 51200}, # 50 TiB
|
||
},
|
||
# GPU 资源(按卡计价,不同型号单价不同)
|
||
"gpu": {
|
||
"RTX4090-24G":
|
||
{"unit_price": 4.0, "resource_unit": "卡", "stock": 12},
|
||
"RTX5090-32G":
|
||
{"unit_price": 6.0, "resource_unit": "卡", "stock": 10},
|
||
"A100-80G":
|
||
{"unit_price": 18.0, "resource_unit": "卡", "stock": 5},
|
||
"V100-32G":
|
||
{"unit_price": 12.0, "resource_unit": "卡", "stock": 8},
|
||
"STANDARD-8G":
|
||
{"unit_price": 2.0, "resource_unit": "卡", "stock": 1},
|
||
}
|
||
}
|
||
|
||
RESOURCE_PRICING = {
|
||
"cpu": {
|
||
"AMD EPYC 7542 32-Core Processor": {
|
||
"unit_price": 0.8,
|
||
"resource_unit": "核",
|
||
"stock": 100
|
||
},
|
||
"STANDARD-9G": {
|
||
"unit_price": 1.22,
|
||
"resource_unit": "核",
|
||
"stock": 2
|
||
},
|
||
"STANDARD": {
|
||
"unit_price": 2.2,
|
||
"resource_unit": "核",
|
||
"stock": 0
|
||
},
|
||
"INTEL(R) XEON(R) PLATINUM 8582C": {
|
||
"unit_price": 1.5,
|
||
"resource_unit": "核",
|
||
"stock": 50
|
||
}
|
||
},
|
||
"memory": {
|
||
"Kingston FURY": {
|
||
"unit_price": 0.0001,
|
||
"resource_unit": "Mi",
|
||
"stock": 1048576
|
||
},
|
||
"Crucial P-series": {
|
||
"unit_price": 0.0005,
|
||
"resource_unit": "Mi",
|
||
"stock": 1048576
|
||
},
|
||
"STANDARD": {
|
||
"unit_price": 0.0004,
|
||
"resource_unit": "Mi",
|
||
"stock": 0
|
||
},
|
||
"Samsung DDR4 DIMMs": {
|
||
"unit_price": 0.005,
|
||
"resource_unit": "Gi",
|
||
"stock": 1048576
|
||
}
|
||
},
|
||
"disk": {
|
||
"SYS": {
|
||
"unit_price": 0.005,
|
||
"resource_unit": "Gi",
|
||
"stock": 51200
|
||
},
|
||
"DATA": {
|
||
"unit_price": 0.01,
|
||
"resource_unit": "Gi",
|
||
"stock": 20480
|
||
}
|
||
},
|
||
"gpu": {
|
||
"V100-32G": {
|
||
"unit_price": 12,
|
||
"resource_unit": "卡",
|
||
"stock": 8
|
||
},
|
||
"RTX4090-24G": {
|
||
"unit_price": 4,
|
||
"resource_unit": "卡",
|
||
"stock": 12
|
||
},
|
||
"RTX5090-32G": {
|
||
"unit_price": 6,
|
||
"resource_unit": "卡",
|
||
"stock": 10
|
||
},
|
||
"A100-80G": {
|
||
"unit_price": 18,
|
||
"resource_unit": "卡",
|
||
"stock": 5
|
||
},
|
||
"STANDARD-8G": {
|
||
"unit_price": 2,
|
||
"resource_unit": "卡",
|
||
"stock": 1
|
||
}
|
||
}
|
||
}
|
||
|
||
# 计费周期转换系数(统一转换为小时)
|
||
DURATION_FACTOR = {
|
||
"小时": 1, # 按量付费(按小时计费)
|
||
"天": 24,
|
||
"周": 168,
|
||
"月": 720 # 按30天计算(按月计费)
|
||
}
|
||
# HTTP请求示例:
|
||
# 4核CPU-INTEL(R) XEON(R) PLATINUM 8582C +
|
||
# 8GB-Samsung DDR4 DIMMs内存 +
|
||
# 512GB-DATA数据盘 +
|
||
# 2张RTX5090-32G +
|
||
# 使用1天
|
||
params = {
|
||
"resources": [
|
||
{"type": "cpu", "model": "INTEL(R) XEON(R) PLATINUM 8582C", "amount": 4},
|
||
{"type": "memory", "model": "Samsung DDR4 DIMMs", "amount": 8192}, # 8GB必须转成8192Mi
|
||
{"type": "disk", "model": "DATA", "amount": 512},
|
||
{"type": "gpu", "model": "RTX5090-32G", "amount": 2}
|
||
],
|
||
"duration": 2,
|
||
"duration_unit": "天"
|
||
}
|
||
# 计算价格
|
||
result = calculate_price(params, RESOURCE_PRICING, DURATION_FACTOR)
|
||
|
||
# 打印结果
|
||
print(f"状态: {result['status']}")
|
||
if result["message"]:
|
||
print(f"提示: {result['message']}")
|
||
print(f"实时总价: {result['total_price']}{result['currency']}/{result.get('duration')}{result.get('duration_unit')}")
|
||
|
||
print(f"价格明细: {result}")
|
||
for detail in result["price_details"]:
|
||
if "error" in detail:
|
||
print(f"❌ {detail['resource_type']}: {detail['error']}")
|
||
else:
|
||
print(f"✅ {detail['resource_name']} ({detail['amount']}{detail['resource_unit']}): "
|
||
f"{detail['subtotal']} 元 ({detail['unit_price']}元/{detail['resource_unit']}/小时 × "
|
||
f"{detail['duration']}{detail['duration_unit']})")
|
||
|