// Package message defines the App message tab inbox domain owned by activity-service. package message const ( // SectionUser is sourced from Tencent IM SDK and never persisted by this service. SectionUser = "user" // SectionSystem stores account, wallet, room and application notifications. SectionSystem = "system" // SectionActivity stores activity, reward and operational campaign notifications. SectionActivity = "activity" SourceTencentIMSDK = "tencent_im_sdk" SourceBackend = "backend" StatusVisible = "visible" StatusRecalled = "recalled" StatusHidden = "hidden" StatusExpired = "expired" FanoutStatusPending = "pending" FanoutStatusRunning = "running" FanoutStatusRetrying = "retrying" FanoutStatusFailed = "failed" FanoutStatusComplete = "completed" TargetScopeSingleUser = "single_user" TargetScopeUserIDs = "user_ids" TargetScopeRegion = "region" TargetScopeCountry = "country" TargetScopeAllActiveUsers = "all_active_users" TargetScopeAllRegistered = "all_registered_users" ) // TabSection is the message tab summary returned to App clients. type TabSection struct { Section string Title string UnreadCount int64 Source string } // RewardItem 是活动奖励的客户端展示快照,发奖后不再依赖可变的资源目录。 type RewardItem struct { RewardType string `json:"reward_type"` Name string `json:"name,omitempty"` ImageURL string `json:"image_url,omitempty"` Quantity int64 `json:"quantity,omitempty"` DurationDays int64 `json:"duration_days,omitempty"` } // InboxActionAPI 只描述 gateway 同源 API;headers 和绝对 URL 不进入消息事实。 type InboxActionAPI struct { Method string `json:"method"` Path string `json:"path"` Query map[string]any `json:"query,omitempty"` Body any `json:"body,omitempty"` } // InboxAction 是 system/activity 卡片的通用操作按钮快照,展示文案完全由生产者提供。 type InboxAction struct { Action string `json:"action"` Label string `json:"label"` Style string `json:"style"` API InboxActionAPI `json:"api"` } // InboxMessage is the user-visible snapshot stored in user_inbox_messages. type InboxMessage struct { AppCode string MessageID string UserID int64 MessageType string Producer string ProducerEventID string ProducerEventType string AggregateType string AggregateID string TemplateID string TemplateVersion string Title string Summary string Body string IconURL string ImageURL string // ImageURLs 是一张通知卡片内的有序图片列表;ImageURL 保留首图兼容旧客户端。 ImageURLs []string // RewardItems 从 metadata_json 还原为强类型响应;历史消息没有该字段时保持空列表。 RewardItems []RewardItem // Actions 与图片/奖励一样存入 metadata_json,避免为展示协议扩表。 Actions []InboxAction ActionType string ActionParam string Priority int32 Status string ReadAtMS int64 DeletedAtMS int64 SentAtMS int64 ExpireAtMS int64 MetadataJSON string CreatedAtMS int64 UpdatedAtMS int64 } // Read reports whether the user has marked the message as read. func (m InboxMessage) Read() bool { return m.ReadAtMS > 0 } // MessageTemplate is an active server-owned content template snapshot source. type MessageTemplate struct { AppCode string TemplateID string TemplateVersion string MessageType string Locale string Title string Summary string Body string IconURL string ImageURL string ActionType string ActionParam string Status string CreatedBy string CreatedAtMS int64 UpdatedAtMS int64 } // ListQuery is the stable cursor query for system/activity inbox lists. type ListQuery struct { UserID int64 Section string Limit int CursorSentAtMS int64 CursorMessageID string NowMS int64 } // CreateInput carries a validated single-user inbox creation command. type CreateInput struct { TargetUserID int64 Producer string ProducerEventID string ProducerEventType string MessageType string AggregateType string AggregateID string TemplateID string TemplateVersion string Title string Summary string Body string IconURL string ImageURL string // ImageURLs 会由 service 写入受控 metadata 快照,MySQL 继续使用现有 JSON 列持久化。 ImageURLs []string // RewardItems 与发奖事实一起固化,防止资源改名、换图或改时长后历史消息漂移。 RewardItems []RewardItem // Actions 最多两个,owner service 会校验按钮文案、样式和同源 API。 Actions []InboxAction ActionType string ActionParam string Priority int32 SentAtMS int64 ExpireAtMS int64 MetadataJSON string } // FanoutJob stores a background fanout command without executing user selection in the request path. type FanoutJob struct { AppCode string JobID string CommandID string MessageType string TargetScope string TargetFilterJSON string TemplateSnapshotJSON string Status string AttemptCount int32 CursorUserID int64 TotalCount int64 SuccessCount int64 FailureCount int64 BatchSize int32 NextRunAtMS int64 LockedBy string LockedUntilMS int64 ErrorMessage string CreatedBy string CreatedAtMS int64 UpdatedAtMS int64 } // CreateFanoutInput is the validated admin or producer command for fanout job creation. type CreateFanoutInput struct { CommandID string MessageType string TargetScope string TargetFilterJSON string TemplateSnapshotJSON string BatchSize int32 CreatedBy string }