feat: implement core backend API structure and frontend service layer for case management and authentication
This commit is contained in:
96
backend/routes/reports.py
Normal file
96
backend/routes/reports.py
Normal file
@@ -0,0 +1,96 @@
|
||||
import io
|
||||
import pandas as pd
|
||||
from flask import Blueprint, send_file, jsonify, make_response
|
||||
from reportlab.lib.pagesizes import letter
|
||||
from reportlab.pdfgen import canvas
|
||||
from reportlab.lib import colors
|
||||
from reportlab.lib.styles import getSampleStyleSheet
|
||||
from reportlab.platypus import SimpleDocTemplate, Paragraph, Spacer, Table, TableStyle
|
||||
|
||||
from ..db import get_db_connection, release_db_connection
|
||||
from ..middleware import token_required
|
||||
|
||||
reports_blueprint = Blueprint('reports', __name__)
|
||||
|
||||
@reports_blueprint.route('/reports/cases/csv', methods=['GET'])
|
||||
@token_required
|
||||
def export_cases_csv(current_user_id):
|
||||
conn = get_db_connection()
|
||||
query = """
|
||||
SELECT id, platform, violator_url, violator_article, my_article, comment, status, created_at
|
||||
FROM cases
|
||||
WHERE user_id = %s
|
||||
"""
|
||||
df = pd.read_sql(query, conn, params=(current_user_id,))
|
||||
release_db_connection(conn)
|
||||
|
||||
output = io.BytesIO()
|
||||
df.to_csv(output, index=False, encoding='utf-8-sig')
|
||||
output.seek(0)
|
||||
|
||||
return send_file(
|
||||
output,
|
||||
mimetype='text/csv',
|
||||
as_attachment=True,
|
||||
download_name=f'cases_export_{current_user_id}.csv'
|
||||
)
|
||||
|
||||
@reports_blueprint.route('/reports/case/<int:case_id>/pdf', methods=['GET'])
|
||||
@token_required
|
||||
def export_case_pdf(current_user_id, case_id):
|
||||
conn = get_db_connection()
|
||||
cur = conn.cursor()
|
||||
cur.execute("""
|
||||
SELECT platform, violator_url, violator_article, my_article, comment, status, created_at
|
||||
FROM cases
|
||||
WHERE id = %s AND user_id = %s
|
||||
""", (case_id, current_user_id))
|
||||
row = cur.fetchone()
|
||||
release_db_connection(conn)
|
||||
|
||||
if not row:
|
||||
return jsonify({"error": "Case not found"}), 404
|
||||
|
||||
platform, v_url, v_art, my_art, comment, status, created_at = row
|
||||
|
||||
buffer = io.BytesIO()
|
||||
doc = SimpleDocTemplate(buffer, pagesize=letter)
|
||||
styles = getSampleStyleSheet()
|
||||
elements = []
|
||||
|
||||
# Title
|
||||
elements.append(Paragraph(f"Официальная претензия #{case_id}", styles['Title']))
|
||||
elements.append(Spacer(1, 12))
|
||||
|
||||
# Info table
|
||||
data = [
|
||||
["Маркетплейс", platform.upper()],
|
||||
["Дата создания", created_at.strftime('%Y-%m-%d %H:%M') if created_at else "-"],
|
||||
["Артикул нарушителя", v_art],
|
||||
["Ссылка на товар", Paragraph(v_url, styles['Normal'])],
|
||||
["Ваш артикул", my_art or "-"],
|
||||
["Текущий статус", status.upper()]
|
||||
]
|
||||
|
||||
t = Table(data, colWidths=[150, 350])
|
||||
t.setStyle(TableStyle([
|
||||
('BACKGROUND', (0, 0), (0, -1), colors.lightgrey),
|
||||
('GRID', (0, 0), (-1, -1), 1, colors.black),
|
||||
('PADDING', (0, 0), (-1, -1), 6),
|
||||
]))
|
||||
elements.append(t)
|
||||
elements.append(Spacer(1, 24))
|
||||
|
||||
# Description
|
||||
elements.append(Paragraph("Описание нарушения:", styles['Heading2']))
|
||||
elements.append(Paragraph(comment or "Комментарий отсутствует", styles['Normal']))
|
||||
|
||||
doc.build(elements)
|
||||
buffer.seek(0)
|
||||
|
||||
return send_file(
|
||||
buffer,
|
||||
mimetype='application/pdf',
|
||||
as_attachment=True,
|
||||
download_name=f'complaint_{case_id}.pdf'
|
||||
)
|
||||
Reference in New Issue
Block a user