224 lines
9.4 KiB
Python
224 lines
9.4 KiB
Python
|
|
#!/usr/bin/env python
|
|||
|
|
# -*- coding: utf-8 -*-
|
|||
|
|
|
|||
|
|
import os
|
|||
|
|
import sqlite3
|
|||
|
|
import csv
|
|||
|
|
import sys
|
|||
|
|
import argparse
|
|||
|
|
from datetime import datetime
|
|||
|
|
|
|||
|
|
# 数据库路径
|
|||
|
|
db_path = '/root/autodl-tmp/TravelContentCreator/distribution.db'
|
|||
|
|
|
|||
|
|
def query_products(product_name=None, object_name=None, output_file=None, show_undistributed_only=False):
|
|||
|
|
"""查询产品信息
|
|||
|
|
|
|||
|
|
Args:
|
|||
|
|
product_name: 产品名称(可选)
|
|||
|
|
object_name: 景点名称(可选)
|
|||
|
|
output_file: 输出CSV文件路径(可选)
|
|||
|
|
show_undistributed_only: 是否只显示未分发的内容
|
|||
|
|
|
|||
|
|
Returns:
|
|||
|
|
查询结果列表
|
|||
|
|
"""
|
|||
|
|
# 连接数据库
|
|||
|
|
try:
|
|||
|
|
conn = sqlite3.connect(db_path)
|
|||
|
|
conn.row_factory = sqlite3.Row # 设置结果为字典格式
|
|||
|
|
cursor = conn.cursor()
|
|||
|
|
print(f"已连接到数据库: {db_path}")
|
|||
|
|
except sqlite3.Error as e:
|
|||
|
|
print(f"数据库连接错误: {e}")
|
|||
|
|
return []
|
|||
|
|
|
|||
|
|
try:
|
|||
|
|
# 构建查询条件
|
|||
|
|
conditions = []
|
|||
|
|
params = []
|
|||
|
|
|
|||
|
|
if product_name:
|
|||
|
|
conditions.append("product LIKE ?")
|
|||
|
|
params.append(f"%{product_name}%")
|
|||
|
|
|
|||
|
|
if object_name:
|
|||
|
|
conditions.append("object LIKE ?")
|
|||
|
|
params.append(f"%{object_name}%")
|
|||
|
|
|
|||
|
|
if show_undistributed_only:
|
|||
|
|
conditions.append("is_distributed = 0")
|
|||
|
|
|
|||
|
|
# 构建WHERE子句
|
|||
|
|
where_clause = " AND ".join(conditions) if conditions else "1=1"
|
|||
|
|
|
|||
|
|
# 执行查询
|
|||
|
|
query = f"""
|
|||
|
|
SELECT
|
|||
|
|
id, entry_id, product, object, date, logic, judge_status,
|
|||
|
|
output_txt_path, poster_path, article_json_path, created_at, is_distributed
|
|||
|
|
FROM
|
|||
|
|
contents
|
|||
|
|
WHERE
|
|||
|
|
{where_clause}
|
|||
|
|
ORDER BY
|
|||
|
|
product, object, entry_id
|
|||
|
|
"""
|
|||
|
|
|
|||
|
|
cursor.execute(query, params)
|
|||
|
|
results = [dict(row) for row in cursor.fetchall()]
|
|||
|
|
|
|||
|
|
# 获取分布统计信息
|
|||
|
|
statistics = {}
|
|||
|
|
if results:
|
|||
|
|
# 按产品分组统计
|
|||
|
|
cursor.execute(f"""
|
|||
|
|
SELECT
|
|||
|
|
product,
|
|||
|
|
COUNT(*) as count,
|
|||
|
|
COUNT(CASE WHEN judge_status = 1 THEN 1 END) as approved_count,
|
|||
|
|
COUNT(CASE WHEN is_distributed = 1 THEN 1 END) as distributed_count
|
|||
|
|
FROM
|
|||
|
|
contents
|
|||
|
|
WHERE
|
|||
|
|
product IS NOT NULL AND product != '' AND {where_clause}
|
|||
|
|
GROUP BY
|
|||
|
|
product
|
|||
|
|
ORDER BY
|
|||
|
|
count DESC
|
|||
|
|
""", params)
|
|||
|
|
statistics['products'] = [dict(row) for row in cursor.fetchall()]
|
|||
|
|
|
|||
|
|
# 按景点分组统计
|
|||
|
|
cursor.execute(f"""
|
|||
|
|
SELECT
|
|||
|
|
object,
|
|||
|
|
COUNT(*) as count,
|
|||
|
|
COUNT(CASE WHEN judge_status = 1 THEN 1 END) as approved_count,
|
|||
|
|
COUNT(CASE WHEN is_distributed = 1 THEN 1 END) as distributed_count
|
|||
|
|
FROM
|
|||
|
|
contents
|
|||
|
|
WHERE
|
|||
|
|
object IS NOT NULL AND object != '' AND {where_clause}
|
|||
|
|
GROUP BY
|
|||
|
|
object
|
|||
|
|
ORDER BY
|
|||
|
|
count DESC
|
|||
|
|
LIMIT 20
|
|||
|
|
""", params)
|
|||
|
|
statistics['objects'] = [dict(row) for row in cursor.fetchall()]
|
|||
|
|
|
|||
|
|
# 输出结果
|
|||
|
|
if results:
|
|||
|
|
print(f"\n查询到 {len(results)} 条产品记录")
|
|||
|
|
|
|||
|
|
# 输出前10条记录
|
|||
|
|
print("\n===== 查询结果 (前10条) =====")
|
|||
|
|
for i, row in enumerate(results[:10], 1):
|
|||
|
|
judge_status = '已通过' if row['judge_status'] == 1 else '未通过' if row['judge_status'] == 0 else '未知'
|
|||
|
|
distributed = '已分发' if row['is_distributed'] == 1 else '未分发'
|
|||
|
|
print(f"{i}. ID: {row['entry_id']}, 产品: {row['product']}, 景点: {row['object']}, 审核: {judge_status}, 分发状态: {distributed}")
|
|||
|
|
|
|||
|
|
if len(results) > 10:
|
|||
|
|
print(f"... 还有 {len(results) - 10} 条记录未显示")
|
|||
|
|
|
|||
|
|
# 输出统计信息
|
|||
|
|
if 'products' in statistics and statistics['products']:
|
|||
|
|
print("\n===== 产品统计 =====")
|
|||
|
|
for prod in statistics['products']:
|
|||
|
|
dist_percent = (prod['distributed_count'] / prod['count'] * 100) if prod['count'] > 0 else 0
|
|||
|
|
approved_percent = (prod['approved_count'] / prod['count'] * 100) if prod['count'] > 0 else 0
|
|||
|
|
print(f"产品: {prod['product']}")
|
|||
|
|
print(f" - 内容总数: {prod['count']}")
|
|||
|
|
print(f" - 已审核通过: {prod['approved_count']} ({approved_percent:.1f}%)")
|
|||
|
|
print(f" - 已分发: {prod['distributed_count']} ({dist_percent:.1f}%)")
|
|||
|
|
print(f" - 未分发: {prod['count'] - prod['distributed_count']} ({100 - dist_percent:.1f}%)")
|
|||
|
|
|
|||
|
|
if 'objects' in statistics and statistics['objects'] and len(statistics['objects']) <= 10:
|
|||
|
|
print("\n===== 景点统计 =====")
|
|||
|
|
for obj in statistics['objects']:
|
|||
|
|
dist_percent = (obj['distributed_count'] / obj['count'] * 100) if obj['count'] > 0 else 0
|
|||
|
|
approved_percent = (obj['approved_count'] / obj['count'] * 100) if obj['count'] > 0 else 0
|
|||
|
|
print(f"景点: {obj['object']}")
|
|||
|
|
print(f" - 内容总数: {obj['count']}")
|
|||
|
|
print(f" - 已审核通过: {obj['approved_count']} ({approved_percent:.1f}%)")
|
|||
|
|
print(f" - 已分发: {obj['distributed_count']} ({dist_percent:.1f}%)")
|
|||
|
|
print(f" - 未分发: {obj['count'] - obj['distributed_count']} ({100 - dist_percent:.1f}%)")
|
|||
|
|
|
|||
|
|
# 未分发内容和已分发内容的汇总
|
|||
|
|
total_count = len(results)
|
|||
|
|
distributed_count = sum(1 for r in results if r['is_distributed'] == 1)
|
|||
|
|
undistributed_count = total_count - distributed_count
|
|||
|
|
|
|||
|
|
print("\n===== 分发状态汇总 =====")
|
|||
|
|
print(f"总内容数: {total_count}")
|
|||
|
|
print(f"已分发: {distributed_count} ({distributed_count/total_count*100:.1f}% 如果为0)" if total_count > 0 else "已分发: 0 (0%)")
|
|||
|
|
print(f"未分发: {undistributed_count} ({undistributed_count/total_count*100:.1f}% 如果为100%)" if total_count > 0 else "未分发: 0 (0%)")
|
|||
|
|
|
|||
|
|
# 如果指定了输出文件,保存结果到CSV
|
|||
|
|
if output_file:
|
|||
|
|
# 确保目录存在
|
|||
|
|
os.makedirs(os.path.dirname(os.path.abspath(output_file)), exist_ok=True)
|
|||
|
|
|
|||
|
|
with open(output_file, 'w', newline='', encoding='utf-8-sig') as f:
|
|||
|
|
if results:
|
|||
|
|
# 确定CSV列
|
|||
|
|
fieldnames = list(results[0].keys())
|
|||
|
|
writer = csv.DictWriter(f, fieldnames=fieldnames)
|
|||
|
|
writer.writeheader()
|
|||
|
|
writer.writerows(results)
|
|||
|
|
print(f"\n查询结果已保存到: {output_file}")
|
|||
|
|
else:
|
|||
|
|
print("\n未查询到相关产品记录")
|
|||
|
|
|
|||
|
|
# 检查数据库是否有任何内容记录
|
|||
|
|
cursor.execute("SELECT COUNT(*) as count FROM contents")
|
|||
|
|
count = cursor.fetchone()['count']
|
|||
|
|
|
|||
|
|
if count == 0:
|
|||
|
|
print("\n提示: 数据库中没有任何内容记录,请先导入数据")
|
|||
|
|
else:
|
|||
|
|
print(f"\n提示: 数据库中有 {count} 条内容记录,但没有符合条件的产品")
|
|||
|
|
|
|||
|
|
return results
|
|||
|
|
|
|||
|
|
except Exception as e:
|
|||
|
|
print(f"查询产品时出错: {e}")
|
|||
|
|
import traceback
|
|||
|
|
traceback.print_exc()
|
|||
|
|
return []
|
|||
|
|
finally:
|
|||
|
|
conn.close()
|
|||
|
|
|
|||
|
|
def main():
|
|||
|
|
parser = argparse.ArgumentParser(description="查询数据库中的产品信息")
|
|||
|
|
parser.add_argument("--product", type=str, help="按产品名称查询")
|
|||
|
|
parser.add_argument("--object", type=str, help="按景点名称查询")
|
|||
|
|
parser.add_argument("--output", type=str, help="输出CSV文件路径")
|
|||
|
|
parser.add_argument("--all", action="store_true", help="查询所有产品")
|
|||
|
|
parser.add_argument("--export-csv", action="store_true", help="导出结果到CSV文件")
|
|||
|
|
parser.add_argument("--undistributed", action="store_true", help="只显示未分发的内容")
|
|||
|
|
|
|||
|
|
args = parser.parse_args()
|
|||
|
|
|
|||
|
|
# 默认输出文件
|
|||
|
|
output_file = None
|
|||
|
|
if args.output:
|
|||
|
|
output_file = args.output
|
|||
|
|
elif args.export_csv or args.all:
|
|||
|
|
timestamp = datetime.now().strftime('%Y%m%d_%H%M%S')
|
|||
|
|
suffix = "_undistributed" if args.undistributed else ""
|
|||
|
|
output_file = f"/root/autodl-tmp/TravelContentCreator/output/product_query{suffix}_{timestamp}.csv"
|
|||
|
|
|
|||
|
|
# 执行查询
|
|||
|
|
if args.product or args.object or args.all or args.undistributed:
|
|||
|
|
results = query_products(args.product, args.object, output_file, args.undistributed)
|
|||
|
|
return len(results) > 0
|
|||
|
|
else:
|
|||
|
|
print("请提供查询条件: --product, --object, --all 或 --undistributed")
|
|||
|
|
parser.print_help()
|
|||
|
|
return False
|
|||
|
|
|
|||
|
|
if __name__ == "__main__":
|
|||
|
|
success = main()
|
|||
|
|
sys.exit(0 if success else 1)
|