145 lines
3.8 KiB
Python
145 lines
3.8 KiB
Python
"""监测优化 Pydantic v2 Schemas"""
|
|
from __future__ import annotations
|
|
|
|
from datetime import datetime
|
|
from typing import Any
|
|
|
|
from pydantic import BaseModel, Field
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# PublishRecord
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class PublishRecordCreate(BaseModel):
|
|
content_title: str = Field(..., max_length=200)
|
|
content_id: str | None = None
|
|
platform: str = Field(..., max_length=50)
|
|
published_url: str | None = None
|
|
status: str = Field(default="published", max_length=20)
|
|
published_at: datetime | None = None
|
|
|
|
|
|
class PublishRecordResponse(BaseModel):
|
|
id: str
|
|
organization_id: str
|
|
content_title: str
|
|
content_id: str | None
|
|
platform: str
|
|
published_url: str | None
|
|
status: str
|
|
published_at: datetime | None
|
|
created_at: datetime
|
|
|
|
model_config = {"from_attributes": True}
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# ContentMetrics
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class MetricsUpdateRequest(BaseModel):
|
|
views: int = Field(default=0, ge=0)
|
|
likes: int = Field(default=0, ge=0)
|
|
comments: int = Field(default=0, ge=0)
|
|
shares: int = Field(default=0, ge=0)
|
|
bookmarks: int = Field(default=0, ge=0)
|
|
ai_citation_count: int = Field(default=0, ge=0)
|
|
search_impressions: int = Field(default=0, ge=0)
|
|
search_clicks: int = Field(default=0, ge=0)
|
|
avg_read_duration: float = Field(default=0.0, ge=0.0)
|
|
read_completion_rate: float = Field(default=0.0, ge=0.0, le=1.0)
|
|
|
|
|
|
class MetricsResponse(BaseModel):
|
|
id: str
|
|
publish_record_id: str
|
|
recorded_at: datetime
|
|
views: int
|
|
likes: int
|
|
comments: int
|
|
shares: int
|
|
bookmarks: int
|
|
ai_citation_count: int
|
|
search_impressions: int
|
|
search_clicks: int
|
|
avg_read_duration: float
|
|
read_completion_rate: float
|
|
|
|
model_config = {"from_attributes": True}
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# Overview
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class OverviewStatsResponse(BaseModel):
|
|
total_published: int
|
|
total_views: int
|
|
total_interactions: int
|
|
total_ai_citations: int
|
|
avg_engagement_rate: float
|
|
platform_distribution: dict[str, int]
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# Content Performance
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class ContentPerformanceResponse(BaseModel):
|
|
id: str
|
|
content_title: str
|
|
platform: str
|
|
published_url: str | None
|
|
status: str
|
|
published_at: str | None
|
|
latest_metrics: dict[str, Any] | None
|
|
metrics_history: list[dict[str, Any]]
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# Insight
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class InsightResponse(BaseModel):
|
|
id: str
|
|
organization_id: str
|
|
content_id: str | None
|
|
insight_type: str
|
|
title: str
|
|
description: str
|
|
recommendation: str
|
|
severity: str
|
|
applied: bool
|
|
created_at: datetime
|
|
|
|
model_config = {"from_attributes": True}
|
|
|
|
|
|
# ------------------------------------------------------------------ #
|
|
# Top Content
|
|
# ------------------------------------------------------------------ #
|
|
|
|
class TopContentItem(BaseModel):
|
|
publish_record_id: str
|
|
content_title: str
|
|
platform: str
|
|
published_url: str | None
|
|
views: int
|
|
likes: int
|
|
comments: int
|
|
shares: int
|
|
bookmarks: int
|
|
ai_citation_count: int
|
|
search_impressions: int
|
|
search_clicks: int
|
|
avg_read_duration: float
|
|
read_completion_rate: float
|
|
recorded_at: str | None
|
|
|
|
|
|
class TopContentResponse(BaseModel):
|
|
items: list[TopContentItem]
|
|
sort_by: str
|
|
total: int
|