批量导出Excel表格以及压缩图片
This commit is contained in:
commit
60c8855993
@ -3327,6 +3327,9 @@ type WorkInfoResp struct {
|
|||||||
ArtistPhone string `protobuf:"bytes,4,opt,name=artistPhone,proto3" json:"artistPhone"`
|
ArtistPhone string `protobuf:"bytes,4,opt,name=artistPhone,proto3" json:"artistPhone"`
|
||||||
ArtistPhoneAreaCode string `protobuf:"bytes,5,opt,name=artistPhoneAreaCode,proto3" json:"artistPhoneAreaCode"`
|
ArtistPhoneAreaCode string `protobuf:"bytes,5,opt,name=artistPhoneAreaCode,proto3" json:"artistPhoneAreaCode"`
|
||||||
WorkCategory uint32 `protobuf:"varint,6,opt,name=workCategory,proto3" json:"workCategory"`
|
WorkCategory uint32 `protobuf:"varint,6,opt,name=workCategory,proto3" json:"workCategory"`
|
||||||
|
PlatformInfoData []*PlatformInfo `protobuf:"bytes,7,rep,name=platformInfoData,proto3" json:"platformInfoData"`
|
||||||
|
Title string `protobuf:"bytes,8,opt,name=title,proto3" json:"title"`
|
||||||
|
PublishStatus PublishStatusENUM `protobuf:"varint,9,opt,name=publishStatus,proto3,enum=Cast.PublishStatusENUM" json:"publishStatus"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@ -3403,6 +3406,27 @@ func (x *WorkInfoResp) GetWorkCategory() uint32 {
|
|||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *WorkInfoResp) GetPlatformInfoData() []*PlatformInfo {
|
||||||
|
if x != nil {
|
||||||
|
return x.PlatformInfoData
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *WorkInfoResp) GetTitle() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.Title
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *WorkInfoResp) GetPublishStatus() PublishStatusENUM {
|
||||||
|
if x != nil {
|
||||||
|
return x.PublishStatus
|
||||||
|
}
|
||||||
|
return PublishStatusENUM_PublishMediaStatus_NO
|
||||||
|
}
|
||||||
|
|
||||||
// 发布成功的作品列表请求
|
// 发布成功的作品列表请求
|
||||||
type WorkListPublishedReq struct {
|
type WorkListPublishedReq struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
@ -3765,7 +3789,7 @@ type PlatformInfo struct {
|
|||||||
PublishType uint32 `protobuf:"varint,4,opt,name=publishType,proto3" json:"publishType"`
|
PublishType uint32 `protobuf:"varint,4,opt,name=publishType,proto3" json:"publishType"`
|
||||||
PublishResp string `protobuf:"bytes,5,opt,name=publishResp,proto3" json:"publishResp"`
|
PublishResp string `protobuf:"bytes,5,opt,name=publishResp,proto3" json:"publishResp"`
|
||||||
PublishMediaId string `protobuf:"bytes,6,opt,name=publishMediaId,proto3" json:"publishMediaId"`
|
PublishMediaId string `protobuf:"bytes,6,opt,name=publishMediaId,proto3" json:"publishMediaId"`
|
||||||
PublishStatus PublishStatusENUM `protobuf:"varint,7,opt,name=publishStatus,proto3,enum=Cast.PublishStatusENUM" json:"publishStatus"`
|
PublishMediaStatus PublishStatusENUM `protobuf:"varint,7,opt,name=publishMediaStatus,proto3,enum=Cast.PublishStatusENUM" json:"publishMediaStatus"`
|
||||||
Remark string `protobuf:"bytes,8,opt,name=remark,proto3" json:"remark"`
|
Remark string `protobuf:"bytes,8,opt,name=remark,proto3" json:"remark"`
|
||||||
PlatformUuid string `protobuf:"bytes,9,opt,name=platformUuid,proto3" json:"platformUuid"`
|
PlatformUuid string `protobuf:"bytes,9,opt,name=platformUuid,proto3" json:"platformUuid"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
@ -3844,9 +3868,9 @@ func (x *PlatformInfo) GetPublishMediaId() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *PlatformInfo) GetPublishStatus() PublishStatusENUM {
|
func (x *PlatformInfo) GetPublishMediaStatus() PublishStatusENUM {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.PublishStatus
|
return x.PublishMediaStatus
|
||||||
}
|
}
|
||||||
return PublishStatusENUM_PublishMediaStatus_NO
|
return PublishStatusENUM_PublishMediaStatus_NO
|
||||||
}
|
}
|
||||||
@ -12947,6 +12971,7 @@ type UpsertTaskListReq struct {
|
|||||||
Status uint32 `protobuf:"varint,4,opt,name=status,proto3" json:"status"` // 状态:1-待处理 2-处理中 3-处理完成
|
Status uint32 `protobuf:"varint,4,opt,name=status,proto3" json:"status"` // 状态:1-待处理 2-处理中 3-处理完成
|
||||||
OperatorID string `protobuf:"bytes,5,opt,name=operatorID,proto3" json:"operatorID"` // 操作人ID
|
OperatorID string `protobuf:"bytes,5,opt,name=operatorID,proto3" json:"operatorID"` // 操作人ID
|
||||||
OperatorName string `protobuf:"bytes,6,opt,name=operatorName,proto3" json:"operatorName"` // 操作人名称
|
OperatorName string `protobuf:"bytes,6,opt,name=operatorName,proto3" json:"operatorName"` // 操作人名称
|
||||||
|
ExtraData string `protobuf:"bytes,7,opt,name=extraData,proto3" json:"extraData"` // 扩展信息
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@ -13023,6 +13048,13 @@ func (x *UpsertTaskListReq) GetOperatorName() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *UpsertTaskListReq) GetExtraData() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.ExtraData
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
// 新增或更新任务响应
|
// 新增或更新任务响应
|
||||||
type UpsertTaskListResp struct {
|
type UpsertTaskListResp struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
@ -13132,6 +13164,7 @@ type TaskListInfo struct {
|
|||||||
OperatorName string `protobuf:"bytes,6,opt,name=operatorName,proto3" json:"operatorName"` // 操作人名称
|
OperatorName string `protobuf:"bytes,6,opt,name=operatorName,proto3" json:"operatorName"` // 操作人名称
|
||||||
CreatedAt string `protobuf:"bytes,7,opt,name=createdAt,proto3" json:"createdAt"` // 创建时间
|
CreatedAt string `protobuf:"bytes,7,opt,name=createdAt,proto3" json:"createdAt"` // 创建时间
|
||||||
UpdatedAt string `protobuf:"bytes,8,opt,name=updatedAt,proto3" json:"updatedAt"` // 更新时间
|
UpdatedAt string `protobuf:"bytes,8,opt,name=updatedAt,proto3" json:"updatedAt"` // 更新时间
|
||||||
|
ExtraData string `protobuf:"bytes,9,opt,name=extraData,proto3" json:"extraData"` // 扩展信息
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@ -13222,6 +13255,13 @@ func (x *TaskListInfo) GetUpdatedAt() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *TaskListInfo) GetExtraData() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.ExtraData
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
// 获取任务详情响应
|
// 获取任务详情响应
|
||||||
type GetTaskListResp struct {
|
type GetTaskListResp struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
@ -17263,7 +17303,7 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"DelWorkReq\x12\x1a\n" +
|
"DelWorkReq\x12\x1a\n" +
|
||||||
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\")\n" +
|
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\")\n" +
|
||||||
"\vWorkInfoReq\x12\x1a\n" +
|
"\vWorkInfoReq\x12\x1a\n" +
|
||||||
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\"\xe6\x01\n" +
|
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\"\xfb\x02\n" +
|
||||||
"\fWorkInfoResp\x12\x1e\n" +
|
"\fWorkInfoResp\x12\x1e\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"workStatus\x18\x01 \x01(\rR\n" +
|
"workStatus\x18\x01 \x01(\rR\n" +
|
||||||
@ -17276,7 +17316,10 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"artistName\x12 \n" +
|
"artistName\x12 \n" +
|
||||||
"\vartistPhone\x18\x04 \x01(\tR\vartistPhone\x120\n" +
|
"\vartistPhone\x18\x04 \x01(\tR\vartistPhone\x120\n" +
|
||||||
"\x13artistPhoneAreaCode\x18\x05 \x01(\tR\x13artistPhoneAreaCode\x12\"\n" +
|
"\x13artistPhoneAreaCode\x18\x05 \x01(\tR\x13artistPhoneAreaCode\x12\"\n" +
|
||||||
"\fworkCategory\x18\x06 \x01(\rR\fworkCategory\"f\n" +
|
"\fworkCategory\x18\x06 \x01(\rR\fworkCategory\x12>\n" +
|
||||||
|
"\x10platformInfoData\x18\a \x03(\v2\x12.Cast.PlatformInfoR\x10platformInfoData\x12\x14\n" +
|
||||||
|
"\x05title\x18\b \x01(\tR\x05title\x12=\n" +
|
||||||
|
"\rpublishStatus\x18\t \x01(\x0e2\x17.Cast.PublishStatusENUMR\rpublishStatus\"f\n" +
|
||||||
"\x14WorkListPublishedReq\x12\x1e\n" +
|
"\x14WorkListPublishedReq\x12\x1e\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"artistUuid\x18\x01 \x01(\tR\n" +
|
"artistUuid\x18\x01 \x01(\tR\n" +
|
||||||
@ -17327,7 +17370,7 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"imageWorks\x18\x01 \x03(\v2\x18.Cast.UpdateWorkImageReqR\n" +
|
"imageWorks\x18\x01 \x03(\v2\x18.Cast.UpdateWorkImageReqR\n" +
|
||||||
"imageWorks\x12\"\n" +
|
"imageWorks\x12\"\n" +
|
||||||
"\fsuccessCount\x18\x02 \x01(\x05R\fsuccessCount\x12\x1c\n" +
|
"\fsuccessCount\x18\x02 \x01(\x05R\fsuccessCount\x12\x1c\n" +
|
||||||
"\tfailCount\x18\x03 \x01(\x05R\tfailCount\"\xdd\x02\n" +
|
"\tfailCount\x18\x03 \x01(\x05R\tfailCount\"\xe7\x02\n" +
|
||||||
"\fPlatformInfo\x12\x1a\n" +
|
"\fPlatformInfo\x12\x1a\n" +
|
||||||
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\x12*\n" +
|
"\bworkUuid\x18\x01 \x01(\tR\bworkUuid\x12*\n" +
|
||||||
"\x10mediaAccountUuid\x18\x02 \x01(\tR\x10mediaAccountUuid\x12\x1e\n" +
|
"\x10mediaAccountUuid\x18\x02 \x01(\tR\x10mediaAccountUuid\x12\x1e\n" +
|
||||||
@ -17336,8 +17379,8 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"platformID\x12 \n" +
|
"platformID\x12 \n" +
|
||||||
"\vpublishType\x18\x04 \x01(\rR\vpublishType\x12 \n" +
|
"\vpublishType\x18\x04 \x01(\rR\vpublishType\x12 \n" +
|
||||||
"\vpublishResp\x18\x05 \x01(\tR\vpublishResp\x12&\n" +
|
"\vpublishResp\x18\x05 \x01(\tR\vpublishResp\x12&\n" +
|
||||||
"\x0epublishMediaId\x18\x06 \x01(\tR\x0epublishMediaId\x12=\n" +
|
"\x0epublishMediaId\x18\x06 \x01(\tR\x0epublishMediaId\x12G\n" +
|
||||||
"\rpublishStatus\x18\a \x01(\x0e2\x17.Cast.PublishStatusENUMR\rpublishStatus\x12\x16\n" +
|
"\x12publishMediaStatus\x18\a \x01(\x0e2\x17.Cast.PublishStatusENUMR\x12publishMediaStatus\x12\x16\n" +
|
||||||
"\x06remark\x18\b \x01(\tR\x06remark\x12\"\n" +
|
"\x06remark\x18\b \x01(\tR\x06remark\x12\"\n" +
|
||||||
"\fplatformUuid\x18\t \x01(\tR\fplatformUuid\"[\n" +
|
"\fplatformUuid\x18\t \x01(\tR\fplatformUuid\"[\n" +
|
||||||
"\x19UpdateWorkPlatformInfoReq\x12>\n" +
|
"\x19UpdateWorkPlatformInfoReq\x12>\n" +
|
||||||
@ -18421,7 +18464,7 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"\tupdatedAt\x18\x14 \x01(\x05R\tupdatedAt\"`\n" +
|
"\tupdatedAt\x18\x14 \x01(\x05R\tupdatedAt\"`\n" +
|
||||||
"\x18ListWorkMetricsDailyResp\x12.\n" +
|
"\x18ListWorkMetricsDailyResp\x12.\n" +
|
||||||
"\x04data\x18\x01 \x03(\v2\x1a.Cast.WorkMetricsDailyInfoR\x04data\x12\x14\n" +
|
"\x04data\x18\x01 \x03(\v2\x1a.Cast.WorkMetricsDailyInfoR\x04data\x12\x14\n" +
|
||||||
"\x05count\x18\x02 \x01(\x03R\x05count\"\xad\x01\n" +
|
"\x05count\x18\x02 \x01(\x03R\x05count\"\xcb\x01\n" +
|
||||||
"\x11UpsertTaskListReq\x12\x12\n" +
|
"\x11UpsertTaskListReq\x12\x12\n" +
|
||||||
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x16\n" +
|
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x16\n" +
|
||||||
"\x06action\x18\x02 \x01(\tR\x06action\x12\x10\n" +
|
"\x06action\x18\x02 \x01(\tR\x06action\x12\x10\n" +
|
||||||
@ -18430,12 +18473,13 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"\n" +
|
"\n" +
|
||||||
"operatorID\x18\x05 \x01(\tR\n" +
|
"operatorID\x18\x05 \x01(\tR\n" +
|
||||||
"operatorID\x12\"\n" +
|
"operatorID\x12\"\n" +
|
||||||
"\foperatorName\x18\x06 \x01(\tR\foperatorName\":\n" +
|
"\foperatorName\x18\x06 \x01(\tR\foperatorName\x12\x1c\n" +
|
||||||
|
"\textraData\x18\a \x01(\tR\textraData\":\n" +
|
||||||
"\x12UpsertTaskListResp\x12\x12\n" +
|
"\x12UpsertTaskListResp\x12\x12\n" +
|
||||||
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x10\n" +
|
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x10\n" +
|
||||||
"\x03msg\x18\x02 \x01(\tR\x03msg\"$\n" +
|
"\x03msg\x18\x02 \x01(\tR\x03msg\"$\n" +
|
||||||
"\x0eGetTaskListReq\x12\x12\n" +
|
"\x0eGetTaskListReq\x12\x12\n" +
|
||||||
"\x04uuid\x18\x01 \x01(\tR\x04uuid\"\xe4\x01\n" +
|
"\x04uuid\x18\x01 \x01(\tR\x04uuid\"\x82\x02\n" +
|
||||||
"\fTaskListInfo\x12\x12\n" +
|
"\fTaskListInfo\x12\x12\n" +
|
||||||
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x16\n" +
|
"\x04uuid\x18\x01 \x01(\tR\x04uuid\x12\x16\n" +
|
||||||
"\x06action\x18\x02 \x01(\tR\x06action\x12\x10\n" +
|
"\x06action\x18\x02 \x01(\tR\x06action\x12\x10\n" +
|
||||||
@ -18446,7 +18490,8 @@ const file_pb_fiee_cast_proto_rawDesc = "" +
|
|||||||
"operatorID\x12\"\n" +
|
"operatorID\x12\"\n" +
|
||||||
"\foperatorName\x18\x06 \x01(\tR\foperatorName\x12\x1c\n" +
|
"\foperatorName\x18\x06 \x01(\tR\foperatorName\x12\x1c\n" +
|
||||||
"\tcreatedAt\x18\a \x01(\tR\tcreatedAt\x12\x1c\n" +
|
"\tcreatedAt\x18\a \x01(\tR\tcreatedAt\x12\x1c\n" +
|
||||||
"\tupdatedAt\x18\b \x01(\tR\tupdatedAt\"K\n" +
|
"\tupdatedAt\x18\b \x01(\tR\tupdatedAt\x12\x1c\n" +
|
||||||
|
"\textraData\x18\t \x01(\tR\textraData\"K\n" +
|
||||||
"\x0fGetTaskListResp\x12&\n" +
|
"\x0fGetTaskListResp\x12&\n" +
|
||||||
"\x04data\x18\x01 \x01(\v2\x12.Cast.TaskListInfoR\x04data\x12\x10\n" +
|
"\x04data\x18\x01 \x01(\v2\x12.Cast.TaskListInfoR\x04data\x12\x10\n" +
|
||||||
"\x03msg\x18\x02 \x01(\tR\x03msg\"\x91\x01\n" +
|
"\x03msg\x18\x02 \x01(\tR\x03msg\"\x91\x01\n" +
|
||||||
@ -19108,268 +19153,270 @@ var file_pb_fiee_cast_proto_depIdxs = []int32{
|
|||||||
200, // 34: Cast.MediaAccountsResp.data:type_name -> Cast.MediaAccountsResp.Info
|
200, // 34: Cast.MediaAccountsResp.data:type_name -> Cast.MediaAccountsResp.Info
|
||||||
201, // 35: Cast.MediaWorksResp.data:type_name -> Cast.MediaWorksResp.Info
|
201, // 35: Cast.MediaWorksResp.data:type_name -> Cast.MediaWorksResp.Info
|
||||||
202, // 36: Cast.PublishResp.data:type_name -> Cast.PublishResp.Info
|
202, // 36: Cast.PublishResp.data:type_name -> Cast.PublishResp.Info
|
||||||
203, // 37: Cast.WorkListPublishedResp.data:type_name -> Cast.WorkListPublishedResp.Info
|
48, // 37: Cast.WorkInfoResp.platformInfoData:type_name -> Cast.PlatformInfo
|
||||||
16, // 38: Cast.ImportWorkBatchReq.imageWorks:type_name -> Cast.UpdateWorkImageReq
|
4, // 38: Cast.WorkInfoResp.publishStatus:type_name -> Cast.PublishStatusENUM
|
||||||
16, // 39: Cast.ImportWorkBatchResp.imageWorks:type_name -> Cast.UpdateWorkImageReq
|
203, // 39: Cast.WorkListPublishedResp.data:type_name -> Cast.WorkListPublishedResp.Info
|
||||||
4, // 40: Cast.PlatformInfo.publishStatus:type_name -> Cast.PublishStatusENUM
|
16, // 40: Cast.ImportWorkBatchReq.imageWorks:type_name -> Cast.UpdateWorkImageReq
|
||||||
48, // 41: Cast.UpdateWorkPlatformInfoReq.PlatformInfoData:type_name -> Cast.PlatformInfo
|
16, // 41: Cast.ImportWorkBatchResp.imageWorks:type_name -> Cast.UpdateWorkImageReq
|
||||||
0, // 42: Cast.UpdateWorkPublishLogReq.platformID:type_name -> Cast.PlatformIDENUM
|
4, // 42: Cast.PlatformInfo.publishMediaStatus:type_name -> Cast.PublishStatusENUM
|
||||||
204, // 43: Cast.RefreshWorkListResp.Data:type_name -> Cast.RefreshWorkListResp.Info
|
48, // 43: Cast.UpdateWorkPlatformInfoReq.PlatformInfoData:type_name -> Cast.PlatformInfo
|
||||||
0, // 44: Cast.OAuthCodeToTokenReq.platformID:type_name -> Cast.PlatformIDENUM
|
0, // 44: Cast.UpdateWorkPublishLogReq.platformID:type_name -> Cast.PlatformIDENUM
|
||||||
206, // 45: Cast.UpdateOAuthReq.Data:type_name -> Cast.UpdateOAuthReq.Info
|
204, // 45: Cast.RefreshWorkListResp.Data:type_name -> Cast.RefreshWorkListResp.Info
|
||||||
0, // 46: Cast.RefreshTokenReq.platformID:type_name -> Cast.PlatformIDENUM
|
0, // 46: Cast.OAuthCodeToTokenReq.platformID:type_name -> Cast.PlatformIDENUM
|
||||||
73, // 47: Cast.ListVideoScriptsResp.data:type_name -> Cast.VideoScriptInfo
|
206, // 47: Cast.UpdateOAuthReq.Data:type_name -> Cast.UpdateOAuthReq.Info
|
||||||
73, // 48: Cast.UpdateVideoScriptBatchReq.data:type_name -> Cast.VideoScriptInfo
|
0, // 48: Cast.RefreshTokenReq.platformID:type_name -> Cast.PlatformIDENUM
|
||||||
73, // 49: Cast.UpdateVideoScriptBatchResp.data:type_name -> Cast.VideoScriptInfo
|
73, // 49: Cast.ListVideoScriptsResp.data:type_name -> Cast.VideoScriptInfo
|
||||||
2, // 50: Cast.UpdateScriptStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
73, // 50: Cast.UpdateVideoScriptBatchReq.data:type_name -> Cast.VideoScriptInfo
|
||||||
6, // 51: Cast.UpdatePromptReq.category:type_name -> Cast.CategoryENUM
|
73, // 51: Cast.UpdateVideoScriptBatchResp.data:type_name -> Cast.VideoScriptInfo
|
||||||
6, // 52: Cast.GetPromptResp.category:type_name -> Cast.CategoryENUM
|
2, // 52: Cast.UpdateScriptStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
||||||
6, // 53: Cast.ListPromptsReq.category:type_name -> Cast.CategoryENUM
|
6, // 53: Cast.UpdatePromptReq.category:type_name -> Cast.CategoryENUM
|
||||||
6, // 54: Cast.PromptInfo.category:type_name -> Cast.CategoryENUM
|
6, // 54: Cast.GetPromptResp.category:type_name -> Cast.CategoryENUM
|
||||||
87, // 55: Cast.ListPromptsResp.data:type_name -> Cast.PromptInfo
|
6, // 55: Cast.ListPromptsReq.category:type_name -> Cast.CategoryENUM
|
||||||
87, // 56: Cast.UpdatePromptBatchReq.data:type_name -> Cast.PromptInfo
|
6, // 56: Cast.PromptInfo.category:type_name -> Cast.CategoryENUM
|
||||||
87, // 57: Cast.UpdatePromptBatchResp.data:type_name -> Cast.PromptInfo
|
87, // 57: Cast.ListPromptsResp.data:type_name -> Cast.PromptInfo
|
||||||
91, // 58: Cast.UpdateArtistReq.artistInfo:type_name -> Cast.ArtistInfo
|
87, // 58: Cast.UpdatePromptBatchReq.data:type_name -> Cast.PromptInfo
|
||||||
91, // 59: Cast.GetArtistResp.artistInfo:type_name -> Cast.ArtistInfo
|
87, // 59: Cast.UpdatePromptBatchResp.data:type_name -> Cast.PromptInfo
|
||||||
2, // 60: Cast.UpdateWorkAnalysisStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
91, // 60: Cast.UpdateArtistReq.artistInfo:type_name -> Cast.ArtistInfo
|
||||||
101, // 61: Cast.GetWorkAnalysisResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
91, // 61: Cast.GetArtistResp.artistInfo:type_name -> Cast.ArtistInfo
|
||||||
102, // 62: Cast.GetWorkAnalysisResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
2, // 62: Cast.UpdateWorkAnalysisStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
||||||
103, // 63: Cast.GetWorkAnalysisResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
101, // 63: Cast.GetWorkAnalysisResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
||||||
104, // 64: Cast.GetWorkAnalysisResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
102, // 64: Cast.GetWorkAnalysisResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
||||||
105, // 65: Cast.GetWorkAnalysisResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
103, // 65: Cast.GetWorkAnalysisResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
||||||
106, // 66: Cast.GetWorkAnalysisResp.topCitiesSeries:type_name -> Cast.WorkAnalysisTopCities
|
104, // 66: Cast.GetWorkAnalysisResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
||||||
107, // 67: Cast.GetWorkAnalysisResp.mostActiveDaySeries:type_name -> Cast.WorkAnalysisMostActiveDay
|
105, // 67: Cast.GetWorkAnalysisResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
||||||
108, // 68: Cast.GetWorkAnalysisResp.bestPostTimeSeries:type_name -> Cast.WorkAnalysisBestPostTime
|
106, // 68: Cast.GetWorkAnalysisResp.topCitiesSeries:type_name -> Cast.WorkAnalysisTopCities
|
||||||
100, // 69: Cast.GetWorkAnalysisDetailResp.WorkAnalysisLogData:type_name -> Cast.WorkAnalysisLogInfo
|
107, // 69: Cast.GetWorkAnalysisResp.mostActiveDaySeries:type_name -> Cast.WorkAnalysisMostActiveDay
|
||||||
101, // 70: Cast.GetWorkAnalysisDetailResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
108, // 70: Cast.GetWorkAnalysisResp.bestPostTimeSeries:type_name -> Cast.WorkAnalysisBestPostTime
|
||||||
102, // 71: Cast.GetWorkAnalysisDetailResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
100, // 71: Cast.GetWorkAnalysisDetailResp.WorkAnalysisLogData:type_name -> Cast.WorkAnalysisLogInfo
|
||||||
103, // 72: Cast.GetWorkAnalysisDetailResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
101, // 72: Cast.GetWorkAnalysisDetailResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
||||||
104, // 73: Cast.GetWorkAnalysisDetailResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
102, // 73: Cast.GetWorkAnalysisDetailResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
||||||
105, // 74: Cast.GetWorkAnalysisDetailResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
103, // 74: Cast.GetWorkAnalysisDetailResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
||||||
106, // 75: Cast.GetWorkAnalysisDetailResp.topCitiesSeries:type_name -> Cast.WorkAnalysisTopCities
|
104, // 75: Cast.GetWorkAnalysisDetailResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
||||||
107, // 76: Cast.GetWorkAnalysisDetailResp.mostActiveDaySeries:type_name -> Cast.WorkAnalysisMostActiveDay
|
105, // 76: Cast.GetWorkAnalysisDetailResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
||||||
108, // 77: Cast.GetWorkAnalysisDetailResp.bestPostTimeSeries:type_name -> Cast.WorkAnalysisBestPostTime
|
106, // 77: Cast.GetWorkAnalysisDetailResp.topCitiesSeries:type_name -> Cast.WorkAnalysisTopCities
|
||||||
109, // 78: Cast.GetWorkAnalysisDetailResp.extra:type_name -> Cast.WorkAnalysisExtra
|
107, // 78: Cast.GetWorkAnalysisDetailResp.mostActiveDaySeries:type_name -> Cast.WorkAnalysisMostActiveDay
|
||||||
115, // 79: Cast.ListWorkAnalysisResp.data:type_name -> Cast.WorkAnalysisInfo
|
108, // 79: Cast.GetWorkAnalysisDetailResp.bestPostTimeSeries:type_name -> Cast.WorkAnalysisBestPostTime
|
||||||
119, // 80: Cast.ArtistDataListResp.data:type_name -> Cast.ArtistDataRespItem
|
109, // 80: Cast.GetWorkAnalysisDetailResp.extra:type_name -> Cast.WorkAnalysisExtra
|
||||||
122, // 81: Cast.MediaDataListResp.data:type_name -> Cast.MediaDataListItem
|
115, // 81: Cast.ListWorkAnalysisResp.data:type_name -> Cast.WorkAnalysisInfo
|
||||||
101, // 82: Cast.ArtistMetricsSeriesResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
119, // 82: Cast.ArtistDataListResp.data:type_name -> Cast.ArtistDataRespItem
|
||||||
102, // 83: Cast.ArtistMetricsSeriesResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
122, // 83: Cast.MediaDataListResp.data:type_name -> Cast.MediaDataListItem
|
||||||
103, // 84: Cast.ArtistMetricsSeriesResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
101, // 84: Cast.ArtistMetricsSeriesResp.fansSeries:type_name -> Cast.WorkAnalysisFansSeries
|
||||||
104, // 85: Cast.ArtistMetricsSeriesResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
102, // 85: Cast.ArtistMetricsSeriesResp.viewsSeries:type_name -> Cast.WorkAnalysisViewsSeries
|
||||||
105, // 86: Cast.ArtistMetricsSeriesResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
103, // 86: Cast.ArtistMetricsSeriesResp.likesSeries:type_name -> Cast.WorkAnalysisLikesSeries
|
||||||
108, // 87: Cast.ArtistMetricsSeriesResp.bestPostTime:type_name -> Cast.WorkAnalysisBestPostTime
|
104, // 87: Cast.ArtistMetricsSeriesResp.commentsSeries:type_name -> Cast.WorkAnalysisCommentsSeries
|
||||||
107, // 88: Cast.ArtistMetricsSeriesResp.mostActiveDay:type_name -> Cast.WorkAnalysisMostActiveDay
|
105, // 88: Cast.ArtistMetricsSeriesResp.sharesSeries:type_name -> Cast.WorkAnalysisSharesSeries
|
||||||
129, // 89: Cast.ArtistMetricsDailyWindowResp.fans:type_name -> Cast.SimplePoint
|
108, // 89: Cast.ArtistMetricsSeriesResp.bestPostTime:type_name -> Cast.WorkAnalysisBestPostTime
|
||||||
129, // 90: Cast.ArtistMetricsDailyWindowResp.views:type_name -> Cast.SimplePoint
|
107, // 90: Cast.ArtistMetricsSeriesResp.mostActiveDay:type_name -> Cast.WorkAnalysisMostActiveDay
|
||||||
129, // 91: Cast.ArtistMetricsDailyWindowResp.likes:type_name -> Cast.SimplePoint
|
129, // 91: Cast.ArtistMetricsDailyWindowResp.fans:type_name -> Cast.SimplePoint
|
||||||
129, // 92: Cast.ArtistMetricsDailyWindowResp.comments:type_name -> Cast.SimplePoint
|
129, // 92: Cast.ArtistMetricsDailyWindowResp.views:type_name -> Cast.SimplePoint
|
||||||
129, // 93: Cast.ArtistMetricsDailyWindowResp.shares:type_name -> Cast.SimplePoint
|
129, // 93: Cast.ArtistMetricsDailyWindowResp.likes:type_name -> Cast.SimplePoint
|
||||||
130, // 94: Cast.ArtistMetricsDailyWindowResp.bestPostTime:type_name -> Cast.BestPostTimePoint
|
129, // 94: Cast.ArtistMetricsDailyWindowResp.comments:type_name -> Cast.SimplePoint
|
||||||
131, // 95: Cast.ArtistMetricsDailyWindowResp.mostActiveDay:type_name -> Cast.MostActiveDayPoint
|
129, // 95: Cast.ArtistMetricsDailyWindowResp.shares:type_name -> Cast.SimplePoint
|
||||||
134, // 96: Cast.TobeConfirmedListResp.data:type_name -> Cast.TobeConfirmedItem
|
130, // 96: Cast.ArtistMetricsDailyWindowResp.bestPostTime:type_name -> Cast.BestPostTimePoint
|
||||||
137, // 97: Cast.UpsertMediaMetricsDailyBatchReq.data:type_name -> Cast.MediaMetricsDailyItem
|
131, // 97: Cast.ArtistMetricsDailyWindowResp.mostActiveDay:type_name -> Cast.MostActiveDayPoint
|
||||||
140, // 98: Cast.UpsertWorkMetricsDailyBatchReq.data:type_name -> Cast.WorkMetricsDailyItem
|
134, // 98: Cast.TobeConfirmedListResp.data:type_name -> Cast.TobeConfirmedItem
|
||||||
144, // 99: Cast.GetArtistAyrShareInfoResp.data:type_name -> Cast.ArtistAyrShareInfo
|
137, // 99: Cast.UpsertMediaMetricsDailyBatchReq.data:type_name -> Cast.MediaMetricsDailyItem
|
||||||
144, // 100: Cast.GetArtistAyrShareInfoByPlatformIDsResp.data:type_name -> Cast.ArtistAyrShareInfo
|
140, // 100: Cast.UpsertWorkMetricsDailyBatchReq.data:type_name -> Cast.WorkMetricsDailyItem
|
||||||
149, // 101: Cast.ListWorkPlatformInfoResp.data:type_name -> Cast.WorkPlatformInfo
|
144, // 101: Cast.GetArtistAyrShareInfoResp.data:type_name -> Cast.ArtistAyrShareInfo
|
||||||
152, // 102: Cast.ListMediaMetricsDailyResp.data:type_name -> Cast.MediaMetricsDailyInfo
|
144, // 102: Cast.GetArtistAyrShareInfoByPlatformIDsResp.data:type_name -> Cast.ArtistAyrShareInfo
|
||||||
155, // 103: Cast.ListWorkMetricsDailyResp.data:type_name -> Cast.WorkMetricsDailyInfo
|
149, // 103: Cast.ListWorkPlatformInfoResp.data:type_name -> Cast.WorkPlatformInfo
|
||||||
160, // 104: Cast.GetTaskListResp.data:type_name -> Cast.TaskListInfo
|
152, // 104: Cast.ListMediaMetricsDailyResp.data:type_name -> Cast.MediaMetricsDailyInfo
|
||||||
160, // 105: Cast.ListTaskListResp.data:type_name -> Cast.TaskListInfo
|
155, // 105: Cast.ListWorkMetricsDailyResp.data:type_name -> Cast.WorkMetricsDailyInfo
|
||||||
170, // 106: Cast.ListCastTagsResp.data:type_name -> Cast.CastTagInfo
|
160, // 106: Cast.GetTaskListResp.data:type_name -> Cast.TaskListInfo
|
||||||
170, // 107: Cast.UpdateCastTagBatchReq.data:type_name -> Cast.CastTagInfo
|
160, // 107: Cast.ListTaskListResp.data:type_name -> Cast.TaskListInfo
|
||||||
170, // 108: Cast.UpdateCastTagBatchResp.data:type_name -> Cast.CastTagInfo
|
170, // 108: Cast.ListCastTagsResp.data:type_name -> Cast.CastTagInfo
|
||||||
170, // 109: Cast.BatchUpdateCastTagsReq.data:type_name -> Cast.CastTagInfo
|
170, // 109: Cast.UpdateCastTagBatchReq.data:type_name -> Cast.CastTagInfo
|
||||||
2, // 110: Cast.UpdateCompetitiveReportStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
170, // 110: Cast.UpdateCastTagBatchResp.data:type_name -> Cast.CastTagInfo
|
||||||
182, // 111: Cast.GetCompetitiveReportDetailResp.reportLogData:type_name -> Cast.CompetitiveReportLogInfo
|
170, // 111: Cast.BatchUpdateCastTagsReq.data:type_name -> Cast.CastTagInfo
|
||||||
183, // 112: Cast.GetCompetitiveReportDetailResp.extra:type_name -> Cast.CompetitiveReportExtra
|
2, // 112: Cast.UpdateCompetitiveReportStatusReq.workAction:type_name -> Cast.WorkActionENUM
|
||||||
189, // 113: Cast.ListCompetitiveReportResp.data:type_name -> Cast.CompetitiveReportInfo
|
182, // 113: Cast.GetCompetitiveReportDetailResp.reportLogData:type_name -> Cast.CompetitiveReportLogInfo
|
||||||
177, // 114: Cast.ImportCompetitiveReportBatchReq.reports:type_name -> Cast.CreateCompetitiveReportReq
|
183, // 114: Cast.GetCompetitiveReportDetailResp.extra:type_name -> Cast.CompetitiveReportExtra
|
||||||
177, // 115: Cast.ImportCompetitiveReportBatchResp.reports:type_name -> Cast.CreateCompetitiveReportReq
|
189, // 115: Cast.ListCompetitiveReportResp.data:type_name -> Cast.CompetitiveReportInfo
|
||||||
195, // 116: Cast.CountCompetitiveReportByWorkUuidsResp.data:type_name -> Cast.WorkUuidCount
|
177, // 116: Cast.ImportCompetitiveReportBatchReq.reports:type_name -> Cast.CreateCompetitiveReportReq
|
||||||
198, // 117: Cast.WorkListResp.Info.PublishMediaIDs:type_name -> Cast.WorkListResp.Info.PublishMediaIDsEntry
|
177, // 117: Cast.ImportCompetitiveReportBatchResp.reports:type_name -> Cast.CreateCompetitiveReportReq
|
||||||
9, // 118: Cast.WorkDetailResp.MediaAccDataEntry.value:type_name -> Cast.MediaUserInfo
|
195, // 118: Cast.CountCompetitiveReportByWorkUuidsResp.data:type_name -> Cast.WorkUuidCount
|
||||||
205, // 119: Cast.RefreshWorkListResp.Info.PlatformInfoData:type_name -> Cast.RefreshWorkListResp.Info.PlatformInfo
|
198, // 119: Cast.WorkListResp.Info.PublishMediaIDs:type_name -> Cast.WorkListResp.Info.PublishMediaIDsEntry
|
||||||
0, // 120: Cast.RefreshWorkListResp.Info.PlatformInfo.platformID:type_name -> Cast.PlatformIDENUM
|
9, // 120: Cast.WorkDetailResp.MediaAccDataEntry.value:type_name -> Cast.MediaUserInfo
|
||||||
0, // 121: Cast.UpdateOAuthReq.Info.platformID:type_name -> Cast.PlatformIDENUM
|
205, // 121: Cast.RefreshWorkListResp.Info.PlatformInfoData:type_name -> Cast.RefreshWorkListResp.Info.PlatformInfo
|
||||||
8, // 122: Cast.Cast.MediaUserList:input_type -> Cast.MediaUserListReq
|
0, // 122: Cast.RefreshWorkListResp.Info.PlatformInfo.platformID:type_name -> Cast.PlatformIDENUM
|
||||||
11, // 123: Cast.Cast.UpdateMediaAccount:input_type -> Cast.UpdateMediaAccountReq
|
0, // 123: Cast.UpdateOAuthReq.Info.platformID:type_name -> Cast.PlatformIDENUM
|
||||||
13, // 124: Cast.Cast.UnbindManager:input_type -> Cast.UnbindManagerReq
|
8, // 124: Cast.Cast.MediaUserList:input_type -> Cast.MediaUserListReq
|
||||||
15, // 125: Cast.Cast.BindManager:input_type -> Cast.BindManagerReq
|
11, // 125: Cast.Cast.UpdateMediaAccount:input_type -> Cast.UpdateMediaAccountReq
|
||||||
16, // 126: Cast.Cast.UpdateWorkImage:input_type -> Cast.UpdateWorkImageReq
|
13, // 126: Cast.Cast.UnbindManager:input_type -> Cast.UnbindManagerReq
|
||||||
19, // 127: Cast.Cast.UpdateWorkVideo:input_type -> Cast.UpdateWorkVideoReq
|
15, // 127: Cast.Cast.BindManager:input_type -> Cast.BindManagerReq
|
||||||
21, // 128: Cast.Cast.MediaInfo:input_type -> Cast.MediaInfoReq
|
16, // 128: Cast.Cast.UpdateWorkImage:input_type -> Cast.UpdateWorkImageReq
|
||||||
23, // 129: Cast.Cast.MediaInfoByPlatform:input_type -> Cast.MediaInfoByPlatformReq
|
19, // 129: Cast.Cast.UpdateWorkVideo:input_type -> Cast.UpdateWorkVideoReq
|
||||||
25, // 130: Cast.Cast.WorkList:input_type -> Cast.WorkListReq
|
21, // 130: Cast.Cast.MediaInfo:input_type -> Cast.MediaInfoReq
|
||||||
42, // 131: Cast.Cast.WorkListPublished:input_type -> Cast.WorkListPublishedReq
|
23, // 131: Cast.Cast.MediaInfoByPlatform:input_type -> Cast.MediaInfoByPlatformReq
|
||||||
27, // 132: Cast.Cast.WorkDetail:input_type -> Cast.WorkDetailReq
|
25, // 132: Cast.Cast.WorkList:input_type -> Cast.WorkListReq
|
||||||
30, // 133: Cast.Cast.UpdateStatus:input_type -> Cast.UpdateStatusReq
|
42, // 133: Cast.Cast.WorkListPublished:input_type -> Cast.WorkListPublishedReq
|
||||||
31, // 134: Cast.Cast.MediaAccounts:input_type -> Cast.MediaAccountsReq
|
27, // 134: Cast.Cast.WorkDetail:input_type -> Cast.WorkDetailReq
|
||||||
33, // 135: Cast.Cast.MediaWorks:input_type -> Cast.MediaWorksReq
|
30, // 135: Cast.Cast.UpdateStatus:input_type -> Cast.UpdateStatusReq
|
||||||
35, // 136: Cast.Cast.Publish:input_type -> Cast.PublishReq
|
31, // 136: Cast.Cast.MediaAccounts:input_type -> Cast.MediaAccountsReq
|
||||||
37, // 137: Cast.Cast.RePublish:input_type -> Cast.RePublishReq
|
33, // 137: Cast.Cast.MediaWorks:input_type -> Cast.MediaWorksReq
|
||||||
39, // 138: Cast.Cast.DelWork:input_type -> Cast.DelWorkReq
|
35, // 138: Cast.Cast.Publish:input_type -> Cast.PublishReq
|
||||||
40, // 139: Cast.Cast.WorkInfo:input_type -> Cast.WorkInfoReq
|
37, // 139: Cast.Cast.RePublish:input_type -> Cast.RePublishReq
|
||||||
44, // 140: Cast.Cast.ArtistInfo:input_type -> Cast.ArtistInfoReq
|
39, // 140: Cast.Cast.DelWork:input_type -> Cast.DelWorkReq
|
||||||
46, // 141: Cast.Cast.ImportWorkBatch:input_type -> Cast.ImportWorkBatchReq
|
40, // 141: Cast.Cast.WorkInfo:input_type -> Cast.WorkInfoReq
|
||||||
49, // 142: Cast.Cast.UpdateWorkPlatformInfo:input_type -> Cast.UpdateWorkPlatformInfoReq
|
44, // 142: Cast.Cast.ArtistInfo:input_type -> Cast.ArtistInfoReq
|
||||||
51, // 143: Cast.Cast.UpdateWorkPublishLog:input_type -> Cast.UpdateWorkPublishLogReq
|
46, // 143: Cast.Cast.ImportWorkBatch:input_type -> Cast.ImportWorkBatchReq
|
||||||
52, // 144: Cast.Cast.RefreshWorkList:input_type -> Cast.RefreshWorkListReq
|
49, // 144: Cast.Cast.UpdateWorkPlatformInfo:input_type -> Cast.UpdateWorkPlatformInfoReq
|
||||||
54, // 145: Cast.Cast.OAuthAccount:input_type -> Cast.OAuthAccountReq
|
51, // 145: Cast.Cast.UpdateWorkPublishLog:input_type -> Cast.UpdateWorkPublishLogReq
|
||||||
56, // 146: Cast.Cast.OAuthAccountV2:input_type -> Cast.OAuthAccountV2Req
|
52, // 146: Cast.Cast.RefreshWorkList:input_type -> Cast.RefreshWorkListReq
|
||||||
60, // 147: Cast.Cast.OAuthCodeToToken:input_type -> Cast.OAuthCodeToTokenReq
|
54, // 147: Cast.Cast.OAuthAccount:input_type -> Cast.OAuthAccountReq
|
||||||
62, // 148: Cast.Cast.UpdateOAuth:input_type -> Cast.UpdateOAuthReq
|
56, // 148: Cast.Cast.OAuthAccountV2:input_type -> Cast.OAuthAccountV2Req
|
||||||
63, // 149: Cast.Cast.RefreshToken:input_type -> Cast.RefreshTokenReq
|
60, // 149: Cast.Cast.OAuthCodeToToken:input_type -> Cast.OAuthCodeToTokenReq
|
||||||
65, // 150: Cast.Cast.PublishMediaInfo:input_type -> Cast.PublishMediaInfoReq
|
62, // 150: Cast.Cast.UpdateOAuth:input_type -> Cast.UpdateOAuthReq
|
||||||
67, // 151: Cast.Cast.Tools:input_type -> Cast.ToolsReq
|
63, // 151: Cast.Cast.RefreshToken:input_type -> Cast.RefreshTokenReq
|
||||||
68, // 152: Cast.Cast.UpdateVideoScript:input_type -> Cast.UpdateVideoScriptReq
|
65, // 152: Cast.Cast.PublishMediaInfo:input_type -> Cast.PublishMediaInfoReq
|
||||||
70, // 153: Cast.Cast.GetVideoScript:input_type -> Cast.GetVideoScriptReq
|
67, // 153: Cast.Cast.Tools:input_type -> Cast.ToolsReq
|
||||||
72, // 154: Cast.Cast.ListVideoScripts:input_type -> Cast.ListVideoScriptsReq
|
68, // 154: Cast.Cast.UpdateVideoScript:input_type -> Cast.UpdateVideoScriptReq
|
||||||
75, // 155: Cast.Cast.DeleteVideoScript:input_type -> Cast.DeleteVideoScriptReq
|
70, // 155: Cast.Cast.GetVideoScript:input_type -> Cast.GetVideoScriptReq
|
||||||
76, // 156: Cast.Cast.UpdateVideoScriptBatch:input_type -> Cast.UpdateVideoScriptBatchReq
|
72, // 156: Cast.Cast.ListVideoScripts:input_type -> Cast.ListVideoScriptsReq
|
||||||
78, // 157: Cast.Cast.UpdateScriptStatus:input_type -> Cast.UpdateScriptStatusReq
|
75, // 157: Cast.Cast.DeleteVideoScript:input_type -> Cast.DeleteVideoScriptReq
|
||||||
80, // 158: Cast.Cast.GetLayout:input_type -> Cast.GetLayoutReq
|
76, // 158: Cast.Cast.UpdateVideoScriptBatch:input_type -> Cast.UpdateVideoScriptBatchReq
|
||||||
79, // 159: Cast.Cast.SetLayout:input_type -> Cast.SetLayoutReq
|
78, // 159: Cast.Cast.UpdateScriptStatus:input_type -> Cast.UpdateScriptStatusReq
|
||||||
82, // 160: Cast.Cast.UpdatePrompt:input_type -> Cast.UpdatePromptReq
|
80, // 160: Cast.Cast.GetLayout:input_type -> Cast.GetLayoutReq
|
||||||
83, // 161: Cast.Cast.DeletePrompt:input_type -> Cast.DeletePromptReq
|
79, // 161: Cast.Cast.SetLayout:input_type -> Cast.SetLayoutReq
|
||||||
84, // 162: Cast.Cast.GetPrompt:input_type -> Cast.GetPromptReq
|
82, // 162: Cast.Cast.UpdatePrompt:input_type -> Cast.UpdatePromptReq
|
||||||
86, // 163: Cast.Cast.ListPrompts:input_type -> Cast.ListPromptsReq
|
83, // 163: Cast.Cast.DeletePrompt:input_type -> Cast.DeletePromptReq
|
||||||
89, // 164: Cast.Cast.UpdatePromptBatch:input_type -> Cast.UpdatePromptBatchReq
|
84, // 164: Cast.Cast.GetPrompt:input_type -> Cast.GetPromptReq
|
||||||
92, // 165: Cast.Cast.UpdateArtist:input_type -> Cast.UpdateArtistReq
|
86, // 165: Cast.Cast.ListPrompts:input_type -> Cast.ListPromptsReq
|
||||||
94, // 166: Cast.Cast.GetArtist:input_type -> Cast.GetArtistReq
|
89, // 166: Cast.Cast.UpdatePromptBatch:input_type -> Cast.UpdatePromptBatchReq
|
||||||
96, // 167: Cast.Cast.CreateWorkAnalysis:input_type -> Cast.CreateWorkAnalysisReq
|
92, // 167: Cast.Cast.UpdateArtist:input_type -> Cast.UpdateArtistReq
|
||||||
98, // 168: Cast.Cast.UpdateWorkAnalysis:input_type -> Cast.UpdateWorkAnalysisReq
|
94, // 168: Cast.Cast.GetArtist:input_type -> Cast.GetArtistReq
|
||||||
99, // 169: Cast.Cast.UpdateWorkAnalysisStatus:input_type -> Cast.UpdateWorkAnalysisStatusReq
|
96, // 169: Cast.Cast.CreateWorkAnalysis:input_type -> Cast.CreateWorkAnalysisReq
|
||||||
110, // 170: Cast.Cast.GetWorkAnalysis:input_type -> Cast.GetWorkAnalysisDetailReq
|
98, // 170: Cast.Cast.UpdateWorkAnalysis:input_type -> Cast.UpdateWorkAnalysisReq
|
||||||
111, // 171: Cast.Cast.GetLatestWorkAnalysis:input_type -> Cast.GetLatestWorkAnalysisReq
|
99, // 171: Cast.Cast.UpdateWorkAnalysisStatus:input_type -> Cast.UpdateWorkAnalysisStatusReq
|
||||||
114, // 172: Cast.Cast.ListWorkAnalysis:input_type -> Cast.ListWorkAnalysisReq
|
110, // 172: Cast.Cast.GetWorkAnalysis:input_type -> Cast.GetWorkAnalysisDetailReq
|
||||||
117, // 173: Cast.Cast.DeleteWorkAnalysis:input_type -> Cast.DeleteWorkAnalysisReq
|
111, // 173: Cast.Cast.GetLatestWorkAnalysis:input_type -> Cast.GetLatestWorkAnalysisReq
|
||||||
136, // 174: Cast.Cast.UpdateWorkAnalysisApprovalID:input_type -> Cast.UpdateWorkAnalysisApprovalIDReq
|
114, // 174: Cast.Cast.ListWorkAnalysis:input_type -> Cast.ListWorkAnalysisReq
|
||||||
118, // 175: Cast.Cast.ArtistDataList:input_type -> Cast.ArtistDataListReq
|
117, // 175: Cast.Cast.DeleteWorkAnalysis:input_type -> Cast.DeleteWorkAnalysisReq
|
||||||
121, // 176: Cast.Cast.MediaDataList:input_type -> Cast.MediaDataListReq
|
136, // 176: Cast.Cast.UpdateWorkAnalysisApprovalID:input_type -> Cast.UpdateWorkAnalysisApprovalIDReq
|
||||||
124, // 177: Cast.Cast.DataOverview:input_type -> Cast.DataOverviewReq
|
118, // 177: Cast.Cast.ArtistDataList:input_type -> Cast.ArtistDataListReq
|
||||||
126, // 178: Cast.Cast.ArtistMetricsSeries:input_type -> Cast.ArtistMetricsSeriesReq
|
121, // 178: Cast.Cast.MediaDataList:input_type -> Cast.MediaDataListReq
|
||||||
128, // 179: Cast.Cast.ArtistMetricsDailyWindow:input_type -> Cast.ArtistMetricsDailyWindowReq
|
124, // 179: Cast.Cast.DataOverview:input_type -> Cast.DataOverviewReq
|
||||||
133, // 180: Cast.Cast.TobeConfirmedList:input_type -> Cast.TobeConfirmedListReq
|
126, // 180: Cast.Cast.ArtistMetricsSeries:input_type -> Cast.ArtistMetricsSeriesReq
|
||||||
138, // 181: Cast.Cast.UpsertMediaMetricsDailyBatch:input_type -> Cast.UpsertMediaMetricsDailyBatchReq
|
128, // 181: Cast.Cast.ArtistMetricsDailyWindow:input_type -> Cast.ArtistMetricsDailyWindowReq
|
||||||
141, // 182: Cast.Cast.UpsertWorkMetricsDailyBatch:input_type -> Cast.UpsertWorkMetricsDailyBatchReq
|
133, // 182: Cast.Cast.TobeConfirmedList:input_type -> Cast.TobeConfirmedListReq
|
||||||
151, // 183: Cast.Cast.ListMediaMetricsDaily:input_type -> Cast.ListMediaMetricsDailyReq
|
138, // 183: Cast.Cast.UpsertMediaMetricsDailyBatch:input_type -> Cast.UpsertMediaMetricsDailyBatchReq
|
||||||
154, // 184: Cast.Cast.ListWorkMetricsDaily:input_type -> Cast.ListWorkMetricsDailyReq
|
141, // 184: Cast.Cast.UpsertWorkMetricsDailyBatch:input_type -> Cast.UpsertWorkMetricsDailyBatchReq
|
||||||
165, // 185: Cast.Cast.CalculateMediaMetricsByWorks:input_type -> Cast.CalculateMediaMetricsByWorksReq
|
151, // 185: Cast.Cast.ListMediaMetricsDaily:input_type -> Cast.ListMediaMetricsDailyReq
|
||||||
143, // 186: Cast.Cast.GetArtistAyrShareInfo:input_type -> Cast.GetArtistAyrShareInfoReq
|
154, // 186: Cast.Cast.ListWorkMetricsDaily:input_type -> Cast.ListWorkMetricsDailyReq
|
||||||
146, // 187: Cast.Cast.GetArtistAyrShareInfoByPlatformIDs:input_type -> Cast.GetArtistAyrShareInfoByPlatformIDsReq
|
165, // 187: Cast.Cast.CalculateMediaMetricsByWorks:input_type -> Cast.CalculateMediaMetricsByWorksReq
|
||||||
148, // 188: Cast.Cast.ListWorkPlatformInfo:input_type -> Cast.ListWorkPlatformInfoReq
|
143, // 188: Cast.Cast.GetArtistAyrShareInfo:input_type -> Cast.GetArtistAyrShareInfoReq
|
||||||
157, // 189: Cast.Cast.UpsertTaskList:input_type -> Cast.UpsertTaskListReq
|
146, // 189: Cast.Cast.GetArtistAyrShareInfoByPlatformIDs:input_type -> Cast.GetArtistAyrShareInfoByPlatformIDsReq
|
||||||
159, // 190: Cast.Cast.GetTaskList:input_type -> Cast.GetTaskListReq
|
148, // 190: Cast.Cast.ListWorkPlatformInfo:input_type -> Cast.ListWorkPlatformInfoReq
|
||||||
162, // 191: Cast.Cast.ListTaskList:input_type -> Cast.ListTaskListReq
|
157, // 191: Cast.Cast.UpsertTaskList:input_type -> Cast.UpsertTaskListReq
|
||||||
164, // 192: Cast.Cast.DeleteTaskList:input_type -> Cast.DeleteTaskListReq
|
159, // 192: Cast.Cast.GetTaskList:input_type -> Cast.GetTaskListReq
|
||||||
167, // 193: Cast.Cast.UpdateCastTag:input_type -> Cast.UpdateCastTagReq
|
162, // 193: Cast.Cast.ListTaskList:input_type -> Cast.ListTaskListReq
|
||||||
169, // 194: Cast.Cast.ListCastTags:input_type -> Cast.ListCastTagsReq
|
164, // 194: Cast.Cast.DeleteTaskList:input_type -> Cast.DeleteTaskListReq
|
||||||
172, // 195: Cast.Cast.UpdateCastTagBatch:input_type -> Cast.UpdateCastTagBatchReq
|
167, // 195: Cast.Cast.UpdateCastTag:input_type -> Cast.UpdateCastTagReq
|
||||||
174, // 196: Cast.Cast.BatchUpdateCastTags:input_type -> Cast.BatchUpdateCastTagsReq
|
169, // 196: Cast.Cast.ListCastTags:input_type -> Cast.ListCastTagsReq
|
||||||
175, // 197: Cast.Cast.UpdateCastTagStatus:input_type -> Cast.UpdateCastTagStatusReq
|
172, // 197: Cast.Cast.UpdateCastTagBatch:input_type -> Cast.UpdateCastTagBatchReq
|
||||||
207, // 198: Cast.Cast.RecalculateCastTagQuoteCount:input_type -> google.protobuf.Empty
|
174, // 198: Cast.Cast.BatchUpdateCastTags:input_type -> Cast.BatchUpdateCastTagsReq
|
||||||
177, // 199: Cast.Cast.CreateCompetitiveReport:input_type -> Cast.CreateCompetitiveReportReq
|
175, // 199: Cast.Cast.UpdateCastTagStatus:input_type -> Cast.UpdateCastTagStatusReq
|
||||||
192, // 200: Cast.Cast.ImportCompetitiveReportBatch:input_type -> Cast.ImportCompetitiveReportBatchReq
|
207, // 200: Cast.Cast.RecalculateCastTagQuoteCount:input_type -> google.protobuf.Empty
|
||||||
180, // 201: Cast.Cast.UpdateCompetitiveReportStatus:input_type -> Cast.UpdateCompetitiveReportStatusReq
|
177, // 201: Cast.Cast.CreateCompetitiveReport:input_type -> Cast.CreateCompetitiveReportReq
|
||||||
184, // 202: Cast.Cast.GetCompetitiveReport:input_type -> Cast.GetCompetitiveReportDetailReq
|
192, // 202: Cast.Cast.ImportCompetitiveReportBatch:input_type -> Cast.ImportCompetitiveReportBatchReq
|
||||||
185, // 203: Cast.Cast.GetCompetitiveReportForApp:input_type -> Cast.GetCompetitiveReportForAppReq
|
180, // 203: Cast.Cast.UpdateCompetitiveReportStatus:input_type -> Cast.UpdateCompetitiveReportStatusReq
|
||||||
188, // 204: Cast.Cast.ListCompetitiveReport:input_type -> Cast.ListCompetitiveReportReq
|
184, // 204: Cast.Cast.GetCompetitiveReport:input_type -> Cast.GetCompetitiveReportDetailReq
|
||||||
191, // 205: Cast.Cast.DeleteCompetitiveReport:input_type -> Cast.DeleteCompetitiveReportReq
|
185, // 205: Cast.Cast.GetCompetitiveReportForApp:input_type -> Cast.GetCompetitiveReportForAppReq
|
||||||
181, // 206: Cast.Cast.UpdateCompetitiveReportApprovalID:input_type -> Cast.UpdateCompetitiveReportApprovalIDReq
|
188, // 206: Cast.Cast.ListCompetitiveReport:input_type -> Cast.ListCompetitiveReportReq
|
||||||
194, // 207: Cast.Cast.CountCompetitiveReportByWorkUuids:input_type -> Cast.CountCompetitiveReportByWorkUuidsReq
|
191, // 207: Cast.Cast.DeleteCompetitiveReport:input_type -> Cast.DeleteCompetitiveReportReq
|
||||||
10, // 208: Cast.Cast.MediaUserList:output_type -> Cast.MediaUserListResp
|
181, // 208: Cast.Cast.UpdateCompetitiveReportApprovalID:input_type -> Cast.UpdateCompetitiveReportApprovalIDReq
|
||||||
12, // 209: Cast.Cast.UpdateMediaAccount:output_type -> Cast.UpdateMediaAccountResp
|
194, // 209: Cast.Cast.CountCompetitiveReportByWorkUuids:input_type -> Cast.CountCompetitiveReportByWorkUuidsReq
|
||||||
14, // 210: Cast.Cast.UnbindManager:output_type -> Cast.UnbindManagerResp
|
10, // 210: Cast.Cast.MediaUserList:output_type -> Cast.MediaUserListResp
|
||||||
207, // 211: Cast.Cast.BindManager:output_type -> google.protobuf.Empty
|
12, // 211: Cast.Cast.UpdateMediaAccount:output_type -> Cast.UpdateMediaAccountResp
|
||||||
17, // 212: Cast.Cast.UpdateWorkImage:output_type -> Cast.UpdateWorkImageResp
|
14, // 212: Cast.Cast.UnbindManager:output_type -> Cast.UnbindManagerResp
|
||||||
20, // 213: Cast.Cast.UpdateWorkVideo:output_type -> Cast.UpdateWorkVideoResp
|
207, // 213: Cast.Cast.BindManager:output_type -> google.protobuf.Empty
|
||||||
22, // 214: Cast.Cast.MediaInfo:output_type -> Cast.MediaInfoResp
|
17, // 214: Cast.Cast.UpdateWorkImage:output_type -> Cast.UpdateWorkImageResp
|
||||||
24, // 215: Cast.Cast.MediaInfoByPlatform:output_type -> Cast.MediaInfoByPlatformResp
|
20, // 215: Cast.Cast.UpdateWorkVideo:output_type -> Cast.UpdateWorkVideoResp
|
||||||
26, // 216: Cast.Cast.WorkList:output_type -> Cast.WorkListResp
|
22, // 216: Cast.Cast.MediaInfo:output_type -> Cast.MediaInfoResp
|
||||||
43, // 217: Cast.Cast.WorkListPublished:output_type -> Cast.WorkListPublishedResp
|
24, // 217: Cast.Cast.MediaInfoByPlatform:output_type -> Cast.MediaInfoByPlatformResp
|
||||||
29, // 218: Cast.Cast.WorkDetail:output_type -> Cast.WorkDetailResp
|
26, // 218: Cast.Cast.WorkList:output_type -> Cast.WorkListResp
|
||||||
207, // 219: Cast.Cast.UpdateStatus:output_type -> google.protobuf.Empty
|
43, // 219: Cast.Cast.WorkListPublished:output_type -> Cast.WorkListPublishedResp
|
||||||
32, // 220: Cast.Cast.MediaAccounts:output_type -> Cast.MediaAccountsResp
|
29, // 220: Cast.Cast.WorkDetail:output_type -> Cast.WorkDetailResp
|
||||||
34, // 221: Cast.Cast.MediaWorks:output_type -> Cast.MediaWorksResp
|
207, // 221: Cast.Cast.UpdateStatus:output_type -> google.protobuf.Empty
|
||||||
36, // 222: Cast.Cast.Publish:output_type -> Cast.PublishResp
|
32, // 222: Cast.Cast.MediaAccounts:output_type -> Cast.MediaAccountsResp
|
||||||
38, // 223: Cast.Cast.RePublish:output_type -> Cast.RePublishResp
|
34, // 223: Cast.Cast.MediaWorks:output_type -> Cast.MediaWorksResp
|
||||||
207, // 224: Cast.Cast.DelWork:output_type -> google.protobuf.Empty
|
36, // 224: Cast.Cast.Publish:output_type -> Cast.PublishResp
|
||||||
41, // 225: Cast.Cast.WorkInfo:output_type -> Cast.WorkInfoResp
|
38, // 225: Cast.Cast.RePublish:output_type -> Cast.RePublishResp
|
||||||
45, // 226: Cast.Cast.ArtistInfo:output_type -> Cast.ArtistInfoResp
|
207, // 226: Cast.Cast.DelWork:output_type -> google.protobuf.Empty
|
||||||
47, // 227: Cast.Cast.ImportWorkBatch:output_type -> Cast.ImportWorkBatchResp
|
41, // 227: Cast.Cast.WorkInfo:output_type -> Cast.WorkInfoResp
|
||||||
50, // 228: Cast.Cast.UpdateWorkPlatformInfo:output_type -> Cast.UpdateWorkPlatformInfoResp
|
45, // 228: Cast.Cast.ArtistInfo:output_type -> Cast.ArtistInfoResp
|
||||||
207, // 229: Cast.Cast.UpdateWorkPublishLog:output_type -> google.protobuf.Empty
|
47, // 229: Cast.Cast.ImportWorkBatch:output_type -> Cast.ImportWorkBatchResp
|
||||||
53, // 230: Cast.Cast.RefreshWorkList:output_type -> Cast.RefreshWorkListResp
|
50, // 230: Cast.Cast.UpdateWorkPlatformInfo:output_type -> Cast.UpdateWorkPlatformInfoResp
|
||||||
55, // 231: Cast.Cast.OAuthAccount:output_type -> Cast.OAuthAccountResp
|
207, // 231: Cast.Cast.UpdateWorkPublishLog:output_type -> google.protobuf.Empty
|
||||||
57, // 232: Cast.Cast.OAuthAccountV2:output_type -> Cast.OAuthAccountV2Resp
|
53, // 232: Cast.Cast.RefreshWorkList:output_type -> Cast.RefreshWorkListResp
|
||||||
61, // 233: Cast.Cast.OAuthCodeToToken:output_type -> Cast.OAuthCodeToTokenResp
|
55, // 233: Cast.Cast.OAuthAccount:output_type -> Cast.OAuthAccountResp
|
||||||
207, // 234: Cast.Cast.UpdateOAuth:output_type -> google.protobuf.Empty
|
57, // 234: Cast.Cast.OAuthAccountV2:output_type -> Cast.OAuthAccountV2Resp
|
||||||
64, // 235: Cast.Cast.RefreshToken:output_type -> Cast.RefreshTokenResp
|
61, // 235: Cast.Cast.OAuthCodeToToken:output_type -> Cast.OAuthCodeToTokenResp
|
||||||
66, // 236: Cast.Cast.PublishMediaInfo:output_type -> Cast.PublishMediaInfoResp
|
207, // 236: Cast.Cast.UpdateOAuth:output_type -> google.protobuf.Empty
|
||||||
207, // 237: Cast.Cast.Tools:output_type -> google.protobuf.Empty
|
64, // 237: Cast.Cast.RefreshToken:output_type -> Cast.RefreshTokenResp
|
||||||
69, // 238: Cast.Cast.UpdateVideoScript:output_type -> Cast.UpdateVideoScriptResp
|
66, // 238: Cast.Cast.PublishMediaInfo:output_type -> Cast.PublishMediaInfoResp
|
||||||
71, // 239: Cast.Cast.GetVideoScript:output_type -> Cast.GetVideoScriptResp
|
207, // 239: Cast.Cast.Tools:output_type -> google.protobuf.Empty
|
||||||
74, // 240: Cast.Cast.ListVideoScripts:output_type -> Cast.ListVideoScriptsResp
|
69, // 240: Cast.Cast.UpdateVideoScript:output_type -> Cast.UpdateVideoScriptResp
|
||||||
207, // 241: Cast.Cast.DeleteVideoScript:output_type -> google.protobuf.Empty
|
71, // 241: Cast.Cast.GetVideoScript:output_type -> Cast.GetVideoScriptResp
|
||||||
77, // 242: Cast.Cast.UpdateVideoScriptBatch:output_type -> Cast.UpdateVideoScriptBatchResp
|
74, // 242: Cast.Cast.ListVideoScripts:output_type -> Cast.ListVideoScriptsResp
|
||||||
207, // 243: Cast.Cast.UpdateScriptStatus:output_type -> google.protobuf.Empty
|
207, // 243: Cast.Cast.DeleteVideoScript:output_type -> google.protobuf.Empty
|
||||||
81, // 244: Cast.Cast.GetLayout:output_type -> Cast.GetLayoutResp
|
77, // 244: Cast.Cast.UpdateVideoScriptBatch:output_type -> Cast.UpdateVideoScriptBatchResp
|
||||||
207, // 245: Cast.Cast.SetLayout:output_type -> google.protobuf.Empty
|
207, // 245: Cast.Cast.UpdateScriptStatus:output_type -> google.protobuf.Empty
|
||||||
207, // 246: Cast.Cast.UpdatePrompt:output_type -> google.protobuf.Empty
|
81, // 246: Cast.Cast.GetLayout:output_type -> Cast.GetLayoutResp
|
||||||
207, // 247: Cast.Cast.DeletePrompt:output_type -> google.protobuf.Empty
|
207, // 247: Cast.Cast.SetLayout:output_type -> google.protobuf.Empty
|
||||||
85, // 248: Cast.Cast.GetPrompt:output_type -> Cast.GetPromptResp
|
207, // 248: Cast.Cast.UpdatePrompt:output_type -> google.protobuf.Empty
|
||||||
88, // 249: Cast.Cast.ListPrompts:output_type -> Cast.ListPromptsResp
|
207, // 249: Cast.Cast.DeletePrompt:output_type -> google.protobuf.Empty
|
||||||
90, // 250: Cast.Cast.UpdatePromptBatch:output_type -> Cast.UpdatePromptBatchResp
|
85, // 250: Cast.Cast.GetPrompt:output_type -> Cast.GetPromptResp
|
||||||
93, // 251: Cast.Cast.UpdateArtist:output_type -> Cast.UpdateArtistResp
|
88, // 251: Cast.Cast.ListPrompts:output_type -> Cast.ListPromptsResp
|
||||||
95, // 252: Cast.Cast.GetArtist:output_type -> Cast.GetArtistResp
|
90, // 252: Cast.Cast.UpdatePromptBatch:output_type -> Cast.UpdatePromptBatchResp
|
||||||
97, // 253: Cast.Cast.CreateWorkAnalysis:output_type -> Cast.CreateWorkAnalysisResp
|
93, // 253: Cast.Cast.UpdateArtist:output_type -> Cast.UpdateArtistResp
|
||||||
207, // 254: Cast.Cast.UpdateWorkAnalysis:output_type -> google.protobuf.Empty
|
95, // 254: Cast.Cast.GetArtist:output_type -> Cast.GetArtistResp
|
||||||
207, // 255: Cast.Cast.UpdateWorkAnalysisStatus:output_type -> google.protobuf.Empty
|
97, // 255: Cast.Cast.CreateWorkAnalysis:output_type -> Cast.CreateWorkAnalysisResp
|
||||||
113, // 256: Cast.Cast.GetWorkAnalysis:output_type -> Cast.GetWorkAnalysisDetailResp
|
207, // 256: Cast.Cast.UpdateWorkAnalysis:output_type -> google.protobuf.Empty
|
||||||
112, // 257: Cast.Cast.GetLatestWorkAnalysis:output_type -> Cast.GetWorkAnalysisResp
|
207, // 257: Cast.Cast.UpdateWorkAnalysisStatus:output_type -> google.protobuf.Empty
|
||||||
116, // 258: Cast.Cast.ListWorkAnalysis:output_type -> Cast.ListWorkAnalysisResp
|
113, // 258: Cast.Cast.GetWorkAnalysis:output_type -> Cast.GetWorkAnalysisDetailResp
|
||||||
207, // 259: Cast.Cast.DeleteWorkAnalysis:output_type -> google.protobuf.Empty
|
112, // 259: Cast.Cast.GetLatestWorkAnalysis:output_type -> Cast.GetWorkAnalysisResp
|
||||||
207, // 260: Cast.Cast.UpdateWorkAnalysisApprovalID:output_type -> google.protobuf.Empty
|
116, // 260: Cast.Cast.ListWorkAnalysis:output_type -> Cast.ListWorkAnalysisResp
|
||||||
120, // 261: Cast.Cast.ArtistDataList:output_type -> Cast.ArtistDataListResp
|
207, // 261: Cast.Cast.DeleteWorkAnalysis:output_type -> google.protobuf.Empty
|
||||||
123, // 262: Cast.Cast.MediaDataList:output_type -> Cast.MediaDataListResp
|
207, // 262: Cast.Cast.UpdateWorkAnalysisApprovalID:output_type -> google.protobuf.Empty
|
||||||
125, // 263: Cast.Cast.DataOverview:output_type -> Cast.DataOverviewResp
|
120, // 263: Cast.Cast.ArtistDataList:output_type -> Cast.ArtistDataListResp
|
||||||
127, // 264: Cast.Cast.ArtistMetricsSeries:output_type -> Cast.ArtistMetricsSeriesResp
|
123, // 264: Cast.Cast.MediaDataList:output_type -> Cast.MediaDataListResp
|
||||||
132, // 265: Cast.Cast.ArtistMetricsDailyWindow:output_type -> Cast.ArtistMetricsDailyWindowResp
|
125, // 265: Cast.Cast.DataOverview:output_type -> Cast.DataOverviewResp
|
||||||
135, // 266: Cast.Cast.TobeConfirmedList:output_type -> Cast.TobeConfirmedListResp
|
127, // 266: Cast.Cast.ArtistMetricsSeries:output_type -> Cast.ArtistMetricsSeriesResp
|
||||||
139, // 267: Cast.Cast.UpsertMediaMetricsDailyBatch:output_type -> Cast.UpsertMediaMetricsDailyBatchResp
|
132, // 267: Cast.Cast.ArtistMetricsDailyWindow:output_type -> Cast.ArtistMetricsDailyWindowResp
|
||||||
142, // 268: Cast.Cast.UpsertWorkMetricsDailyBatch:output_type -> Cast.UpsertWorkMetricsDailyBatchResp
|
135, // 268: Cast.Cast.TobeConfirmedList:output_type -> Cast.TobeConfirmedListResp
|
||||||
153, // 269: Cast.Cast.ListMediaMetricsDaily:output_type -> Cast.ListMediaMetricsDailyResp
|
139, // 269: Cast.Cast.UpsertMediaMetricsDailyBatch:output_type -> Cast.UpsertMediaMetricsDailyBatchResp
|
||||||
156, // 270: Cast.Cast.ListWorkMetricsDaily:output_type -> Cast.ListWorkMetricsDailyResp
|
142, // 270: Cast.Cast.UpsertWorkMetricsDailyBatch:output_type -> Cast.UpsertWorkMetricsDailyBatchResp
|
||||||
166, // 271: Cast.Cast.CalculateMediaMetricsByWorks:output_type -> Cast.CalculateMediaMetricsByWorksResp
|
153, // 271: Cast.Cast.ListMediaMetricsDaily:output_type -> Cast.ListMediaMetricsDailyResp
|
||||||
145, // 272: Cast.Cast.GetArtistAyrShareInfo:output_type -> Cast.GetArtistAyrShareInfoResp
|
156, // 272: Cast.Cast.ListWorkMetricsDaily:output_type -> Cast.ListWorkMetricsDailyResp
|
||||||
147, // 273: Cast.Cast.GetArtistAyrShareInfoByPlatformIDs:output_type -> Cast.GetArtistAyrShareInfoByPlatformIDsResp
|
166, // 273: Cast.Cast.CalculateMediaMetricsByWorks:output_type -> Cast.CalculateMediaMetricsByWorksResp
|
||||||
150, // 274: Cast.Cast.ListWorkPlatformInfo:output_type -> Cast.ListWorkPlatformInfoResp
|
145, // 274: Cast.Cast.GetArtistAyrShareInfo:output_type -> Cast.GetArtistAyrShareInfoResp
|
||||||
158, // 275: Cast.Cast.UpsertTaskList:output_type -> Cast.UpsertTaskListResp
|
147, // 275: Cast.Cast.GetArtistAyrShareInfoByPlatformIDs:output_type -> Cast.GetArtistAyrShareInfoByPlatformIDsResp
|
||||||
161, // 276: Cast.Cast.GetTaskList:output_type -> Cast.GetTaskListResp
|
150, // 276: Cast.Cast.ListWorkPlatformInfo:output_type -> Cast.ListWorkPlatformInfoResp
|
||||||
163, // 277: Cast.Cast.ListTaskList:output_type -> Cast.ListTaskListResp
|
158, // 277: Cast.Cast.UpsertTaskList:output_type -> Cast.UpsertTaskListResp
|
||||||
207, // 278: Cast.Cast.DeleteTaskList:output_type -> google.protobuf.Empty
|
161, // 278: Cast.Cast.GetTaskList:output_type -> Cast.GetTaskListResp
|
||||||
168, // 279: Cast.Cast.UpdateCastTag:output_type -> Cast.UpdateCastTagResp
|
163, // 279: Cast.Cast.ListTaskList:output_type -> Cast.ListTaskListResp
|
||||||
171, // 280: Cast.Cast.ListCastTags:output_type -> Cast.ListCastTagsResp
|
207, // 280: Cast.Cast.DeleteTaskList:output_type -> google.protobuf.Empty
|
||||||
173, // 281: Cast.Cast.UpdateCastTagBatch:output_type -> Cast.UpdateCastTagBatchResp
|
168, // 281: Cast.Cast.UpdateCastTag:output_type -> Cast.UpdateCastTagResp
|
||||||
207, // 282: Cast.Cast.BatchUpdateCastTags:output_type -> google.protobuf.Empty
|
171, // 282: Cast.Cast.ListCastTags:output_type -> Cast.ListCastTagsResp
|
||||||
207, // 283: Cast.Cast.UpdateCastTagStatus:output_type -> google.protobuf.Empty
|
173, // 283: Cast.Cast.UpdateCastTagBatch:output_type -> Cast.UpdateCastTagBatchResp
|
||||||
176, // 284: Cast.Cast.RecalculateCastTagQuoteCount:output_type -> Cast.RecalculateCastTagQuoteCountResp
|
207, // 284: Cast.Cast.BatchUpdateCastTags:output_type -> google.protobuf.Empty
|
||||||
178, // 285: Cast.Cast.CreateCompetitiveReport:output_type -> Cast.CreateCompetitiveReportResp
|
207, // 285: Cast.Cast.UpdateCastTagStatus:output_type -> google.protobuf.Empty
|
||||||
193, // 286: Cast.Cast.ImportCompetitiveReportBatch:output_type -> Cast.ImportCompetitiveReportBatchResp
|
176, // 286: Cast.Cast.RecalculateCastTagQuoteCount:output_type -> Cast.RecalculateCastTagQuoteCountResp
|
||||||
207, // 287: Cast.Cast.UpdateCompetitiveReportStatus:output_type -> google.protobuf.Empty
|
178, // 287: Cast.Cast.CreateCompetitiveReport:output_type -> Cast.CreateCompetitiveReportResp
|
||||||
187, // 288: Cast.Cast.GetCompetitiveReport:output_type -> Cast.GetCompetitiveReportDetailResp
|
193, // 288: Cast.Cast.ImportCompetitiveReportBatch:output_type -> Cast.ImportCompetitiveReportBatchResp
|
||||||
186, // 289: Cast.Cast.GetCompetitiveReportForApp:output_type -> Cast.GetCompetitiveReportForAppResp
|
207, // 289: Cast.Cast.UpdateCompetitiveReportStatus:output_type -> google.protobuf.Empty
|
||||||
190, // 290: Cast.Cast.ListCompetitiveReport:output_type -> Cast.ListCompetitiveReportResp
|
187, // 290: Cast.Cast.GetCompetitiveReport:output_type -> Cast.GetCompetitiveReportDetailResp
|
||||||
207, // 291: Cast.Cast.DeleteCompetitiveReport:output_type -> google.protobuf.Empty
|
186, // 291: Cast.Cast.GetCompetitiveReportForApp:output_type -> Cast.GetCompetitiveReportForAppResp
|
||||||
207, // 292: Cast.Cast.UpdateCompetitiveReportApprovalID:output_type -> google.protobuf.Empty
|
190, // 292: Cast.Cast.ListCompetitiveReport:output_type -> Cast.ListCompetitiveReportResp
|
||||||
196, // 293: Cast.Cast.CountCompetitiveReportByWorkUuids:output_type -> Cast.CountCompetitiveReportByWorkUuidsResp
|
207, // 293: Cast.Cast.DeleteCompetitiveReport:output_type -> google.protobuf.Empty
|
||||||
208, // [208:294] is the sub-list for method output_type
|
207, // 294: Cast.Cast.UpdateCompetitiveReportApprovalID:output_type -> google.protobuf.Empty
|
||||||
122, // [122:208] is the sub-list for method input_type
|
196, // 295: Cast.Cast.CountCompetitiveReportByWorkUuids:output_type -> Cast.CountCompetitiveReportByWorkUuidsResp
|
||||||
122, // [122:122] is the sub-list for extension type_name
|
210, // [210:296] is the sub-list for method output_type
|
||||||
122, // [122:122] is the sub-list for extension extendee
|
124, // [124:210] is the sub-list for method input_type
|
||||||
0, // [0:122] is the sub-list for field type_name
|
124, // [124:124] is the sub-list for extension type_name
|
||||||
|
124, // [124:124] is the sub-list for extension extendee
|
||||||
|
0, // [0:124] is the sub-list for field type_name
|
||||||
}
|
}
|
||||||
|
|
||||||
func init() { file_pb_fiee_cast_proto_init() }
|
func init() { file_pb_fiee_cast_proto_init() }
|
||||||
|
|||||||
@ -4586,6 +4586,44 @@ func (m *WorkInfoResp) validate(all bool) error {
|
|||||||
|
|
||||||
// no validation rules for WorkCategory
|
// no validation rules for WorkCategory
|
||||||
|
|
||||||
|
for idx, item := range m.GetPlatformInfoData() {
|
||||||
|
_, _ = idx, item
|
||||||
|
|
||||||
|
if all {
|
||||||
|
switch v := interface{}(item).(type) {
|
||||||
|
case interface{ ValidateAll() error }:
|
||||||
|
if err := v.ValidateAll(); err != nil {
|
||||||
|
errors = append(errors, WorkInfoRespValidationError{
|
||||||
|
field: fmt.Sprintf("PlatformInfoData[%v]", idx),
|
||||||
|
reason: "embedded message failed validation",
|
||||||
|
cause: err,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
case interface{ Validate() error }:
|
||||||
|
if err := v.Validate(); err != nil {
|
||||||
|
errors = append(errors, WorkInfoRespValidationError{
|
||||||
|
field: fmt.Sprintf("PlatformInfoData[%v]", idx),
|
||||||
|
reason: "embedded message failed validation",
|
||||||
|
cause: err,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if v, ok := interface{}(item).(interface{ Validate() error }); ok {
|
||||||
|
if err := v.Validate(); err != nil {
|
||||||
|
return WorkInfoRespValidationError{
|
||||||
|
field: fmt.Sprintf("PlatformInfoData[%v]", idx),
|
||||||
|
reason: "embedded message failed validation",
|
||||||
|
cause: err,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// no validation rules for Title
|
||||||
|
|
||||||
|
// no validation rules for PublishStatus
|
||||||
|
|
||||||
if len(errors) > 0 {
|
if len(errors) > 0 {
|
||||||
return WorkInfoRespMultiError(errors)
|
return WorkInfoRespMultiError(errors)
|
||||||
}
|
}
|
||||||
@ -5435,7 +5473,7 @@ func (m *PlatformInfo) validate(all bool) error {
|
|||||||
|
|
||||||
// no validation rules for PublishMediaId
|
// no validation rules for PublishMediaId
|
||||||
|
|
||||||
// no validation rules for PublishStatus
|
// no validation rules for PublishMediaStatus
|
||||||
|
|
||||||
// no validation rules for Remark
|
// no validation rules for Remark
|
||||||
|
|
||||||
@ -19391,6 +19429,8 @@ func (m *UpsertTaskListReq) validate(all bool) error {
|
|||||||
|
|
||||||
// no validation rules for OperatorName
|
// no validation rules for OperatorName
|
||||||
|
|
||||||
|
// no validation rules for ExtraData
|
||||||
|
|
||||||
if len(errors) > 0 {
|
if len(errors) > 0 {
|
||||||
return UpsertTaskListReqMultiError(errors)
|
return UpsertTaskListReqMultiError(errors)
|
||||||
}
|
}
|
||||||
@ -19717,6 +19757,8 @@ func (m *TaskListInfo) validate(all bool) error {
|
|||||||
|
|
||||||
// no validation rules for UpdatedAt
|
// no validation rules for UpdatedAt
|
||||||
|
|
||||||
|
// no validation rules for ExtraData
|
||||||
|
|
||||||
if len(errors) > 0 {
|
if len(errors) > 0 {
|
||||||
return TaskListInfoMultiError(errors)
|
return TaskListInfoMultiError(errors)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -27,7 +27,7 @@ func InitTasks() error {
|
|||||||
cm := GetCronManager()
|
cm := GetCronManager()
|
||||||
err := cm.AddTask("refreshWorkApprovalStatus", "0 */1 * * * *", RefreshWorkApprovalStatusTask)
|
err := cm.AddTask("refreshWorkApprovalStatus", "0 */1 * * * *", RefreshWorkApprovalStatusTask)
|
||||||
err = cm.AddTask("artistAutoConfirm", "0 */1 * * * *", ArtistAutoConfirmTask)
|
err = cm.AddTask("artistAutoConfirm", "0 */1 * * * *", ArtistAutoConfirmTask)
|
||||||
err = cm.AddTask("refreshPublishStatus", "0 */1 * * * *", RefreshPublishStatusTask)
|
err = cm.AddTask("refreshPublishStatus", "0 */1 * * * *", PublishTask)
|
||||||
err = cm.AddTask("scheduledPublish", "0 */1 * * * *", ScheduledPublishTask)
|
err = cm.AddTask("scheduledPublish", "0 */1 * * * *", ScheduledPublishTask)
|
||||||
|
|
||||||
err = cm.AddTask("artistAutoConfirmAnalysis", "0 */1 * * * *", ArtistAutoConfirmAnalysisTask)
|
err = cm.AddTask("artistAutoConfirmAnalysis", "0 */1 * * * *", ArtistAutoConfirmAnalysisTask)
|
||||||
@ -272,7 +272,11 @@ func RefreshPublishStatusTask() {
|
|||||||
//zap.L().Info("刷新发布状态成功")
|
//zap.L().Info("刷新发布状态成功")
|
||||||
}
|
}
|
||||||
|
|
||||||
// ScheduledPublishTask 定时发布任务,从Redis Sorted Set中获取所有workUuid并根据score判断处理
|
// PublishTask 定时发布任务,从Redis Sorted Set中获取所有workUuid并根据score判断处理
|
||||||
|
func PublishTask() {
|
||||||
|
go RefreshPublishStatusTask() // 刷新发布状态
|
||||||
|
go TaskStatus() // 异步任务状态
|
||||||
|
}
|
||||||
func ScheduledPublishTask() {
|
func ScheduledPublishTask() {
|
||||||
// 加上锁
|
// 加上锁
|
||||||
lockKey := "scheduled_publish:lock"
|
lockKey := "scheduled_publish:lock"
|
||||||
@ -303,7 +307,7 @@ func ScheduledPublishTask() {
|
|||||||
|
|
||||||
publishCount := 0
|
publishCount := 0
|
||||||
expiredCount := 0
|
expiredCount := 0
|
||||||
const batchSize = 10 // 每批发布10个
|
const batchSize = 8 // 每批发布8个,与PublishWork的workerCount保持一致
|
||||||
|
|
||||||
zap.L().Info("发现定时发布任务", zap.Int("total_count", len(workList)))
|
zap.L().Info("发现定时发布任务", zap.Int("total_count", len(workList)))
|
||||||
|
|
||||||
@ -382,6 +386,61 @@ func ScheduledPublishTask() {
|
|||||||
zap.Int("total_count", len(workList)))
|
zap.Int("total_count", len(workList)))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TaskStatus() {
|
||||||
|
var actions []string = []string{"publishBatch1", "publishBatch2"}
|
||||||
|
for _, action := range actions {
|
||||||
|
resp, err := service.CastProvider.ListTaskList(context.Background(), &cast.ListTaskListReq{
|
||||||
|
Action: action,
|
||||||
|
Status: 1,
|
||||||
|
Page: 1,
|
||||||
|
PageSize: 100,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("获取任务列表失败", zap.Error(err))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
for _, v := range resp.Data {
|
||||||
|
var extraData modelCast.PublishTaskDto
|
||||||
|
if v.ExtraData == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
_ = json.Unmarshal([]byte(v.ExtraData), &extraData)
|
||||||
|
var allDone = true
|
||||||
|
for _, workUuid := range extraData.WorkUuids {
|
||||||
|
infoResp, _err := service.CastProvider.WorkInfo(context.Background(), &cast.WorkInfoReq{WorkUuid: workUuid})
|
||||||
|
if _err != nil {
|
||||||
|
zap.L().Error("获取作品信息失败", zap.Error(_err))
|
||||||
|
allDone = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if infoResp.PublishStatus != cast.PublishStatusENUM_PublishMediaStatus_DONE {
|
||||||
|
allDone = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var excelUrl string
|
||||||
|
if allDone {
|
||||||
|
excelUrl, err = serverCast.PublishTaskExcel(extraData.WorkUuids, true, v.Action)
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("生成发布任务Excel失败", zap.Error(err))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
_, err = service.CastProvider.UpsertTaskList(context.Background(), &cast.UpsertTaskListReq{
|
||||||
|
Uuid: v.Uuid,
|
||||||
|
Action: v.Action,
|
||||||
|
Url: excelUrl,
|
||||||
|
Status: 3,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("更新任务状态失败", zap.Error(err))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
zap.L().Info("任务已完成,更新状态为完成", zap.String("task_uuid", v.Uuid), zap.String("excel_url", excelUrl))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// WorkPublishQueueConsumer 监听work:publish:queue队列的消费者
|
// WorkPublishQueueConsumer 监听work:publish:queue队列的消费者
|
||||||
func WorkPublishQueueConsumer() {
|
func WorkPublishQueueConsumer() {
|
||||||
zap.L().Info("开始监听work:publish:queue队列(批量处理模式)")
|
zap.L().Info("开始监听work:publish:queue队列(批量处理模式)")
|
||||||
@ -506,5 +565,5 @@ func AyrshareMetricsCollectorTask() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func RefreshArtistOrderTask() {
|
func RefreshArtistOrderTask() {
|
||||||
service.CastProvider.Tools(context.Background(), &cast.ToolsReq{Action: "refreshArtistOrder"})
|
_, _ = service.CastProvider.Tools(context.Background(), &cast.ToolsReq{Action: "artistOrderInfo"})
|
||||||
}
|
}
|
||||||
|
|||||||
13
pkg/model/cast/task.go
Normal file
13
pkg/model/cast/task.go
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
package cast
|
||||||
|
|
||||||
|
type PublishTaskDto struct {
|
||||||
|
WorkUuids []string
|
||||||
|
MediaAccountUuids []string
|
||||||
|
PlatformIds []string
|
||||||
|
}
|
||||||
|
|
||||||
|
var TaskActionName = map[string]string{
|
||||||
|
"importWorkBatch": "批量导入图文",
|
||||||
|
"publishBatch1": "批量发布",
|
||||||
|
"publishBatch2": "多账号同步",
|
||||||
|
}
|
||||||
@ -63,6 +63,7 @@ func MediaRouter(r *gin.RouterGroup) {
|
|||||||
{
|
{
|
||||||
task.POST("list", serviceCast.TaskList)
|
task.POST("list", serviceCast.TaskList)
|
||||||
task.POST("delete", serviceCast.DeleteTasK)
|
task.POST("delete", serviceCast.DeleteTasK)
|
||||||
|
task.POST("download", serviceCast.DownloadTaskFile)
|
||||||
}
|
}
|
||||||
|
|
||||||
layout := auth.Group("layout")
|
layout := auth.Group("layout")
|
||||||
|
|||||||
@ -169,7 +169,7 @@ func UpdateMediaAccount(ctx *gin.Context) {
|
|||||||
}
|
}
|
||||||
if userResp != nil && len(userResp.Data) > 0 {
|
if userResp != nil && len(userResp.Data) > 0 {
|
||||||
for _, v := range userResp.Data {
|
for _, v := range userResp.Data {
|
||||||
if v.PlatformID == uint32(req.PlatformID) {
|
if v.PlatformID == uint32(req.PlatformID) && v.Expired == 1 {
|
||||||
service.Error(ctx, errors.New("账号已存在"))
|
service.Error(ctx, errors.New("账号已存在"))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -258,6 +258,10 @@ func OAuthAccount(ctx *gin.Context) {
|
|||||||
service.Error(ctx, errors.New("未找到该账号"))
|
service.Error(ctx, errors.New("未找到该账号"))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
if mediaResp.Data[0].Expired != 1 {
|
||||||
|
service.Error(ctx, errors.New("账号已过期"))
|
||||||
|
return
|
||||||
|
}
|
||||||
if err = SyncAsAuth(mediaResp.Data[0].ArtistUuid); err != nil {
|
if err = SyncAsAuth(mediaResp.Data[0].ArtistUuid); err != nil {
|
||||||
service.Error(ctx, err)
|
service.Error(ctx, err)
|
||||||
return
|
return
|
||||||
|
|||||||
@ -2,12 +2,23 @@ package cast
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"encoding/json"
|
||||||
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"fonchain-fiee/cmd/config"
|
||||||
|
"fonchain-fiee/pkg/service/upload"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
"time"
|
||||||
|
|
||||||
"fonchain-fiee/api/cast"
|
"fonchain-fiee/api/cast"
|
||||||
|
modelCast "fonchain-fiee/pkg/model/cast"
|
||||||
"fonchain-fiee/pkg/model/login"
|
"fonchain-fiee/pkg/model/login"
|
||||||
"fonchain-fiee/pkg/service"
|
"fonchain-fiee/pkg/service"
|
||||||
|
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
|
"github.com/xuri/excelize/v2"
|
||||||
|
"go.uber.org/zap"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TaskList(ctx *gin.Context) {
|
func TaskList(ctx *gin.Context) {
|
||||||
@ -42,5 +53,148 @@ func DeleteTasK(ctx *gin.Context) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
service.Success(ctx, resp)
|
service.Success(ctx, resp)
|
||||||
|
}
|
||||||
|
|
||||||
|
func DownloadTaskFile(ctx *gin.Context) {
|
||||||
|
var req *cast.GetTaskListReq
|
||||||
|
var err error
|
||||||
|
if err = ctx.ShouldBind(&req); err != nil {
|
||||||
|
service.Error(ctx, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
resp, err := service.CastProvider.GetTaskList(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
service.Error(ctx, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if resp == nil || resp.Data == nil {
|
||||||
|
service.Error(ctx, errors.New("没有此任务"))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var taskInfo modelCast.PublishTaskDto
|
||||||
|
if resp.Data.ExtraData != "" {
|
||||||
|
_ = json.Unmarshal([]byte(resp.Data.ExtraData), &taskInfo)
|
||||||
|
}
|
||||||
|
exportUrl, err := PublishTaskExcel(taskInfo.WorkUuids, false, resp.Data.Action)
|
||||||
|
if err != nil {
|
||||||
|
service.Error(ctx, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
service.Success(ctx, gin.H{
|
||||||
|
"url": exportUrl,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func PublishTaskExcel(workUuids []string, uploadOss bool, action string) (string, error) {
|
||||||
|
// 创建Excel文件
|
||||||
|
f := excelize.NewFile()
|
||||||
|
sheetName := "Sheet1"
|
||||||
|
f.SetSheetName("Sheet1", sheetName)
|
||||||
|
// 设置表头
|
||||||
|
headers := []interface{}{
|
||||||
|
"艺人编号", "艺人姓名", "内容类型", "内容标题",
|
||||||
|
"执行结果", "TIKTOK", "YOUTUBE", "INS", "DM", "BULESKY",
|
||||||
|
}
|
||||||
|
sw, err := f.NewStreamWriter(sheetName)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if err = sw.SetRow("A1", headers); err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
// 遍历所有作品,收集数据
|
||||||
|
rowIndex := 2
|
||||||
|
for _, workUuid := range workUuids {
|
||||||
|
var workResp *cast.WorkDetailResp
|
||||||
|
workResp, err = service.CastProvider.WorkDetail(context.Background(), &cast.WorkDetailReq{WorkUuid: workUuid})
|
||||||
|
if err != nil {
|
||||||
|
continue // 如果某个作品获取失败,跳过继续处理其他作品
|
||||||
|
}
|
||||||
|
// 内容类型
|
||||||
|
contentType := ""
|
||||||
|
if workResp.WorkCategory == 1 {
|
||||||
|
contentType = "图文"
|
||||||
|
} else if workResp.WorkCategory == 2 {
|
||||||
|
contentType = "视频"
|
||||||
|
}
|
||||||
|
// 执行结果
|
||||||
|
executionResult := modelCast.WorkStatusMM[int(workResp.WorkStatus)]
|
||||||
|
tiktokStatus := ""
|
||||||
|
youtubeStatus := ""
|
||||||
|
insStatus := ""
|
||||||
|
dmStatus := ""
|
||||||
|
blueskyStatus := ""
|
||||||
|
|
||||||
|
// 获取平台信息和艺人姓名
|
||||||
|
artistName := ""
|
||||||
|
var infoResp *cast.WorkInfoResp
|
||||||
|
infoResp, err = service.CastProvider.WorkInfo(context.Background(), &cast.WorkInfoReq{WorkUuid: workUuid})
|
||||||
|
if err == nil && infoResp != nil {
|
||||||
|
artistName = infoResp.ArtistName
|
||||||
|
if infoResp.PlatformInfoData != nil {
|
||||||
|
for _, platform := range infoResp.PlatformInfoData {
|
||||||
|
statusText := modelCast.PlatformPublishStatusMM[platform.PublishMediaStatus]
|
||||||
|
switch cast.PlatformIDENUM(platform.PlatformID) {
|
||||||
|
case cast.PlatformIDENUM_TIKTOK:
|
||||||
|
tiktokStatus = statusText
|
||||||
|
case cast.PlatformIDENUM_YOUTUBE:
|
||||||
|
youtubeStatus = statusText
|
||||||
|
case cast.PlatformIDENUM_INS:
|
||||||
|
insStatus = statusText
|
||||||
|
case cast.PlatformIDENUM_DM:
|
||||||
|
dmStatus = statusText
|
||||||
|
case cast.PlatformIDENUM_BULESKY:
|
||||||
|
blueskyStatus = statusText
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
row := []interface{}{
|
||||||
|
workResp.ArtistSubNum,
|
||||||
|
artistName,
|
||||||
|
contentType,
|
||||||
|
workResp.Title,
|
||||||
|
executionResult,
|
||||||
|
tiktokStatus,
|
||||||
|
youtubeStatus,
|
||||||
|
insStatus,
|
||||||
|
dmStatus,
|
||||||
|
blueskyStatus,
|
||||||
|
}
|
||||||
|
cell, _ := excelize.CoordinatesToCellName(1, rowIndex)
|
||||||
|
if err = sw.SetRow(cell, row); err != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
rowIndex++
|
||||||
|
}
|
||||||
|
if err = sw.Flush(); err != nil {
|
||||||
|
zap.L().Error("PublishTaskExcel Flush err", zap.Error(err))
|
||||||
|
return "", errors.New("生成Excel文件失败")
|
||||||
|
}
|
||||||
|
tempDir := "./runtime/task"
|
||||||
|
if _, err = os.Stat(tempDir); os.IsNotExist(err) {
|
||||||
|
if err = os.MkdirAll(tempDir, 0755); err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TaskActionName, ok := modelCast.TaskActionName[action]
|
||||||
|
if !ok {
|
||||||
|
TaskActionName = "未知任务"
|
||||||
|
}
|
||||||
|
filename := fmt.Sprintf("%s_%s.xlsx", TaskActionName, time.Now().Format("20060102150405"))
|
||||||
|
filePath := tempDir + "/" + filename
|
||||||
|
var exportUrl string = fmt.Sprintf("%s/api/fiee/static/%s", config.AppConfig.System.FieeHost, strings.Replace(filePath, "./runtime/", "", 1))
|
||||||
|
if err = f.SaveAs(filePath); err != nil {
|
||||||
|
zap.L().Error("PublishTaskExcel SaveAs err", zap.Error(err))
|
||||||
|
return "", errors.New("保存Excel文件失败")
|
||||||
|
}
|
||||||
|
if uploadOss {
|
||||||
|
// 上传到阿里云
|
||||||
|
exportUrl, err = upload.PutBos(filePath, "excel", true)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return exportUrl, nil
|
||||||
|
}
|
||||||
|
|||||||
@ -16,6 +16,10 @@ import (
|
|||||||
|
|
||||||
func Test(ctx *gin.Context) {
|
func Test(ctx *gin.Context) {
|
||||||
action := ctx.PostForm("action")
|
action := ctx.PostForm("action")
|
||||||
|
if action == "" {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
if action == "getPost" {
|
if action == "getPost" {
|
||||||
id := ctx.PostForm("id")
|
id := ctx.PostForm("id")
|
||||||
profileKey := ctx.PostForm("profileKey")
|
profileKey := ctx.PostForm("profileKey")
|
||||||
@ -70,19 +74,6 @@ func Test(ctx *gin.Context) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if action == "" {
|
|
||||||
resp, err := service.CastProvider.WorkList(context.Background(), &cast.WorkListReq{
|
|
||||||
Page: 1,
|
|
||||||
PageSize: 1000,
|
|
||||||
SubmitTimeMonths: []string{"2026-01", "2025-12"},
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
service.Error(ctx, err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
service.Success(ctx, resp)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
if action == "getProfile" {
|
if action == "getProfile" {
|
||||||
//profileKey := ctx.PostForm("profileKey")
|
//profileKey := ctx.PostForm("profileKey")
|
||||||
resp, err := service.AyrshareProvider.GetProfiles(context.Background(), &aryshare.GetProfilesRequest{
|
resp, err := service.AyrshareProvider.GetProfiles(context.Background(), &aryshare.GetProfilesRequest{
|
||||||
@ -166,6 +157,16 @@ func Test(ctx *gin.Context) {
|
|||||||
service.Success(ctx, "ok")
|
service.Success(ctx, "ok")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if action == "RefreshWorkList" {
|
||||||
|
resp, err := service.CastProvider.RefreshWorkList(context.Background(), &cast.RefreshWorkListReq{PublishStatus: 1})
|
||||||
|
if err != nil {
|
||||||
|
service.Error(ctx, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
service.Success(ctx, resp)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
service.Success(ctx, "unknow")
|
service.Success(ctx, "unknow")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,6 +21,7 @@ import (
|
|||||||
"fonchain-fiee/pkg/service/check"
|
"fonchain-fiee/pkg/service/check"
|
||||||
"fonchain-fiee/pkg/service/upload"
|
"fonchain-fiee/pkg/service/upload"
|
||||||
"fonchain-fiee/pkg/utils"
|
"fonchain-fiee/pkg/utils"
|
||||||
|
utilsImg "fonchain-fiee/pkg/utils/img"
|
||||||
"fonchain-fiee/pkg/utils/stime"
|
"fonchain-fiee/pkg/utils/stime"
|
||||||
"image"
|
"image"
|
||||||
"image/jpeg"
|
"image/jpeg"
|
||||||
@ -109,11 +110,10 @@ func UpdateWorkImageCore(ctx *gin.Context, req *cast.UpdateWorkImageReq) (*cast.
|
|||||||
ID: artistId,
|
ID: artistId,
|
||||||
Domain: "app",
|
Domain: "app",
|
||||||
})
|
})
|
||||||
zap.L().Info("UpdateWorkImage infoResp", zap.Any("infoResp", infoResp))
|
zap.L().Info("UpdateWorkImage infoResp1", zap.Any("infoResp", infoResp))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
req.ArtistName = infoResp.Name
|
req.ArtistName = infoResp.Name
|
||||||
req.ArtistPhone = infoResp.TelNum
|
req.ArtistPhone = infoResp.TelNum
|
||||||
req.ArtistPhoneAreaCode = infoResp.TelAreaCode
|
req.ArtistPhoneAreaCode = infoResp.TelAreaCode
|
||||||
@ -127,6 +127,7 @@ func UpdateWorkImageCore(ctx *gin.Context, req *cast.UpdateWorkImageReq) (*cast.
|
|||||||
resp, err := service.CastProvider.UpdateWorkImage(newCtx, req)
|
resp, err := service.CastProvider.UpdateWorkImage(newCtx, req)
|
||||||
zap.L().Info("UpdateWorkImage resp", zap.Any("resp", resp))
|
zap.L().Info("UpdateWorkImage resp", zap.Any("resp", resp))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
zap.L().Error("UpdateWorkImage err", zap.Error(err))
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
return resp, nil
|
return resp, nil
|
||||||
@ -434,10 +435,26 @@ func Publish(ctx *gin.Context) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
newCtx := NewCtxWithUserInfo(ctx)
|
newCtx := NewCtxWithUserInfo(ctx)
|
||||||
|
loginInfo := login.GetUserInfoFromC(ctx)
|
||||||
|
var extraBytes []byte
|
||||||
|
extraBytes, _ = json.Marshal(req)
|
||||||
|
_, err = service.CastProvider.UpsertTaskList(newCtx, &cast.UpsertTaskListReq{
|
||||||
|
Action: "publishBatch1",
|
||||||
|
Url: "",
|
||||||
|
Status: 1,
|
||||||
|
OperatorID: fmt.Sprint(loginInfo.ID),
|
||||||
|
OperatorName: loginInfo.Name,
|
||||||
|
ExtraData: string(extraBytes),
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
service.Error(ctx, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
if err = PublishWork(newCtx, req); err != nil {
|
if err = PublishWork(newCtx, req); err != nil {
|
||||||
service.Error(ctx, err)
|
service.Error(ctx, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
service.Success(ctx, req)
|
service.Success(ctx, req)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -445,7 +462,6 @@ func Publish(ctx *gin.Context) {
|
|||||||
// PublishWork 统一发布
|
// PublishWork 统一发布
|
||||||
func PublishWork(ctx context.Context, req *cast.PublishReq) error {
|
func PublishWork(ctx context.Context, req *cast.PublishReq) error {
|
||||||
var (
|
var (
|
||||||
wg sync.WaitGroup
|
|
||||||
errsMu sync.Mutex
|
errsMu sync.Mutex
|
||||||
errs []error
|
errs []error
|
||||||
)
|
)
|
||||||
@ -453,20 +469,45 @@ func PublishWork(ctx context.Context, req *cast.PublishReq) error {
|
|||||||
if len(req.WorkUuids) == 0 {
|
if len(req.WorkUuids) == 0 {
|
||||||
return errors.New("请选择作品")
|
return errors.New("请选择作品")
|
||||||
}
|
}
|
||||||
jobs := make(chan string, len(req.WorkUuids))
|
|
||||||
// 添加日志
|
// 添加日志
|
||||||
zap.L().Info("开始发布作品", zap.Int("总数", len(req.WorkUuids)))
|
zap.L().Info("开始发布作品", zap.Int("总数", len(req.WorkUuids)))
|
||||||
startTime := time.Now().Unix()
|
startTime := time.Now().Unix()
|
||||||
workerCount := 10
|
|
||||||
if len(req.WorkUuids) < workerCount {
|
// 每批次协程数量设为8
|
||||||
workerCount = len(req.WorkUuids) // 避免创建多余的协程
|
workerCount := 8
|
||||||
|
batchSize := workerCount // 每批处理8个任务
|
||||||
|
|
||||||
|
// 分批处理
|
||||||
|
for batchStart := 0; batchStart < len(req.WorkUuids); batchStart += batchSize {
|
||||||
|
batchEnd := batchStart + batchSize
|
||||||
|
if batchEnd > len(req.WorkUuids) {
|
||||||
|
batchEnd = len(req.WorkUuids)
|
||||||
}
|
}
|
||||||
for i := 0; i < workerCount; i++ {
|
|
||||||
|
currentBatch := req.WorkUuids[batchStart:batchEnd]
|
||||||
|
batchNum := batchStart/batchSize + 1
|
||||||
|
totalBatches := (len(req.WorkUuids) + batchSize - 1) / batchSize
|
||||||
|
|
||||||
|
zap.L().Info("开始处理批次",
|
||||||
|
zap.Int("批次", batchNum),
|
||||||
|
zap.Int("总批次", totalBatches),
|
||||||
|
zap.Int("本批数量", len(currentBatch)))
|
||||||
|
|
||||||
|
// 处理当前批次
|
||||||
|
var wg sync.WaitGroup
|
||||||
|
jobs := make(chan string, len(currentBatch))
|
||||||
|
|
||||||
|
currentWorkerCount := workerCount
|
||||||
|
if len(currentBatch) < workerCount {
|
||||||
|
currentWorkerCount = len(currentBatch) // 避免创建多余的协程
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < currentWorkerCount; i++ {
|
||||||
wg.Add(1)
|
wg.Add(1)
|
||||||
go func() {
|
go func() {
|
||||||
defer wg.Done()
|
defer wg.Done()
|
||||||
for workUuid := range jobs {
|
for workUuid := range jobs {
|
||||||
if err := PostAS(workUuid); err != nil {
|
if err := PostAS(ctx, workUuid); err != nil {
|
||||||
errsMu.Lock()
|
errsMu.Lock()
|
||||||
errs = append(errs, err)
|
errs = append(errs, err)
|
||||||
errsMu.Unlock()
|
errsMu.Unlock()
|
||||||
@ -474,11 +515,23 @@ func PublishWork(ctx context.Context, req *cast.PublishReq) error {
|
|||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
}
|
}
|
||||||
for _, workUuid := range req.WorkUuids {
|
|
||||||
|
for _, workUuid := range currentBatch {
|
||||||
jobs <- workUuid
|
jobs <- workUuid
|
||||||
}
|
}
|
||||||
close(jobs)
|
close(jobs)
|
||||||
wg.Wait()
|
wg.Wait()
|
||||||
|
|
||||||
|
zap.L().Info("批次处理完成", zap.Int("批次", batchNum))
|
||||||
|
|
||||||
|
// 如果不是最后一批,等待10-15秒再进行下一批
|
||||||
|
if batchEnd < len(req.WorkUuids) {
|
||||||
|
waitTime := 10 + time.Duration(time.Now().UnixNano()%6) // 随机10-15秒
|
||||||
|
zap.L().Info("等待后再处理下一批", zap.Int64("等待秒数", int64(waitTime)))
|
||||||
|
time.Sleep(waitTime * time.Second)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// 统计结果
|
// 统计结果
|
||||||
successCount := len(req.WorkUuids) - len(errs)
|
successCount := len(req.WorkUuids) - len(errs)
|
||||||
zap.L().Info("发布完成",
|
zap.L().Info("发布完成",
|
||||||
@ -493,9 +546,9 @@ func PublishWork(ctx context.Context, req *cast.PublishReq) error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func PostAS(workUuid string) error {
|
func PostAS(ctx context.Context, workUuid string) error {
|
||||||
var err error
|
var err error
|
||||||
_, err = service.CastProvider.Publish(context.Background(), &cast.PublishReq{WorkUuids: []string{workUuid}})
|
_, err = service.CastProvider.Publish(ctx, &cast.PublishReq{WorkUuids: []string{workUuid}})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
zap.L().Error("Publish err", zap.String("workUuid", workUuid), zap.Error(err))
|
zap.L().Error("Publish err", zap.String("workUuid", workUuid), zap.Error(err))
|
||||||
return err
|
return err
|
||||||
@ -528,7 +581,12 @@ func PostAS(workUuid string) error {
|
|||||||
if workDetail.WorkCategory == 1 {
|
if workDetail.WorkCategory == 1 {
|
||||||
isVideo = false
|
isVideo = false
|
||||||
// 先用服务器上的文件,不上传到第三方
|
// 先用服务器上的文件,不上传到第三方
|
||||||
|
//mediaUrls = workDetail.Images
|
||||||
|
mediaUrls, err = ProcessImg(workDetail.Images)
|
||||||
|
if err != nil {
|
||||||
mediaUrls = workDetail.Images
|
mediaUrls = workDetail.Images
|
||||||
|
err = nil
|
||||||
|
}
|
||||||
/* for _, imageUrl := range workDetail.Images {
|
/* for _, imageUrl := range workDetail.Images {
|
||||||
urlResp, err = UploadMediaByURL(context.Background(), imageUrl, "", "")
|
urlResp, err = UploadMediaByURL(context.Background(), imageUrl, "", "")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -544,6 +602,10 @@ func PostAS(workUuid string) error {
|
|||||||
isVideo = true
|
isVideo = true
|
||||||
mediaUrls = []string{workDetail.VideoUrl}
|
mediaUrls = []string{workDetail.VideoUrl}
|
||||||
coverUrl = workDetail.CoverUrl
|
coverUrl = workDetail.CoverUrl
|
||||||
|
coverUrls, _ := ProcessImg([]string{workDetail.CoverUrl})
|
||||||
|
if len(coverUrls) > 0 {
|
||||||
|
coverUrl = coverUrls[0]
|
||||||
|
}
|
||||||
// 先用服务器上的文件,不上传到第三方
|
// 先用服务器上的文件,不上传到第三方
|
||||||
/*urlResp, err = UploadMediaByURL(context.Background(), workDetail.VideoUrl, "", "")
|
/*urlResp, err = UploadMediaByURL(context.Background(), workDetail.VideoUrl, "", "")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -686,7 +748,7 @@ func PostAS(workUuid string) error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: _err.Error(),
|
PublishResp: _err.Error(),
|
||||||
PublishMediaId: "",
|
PublishMediaId: "",
|
||||||
PublishStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
})
|
})
|
||||||
zap.L().Info("UpdateWorkPlatformInfo", zap.Any("infoReq", infoReq))
|
zap.L().Info("UpdateWorkPlatformInfo", zap.Any("infoReq", infoReq))
|
||||||
@ -747,7 +809,7 @@ func PostAS(workUuid string) error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: string(postBytes),
|
PublishResp: string(postBytes),
|
||||||
PublishMediaId: postResp.Posts[0].Id,
|
PublishMediaId: postResp.Posts[0].Id,
|
||||||
PublishStatus: publishStatus,
|
PublishMediaStatus: publishStatus,
|
||||||
Remark: string(postData),
|
Remark: string(postData),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@ -806,11 +868,27 @@ func RePublish(ctx *gin.Context) {
|
|||||||
service.Error(ctx, err)
|
service.Error(ctx, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
fmt.Println(resp)
|
loginInfo := login.GetUserInfoFromC(ctx)
|
||||||
|
var extraBytes []byte
|
||||||
|
extraBytes, _ = json.Marshal(req)
|
||||||
|
_, err = service.CastProvider.UpsertTaskList(newCtx, &cast.UpsertTaskListReq{
|
||||||
|
Action: "publishBatch2",
|
||||||
|
Url: "",
|
||||||
|
Status: 1,
|
||||||
|
OperatorID: fmt.Sprint(loginInfo.ID),
|
||||||
|
OperatorName: loginInfo.Name,
|
||||||
|
ExtraData: string(extraBytes),
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("RePublish UpsertTaskList failed", zap.Error(err))
|
||||||
|
service.Error(ctx, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
if err = PublishWork(newCtx, &cast.PublishReq{WorkUuids: resp.WorkUuids}); err != nil {
|
if err = PublishWork(newCtx, &cast.PublishReq{WorkUuids: resp.WorkUuids}); err != nil {
|
||||||
service.Error(ctx, err)
|
service.Error(ctx, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
service.Success(ctx, req)
|
service.Success(ctx, req)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -1564,9 +1642,11 @@ func ImportWorkBatch(ctx *gin.Context) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
service.CastProvider.UpsertTaskList(context.Background(), &cast.UpsertTaskListReq{
|
urlResult, _ = upload.PutBos(excelPath, "excel", true)
|
||||||
|
_, _ = service.CastProvider.UpsertTaskList(context.Background(), &cast.UpsertTaskListReq{
|
||||||
Uuid: taskResp.Uuid,
|
Uuid: taskResp.Uuid,
|
||||||
Status: 3,
|
Status: 3,
|
||||||
|
Url: urlResult,
|
||||||
})
|
})
|
||||||
service.Success(ctx, map[string]interface{}{
|
service.Success(ctx, map[string]interface{}{
|
||||||
"successCount": resp.SuccessCount,
|
"successCount": resp.SuccessCount,
|
||||||
@ -1600,6 +1680,14 @@ func RefreshPublish() error {
|
|||||||
}
|
}
|
||||||
for _, platformInfo := range workInfo.PlatformInfoData {
|
for _, platformInfo := range workInfo.PlatformInfoData {
|
||||||
if platformInfo.PublishMediaID == "" {
|
if platformInfo.PublishMediaID == "" {
|
||||||
|
var infoReq = &cast.UpdateWorkPlatformInfoReq{
|
||||||
|
PlatformInfoData: make([]*cast.PlatformInfo, 0),
|
||||||
|
}
|
||||||
|
infoReq.PlatformInfoData = append(infoReq.PlatformInfoData, &cast.PlatformInfo{
|
||||||
|
WorkUuid: workInfo.WorkUuid,
|
||||||
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_NO,
|
||||||
|
})
|
||||||
|
_, _ = service.CastProvider.UpdateWorkPlatformInfo(context.Background(), infoReq)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
var infoReq = &cast.UpdateWorkPlatformInfoReq{
|
var infoReq = &cast.UpdateWorkPlatformInfoReq{
|
||||||
@ -1618,7 +1706,7 @@ func RefreshPublish() error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: err.Error(),
|
PublishResp: err.Error(),
|
||||||
PublishMediaId: platformInfo.PublishMediaID,
|
PublishMediaId: platformInfo.PublishMediaID,
|
||||||
PublishStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
PlatformUuid: platformInfo.PlatformUuid,
|
PlatformUuid: platformInfo.PlatformUuid,
|
||||||
})
|
})
|
||||||
@ -1635,7 +1723,7 @@ func RefreshPublish() error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: string(dmData),
|
PublishResp: string(dmData),
|
||||||
PublishMediaId: platformInfo.PublishMediaID,
|
PublishMediaId: platformInfo.PublishMediaID,
|
||||||
PublishStatus: cast.PublishStatusENUM_PublishMediaStatus_DONE,
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_DONE,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
PlatformUuid: platformInfo.PlatformUuid,
|
PlatformUuid: platformInfo.PlatformUuid,
|
||||||
})
|
})
|
||||||
@ -1688,7 +1776,7 @@ func RefreshPublish() error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: _err.Error(),
|
PublishResp: _err.Error(),
|
||||||
PublishMediaId: platformInfo.PublishMediaID,
|
PublishMediaId: platformInfo.PublishMediaID,
|
||||||
PublishStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_EXCEPTION,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
PlatformUuid: platformInfo.PlatformUuid,
|
PlatformUuid: platformInfo.PlatformUuid,
|
||||||
})
|
})
|
||||||
@ -1708,7 +1796,7 @@ func RefreshPublish() error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: string(postBytes),
|
PublishResp: string(postBytes),
|
||||||
PublishMediaId: platformInfo.PublishMediaID,
|
PublishMediaId: platformInfo.PublishMediaID,
|
||||||
PublishStatus: cast.PublishStatusENUM_PublishMediaStatus_FAIL,
|
PublishMediaStatus: cast.PublishStatusENUM_PublishMediaStatus_FAIL,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
PlatformUuid: platformInfo.PlatformUuid,
|
PlatformUuid: platformInfo.PlatformUuid,
|
||||||
})
|
})
|
||||||
@ -1738,7 +1826,7 @@ func RefreshPublish() error {
|
|||||||
PublishType: 2,
|
PublishType: 2,
|
||||||
PublishResp: string(postBytes),
|
PublishResp: string(postBytes),
|
||||||
PublishMediaId: platformInfo.PublishMediaID,
|
PublishMediaId: platformInfo.PublishMediaID,
|
||||||
PublishStatus: publishStatus,
|
PublishMediaStatus: publishStatus,
|
||||||
Remark: "",
|
Remark: "",
|
||||||
PlatformUuid: platformInfo.PlatformUuid,
|
PlatformUuid: platformInfo.PlatformUuid,
|
||||||
})
|
})
|
||||||
@ -1799,3 +1887,38 @@ func checkAndReuploadImage(imageUrl string, mediaType string) (string, error) {
|
|||||||
}
|
}
|
||||||
return compressUrl, nil
|
return compressUrl, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func ProcessImg(imgs []string) ([]string, error) {
|
||||||
|
var newImgs []string
|
||||||
|
for _, img := range imgs {
|
||||||
|
newPath, err := utilsImg.ProcessFromURL(
|
||||||
|
img,
|
||||||
|
utilsImg.Options{
|
||||||
|
TargetWidth: 1024,
|
||||||
|
TargetHeight: 1024,
|
||||||
|
MaxSizeMB: 1, // 提高到 2MB,对于 1024x1024 更合理
|
||||||
|
Mode: utilsImg.ResizeModePad, // 等比缩放+留白
|
||||||
|
OutputDir: "./runtime/tmp/images/processed",
|
||||||
|
MinQuality: 20, // 最低质量阈值
|
||||||
|
MaxRetries: 15, // 最大尝试次数
|
||||||
|
AllowResolutionReduction: true, // 允许降低分辨率
|
||||||
|
ForceJPEG: true, // 强制转换为 JPEG 格式
|
||||||
|
},
|
||||||
|
)
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("processImg err", zap.Error(err), zap.Any("img", img))
|
||||||
|
newImgs = append(newImgs, img)
|
||||||
|
err = nil
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
exportUrl, err := upload.PutBos(newPath, "fieework", true)
|
||||||
|
if err != nil {
|
||||||
|
zap.L().Error("upload.PutBos err", zap.Error(err), zap.Any("img", img))
|
||||||
|
newImgs = append(newImgs, img)
|
||||||
|
err = nil
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
newImgs = append(newImgs, exportUrl)
|
||||||
|
}
|
||||||
|
return newImgs, nil
|
||||||
|
}
|
||||||
|
|||||||
555
pkg/utils/img/imageproc.go
Normal file
555
pkg/utils/img/imageproc.go
Normal file
@ -0,0 +1,555 @@
|
|||||||
|
package img
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"context"
|
||||||
|
"crypto/sha256"
|
||||||
|
"encoding/hex"
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"image"
|
||||||
|
"image/color"
|
||||||
|
"image/gif"
|
||||||
|
"image/jpeg"
|
||||||
|
"image/png"
|
||||||
|
"io"
|
||||||
|
"net/http"
|
||||||
|
"net/url"
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
"strings"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/disintegration/imaging"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ResizeMode controls how the source image is mapped to the target WxH.
|
||||||
|
//
|
||||||
|
// - ResizeModeFit: contain (keep aspect), no cropping; resulting image may be smaller than WxH
|
||||||
|
// - ResizeModeFill: cover + crop (center crop) to exactly WxH
|
||||||
|
// - ResizeModePad: keep aspect + pad (letterbox) to exactly WxH (no crop, no stretch)
|
||||||
|
//
|
||||||
|
// If you only pass a single dimension (e.g. W>0, H=0), Fit will keep aspect.
|
||||||
|
// Fill/Pad requires both W and H.
|
||||||
|
//
|
||||||
|
// Note: GIF input will be processed as a single frame (first frame).
|
||||||
|
// If you need animated GIF support, we can extend this later.
|
||||||
|
type ResizeMode string
|
||||||
|
|
||||||
|
const (
|
||||||
|
ResizeModeFit ResizeMode = "fit"
|
||||||
|
ResizeModeFill ResizeMode = "fill"
|
||||||
|
// ResizeModePad keeps aspect ratio (no crop, no stretch) and pads to exactly WxH.
|
||||||
|
// Typical use: 16:9 -> 1024x1024 with white/black bars.
|
||||||
|
ResizeModePad ResizeMode = "pad"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Options struct {
|
||||||
|
TargetWidth int
|
||||||
|
TargetHeight int
|
||||||
|
MaxSizeMB float64
|
||||||
|
|
||||||
|
Mode ResizeMode
|
||||||
|
|
||||||
|
// PadColor is used only when Mode == ResizeModePad.
|
||||||
|
// Default: white.
|
||||||
|
PadColor color.Color
|
||||||
|
|
||||||
|
// OutputDir is where the processed image will be written.
|
||||||
|
// Default: ./runtime/tmp/images/processed
|
||||||
|
OutputDir string
|
||||||
|
|
||||||
|
// Timeout controls total download time.
|
||||||
|
// Default: 30s.
|
||||||
|
Timeout time.Duration
|
||||||
|
|
||||||
|
// MaxDownloadMB caps download size to protect memory/disk.
|
||||||
|
// Default: max( maxSizeMB*6, 30MB ).
|
||||||
|
MaxDownloadMB float64
|
||||||
|
|
||||||
|
// MinQuality is the minimum JPEG quality to try (1-100).
|
||||||
|
// Default: 10. If compression still can't meet MaxSizeMB, returns error.
|
||||||
|
MinQuality int
|
||||||
|
|
||||||
|
// MaxRetries controls how many quality adjustments to attempt.
|
||||||
|
// Default: 15.
|
||||||
|
MaxRetries int
|
||||||
|
|
||||||
|
// AllowResolutionReduction allows reducing resolution further if compression fails.
|
||||||
|
// Default: false.
|
||||||
|
AllowResolutionReduction bool
|
||||||
|
|
||||||
|
// ForceJPEG forces output to JPEG format even if input is PNG/GIF/etc.
|
||||||
|
// If image has alpha channel, it will be flattened to white background.
|
||||||
|
// Default: false.
|
||||||
|
ForceJPEG bool
|
||||||
|
}
|
||||||
|
|
||||||
|
// ProcessFromURL downloads an image from imgURL, resizes it, compresses it to <= MaxSizeMB,
|
||||||
|
// and returns the local output path.
|
||||||
|
//
|
||||||
|
// Contract:
|
||||||
|
// - imgURL: http/https
|
||||||
|
// - TargetWidth/TargetHeight: pixels, >=0
|
||||||
|
// - MaxSizeMB: >0
|
||||||
|
// - returns: absolute or relative file path (depending on OutputDir), and error
|
||||||
|
func ProcessFromURL(imgURL string, opt Options) (string, error) {
|
||||||
|
if strings.TrimSpace(imgURL) == "" {
|
||||||
|
return "", errors.New("imgURL is empty")
|
||||||
|
}
|
||||||
|
u, err := url.Parse(imgURL)
|
||||||
|
if err != nil || (u.Scheme != "http" && u.Scheme != "https") {
|
||||||
|
return "", errors.New("imgURL must be http/https")
|
||||||
|
}
|
||||||
|
if opt.MaxSizeMB <= 0 {
|
||||||
|
return "", errors.New("MaxSizeMB must be > 0")
|
||||||
|
}
|
||||||
|
if opt.TargetWidth < 0 || opt.TargetHeight < 0 {
|
||||||
|
return "", errors.New("TargetWidth/TargetHeight must be >= 0")
|
||||||
|
}
|
||||||
|
if opt.TargetWidth == 0 && opt.TargetHeight == 0 {
|
||||||
|
return "", errors.New("TargetWidth and TargetHeight cannot both be 0")
|
||||||
|
}
|
||||||
|
if opt.Mode == "" {
|
||||||
|
opt.Mode = ResizeModeFit
|
||||||
|
}
|
||||||
|
if opt.Mode != ResizeModeFit && opt.Mode != ResizeModeFill && opt.Mode != ResizeModePad {
|
||||||
|
return "", errors.New("invalid resize Mode")
|
||||||
|
}
|
||||||
|
if (opt.Mode == ResizeModeFill || opt.Mode == ResizeModePad) && (opt.TargetWidth == 0 || opt.TargetHeight == 0) {
|
||||||
|
return "", errors.New("fill/pad mode requires both TargetWidth and TargetHeight")
|
||||||
|
}
|
||||||
|
if opt.Timeout <= 0 {
|
||||||
|
opt.Timeout = 30 * time.Second
|
||||||
|
}
|
||||||
|
if opt.OutputDir == "" {
|
||||||
|
opt.OutputDir = filepath.FromSlash("./runtime/tmp/images/processed")
|
||||||
|
}
|
||||||
|
if opt.MaxDownloadMB <= 0 {
|
||||||
|
opt.MaxDownloadMB = opt.MaxSizeMB * 6
|
||||||
|
if opt.MaxDownloadMB < 30 {
|
||||||
|
opt.MaxDownloadMB = 30
|
||||||
|
}
|
||||||
|
if opt.MaxDownloadMB > 200 {
|
||||||
|
opt.MaxDownloadMB = 200
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if opt.MinQuality <= 0 {
|
||||||
|
opt.MinQuality = 10
|
||||||
|
}
|
||||||
|
if opt.MinQuality > 100 {
|
||||||
|
opt.MinQuality = 100
|
||||||
|
}
|
||||||
|
if opt.MaxRetries <= 0 {
|
||||||
|
opt.MaxRetries = 15
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ensure output dir exists.
|
||||||
|
if err := os.MkdirAll(opt.OutputDir, os.ModePerm); err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx, cancel := context.WithTimeout(context.Background(), opt.Timeout)
|
||||||
|
defer cancel()
|
||||||
|
|
||||||
|
data, contentType, err := downloadWithLimit(ctx, imgURL, int64(opt.MaxDownloadMB*1024*1024))
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
img, fmtName, err := decodeImage(data, contentType)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if image already meets requirements
|
||||||
|
if alreadyMeetsRequirements(img, data, opt) {
|
||||||
|
return "", nil
|
||||||
|
}
|
||||||
|
|
||||||
|
img = applyResize(img, opt)
|
||||||
|
|
||||||
|
// Determine output format
|
||||||
|
outExt := ".jpg"
|
||||||
|
outFormat := "jpeg"
|
||||||
|
|
||||||
|
if opt.ForceJPEG {
|
||||||
|
// Force JPEG output, flatten alpha if needed
|
||||||
|
outFormat = "jpeg"
|
||||||
|
outExt = ".jpg"
|
||||||
|
if imageHasAlpha(img) {
|
||||||
|
img = flattenToWhite(img)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// Auto-detect: if image has alpha, output PNG; otherwise JPEG
|
||||||
|
hasAlpha := imageHasAlpha(img)
|
||||||
|
if hasAlpha {
|
||||||
|
outExt = ".png"
|
||||||
|
outFormat = "png"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create a stable file name based on url + options + content signature.
|
||||||
|
h := sha256.New()
|
||||||
|
h.Write([]byte(imgURL))
|
||||||
|
h.Write([]byte(fmt.Sprintf("|%d|%d|%f|%s|%s", opt.TargetWidth, opt.TargetHeight, opt.MaxSizeMB, opt.Mode, outFormat)))
|
||||||
|
h.Write(data[:minInt(len(data), 1024)])
|
||||||
|
name := hex.EncodeToString(h.Sum(nil))[:32] + outExt
|
||||||
|
outPath := filepath.Join(opt.OutputDir, name)
|
||||||
|
|
||||||
|
maxBytes := int64(opt.MaxSizeMB * 1024 * 1024)
|
||||||
|
encoded, err := encodeUnderSize(img, outFormat, maxBytes, opt.MinQuality, opt.MaxRetries)
|
||||||
|
if err != nil {
|
||||||
|
// Fallback: if PNG can't fit, try JPEG (dropping alpha with white background).
|
||||||
|
if outFormat == "png" {
|
||||||
|
flattened := flattenToWhite(img)
|
||||||
|
encoded, err = encodeUnderSize(flattened, "jpeg", maxBytes, opt.MinQuality, opt.MaxRetries)
|
||||||
|
if err == nil {
|
||||||
|
outPath = strings.TrimSuffix(outPath, filepath.Ext(outPath)) + ".jpg"
|
||||||
|
} else {
|
||||||
|
// If AllowResolutionReduction is true, try reducing resolution
|
||||||
|
if opt.AllowResolutionReduction {
|
||||||
|
return tryWithReducedResolution(img, opt, outPath, maxBytes)
|
||||||
|
}
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// If AllowResolutionReduction is true, try reducing resolution
|
||||||
|
if opt.AllowResolutionReduction {
|
||||||
|
return tryWithReducedResolution(img, opt, outPath, maxBytes)
|
||||||
|
}
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpPath := outPath + ".tmp"
|
||||||
|
if err := os.WriteFile(tmpPath, encoded, 0o644); err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if err := os.Rename(tmpPath, outPath); err != nil {
|
||||||
|
_ = os.Remove(tmpPath)
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
_ = fmtName // reserved for future behavior
|
||||||
|
return outPath, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func downloadWithLimit(ctx context.Context, imgURL string, maxBytes int64) ([]byte, string, error) {
|
||||||
|
req, err := http.NewRequestWithContext(ctx, http.MethodGet, imgURL, nil)
|
||||||
|
if err != nil {
|
||||||
|
return nil, "", err
|
||||||
|
}
|
||||||
|
// Reasonable defaults; could be overridden later.
|
||||||
|
req.Header.Set("User-Agent", "fonchain-tools/1.0")
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
resp, err := client.Do(req)
|
||||||
|
if err != nil {
|
||||||
|
return nil, "", err
|
||||||
|
}
|
||||||
|
defer func() { _ = resp.Body.Close() }()
|
||||||
|
|
||||||
|
if resp.StatusCode < 200 || resp.StatusCode >= 300 {
|
||||||
|
return nil, "", fmt.Errorf("download failed: %s", resp.Status)
|
||||||
|
}
|
||||||
|
if resp.ContentLength > 0 && resp.ContentLength > maxBytes {
|
||||||
|
return nil, "", fmt.Errorf("remote file too large: %d > %d", resp.ContentLength, maxBytes)
|
||||||
|
}
|
||||||
|
|
||||||
|
lr := &io.LimitedReader{R: resp.Body, N: maxBytes + 1}
|
||||||
|
b, err := io.ReadAll(lr)
|
||||||
|
if err != nil {
|
||||||
|
return nil, "", err
|
||||||
|
}
|
||||||
|
if int64(len(b)) > maxBytes {
|
||||||
|
return nil, "", fmt.Errorf("download exceeded limit: %d > %d", len(b), maxBytes)
|
||||||
|
}
|
||||||
|
return b, resp.Header.Get("Content-Type"), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func decodeImage(data []byte, contentType string) (image.Image, string, error) {
|
||||||
|
// Register gif (jpeg/png already registered) for Decode.
|
||||||
|
_ = gif.GIF{}
|
||||||
|
reader := bytes.NewReader(data)
|
||||||
|
img, fmtName, err := image.Decode(reader)
|
||||||
|
if err == nil {
|
||||||
|
return img, fmtName, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// Some servers set odd content-type; try simple sniff.
|
||||||
|
_ = contentType
|
||||||
|
return nil, "", fmt.Errorf("decode image failed: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
func applyResize(img image.Image, opt Options) image.Image {
|
||||||
|
w := opt.TargetWidth
|
||||||
|
h := opt.TargetHeight
|
||||||
|
|
||||||
|
srcW := img.Bounds().Dx()
|
||||||
|
srcH := img.Bounds().Dy()
|
||||||
|
if srcW <= 0 || srcH <= 0 {
|
||||||
|
return img
|
||||||
|
}
|
||||||
|
|
||||||
|
switch opt.Mode {
|
||||||
|
case ResizeModeFill:
|
||||||
|
return imaging.Fill(img, w, h, imaging.Center, imaging.Lanczos)
|
||||||
|
case ResizeModeFit:
|
||||||
|
// If only one dimension is provided, keep aspect.
|
||||||
|
if w == 0 {
|
||||||
|
w = int(float64(srcW) * (float64(h) / float64(srcH)))
|
||||||
|
if w < 1 {
|
||||||
|
w = 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if h == 0 {
|
||||||
|
h = int(float64(srcH) * (float64(w) / float64(srcW)))
|
||||||
|
if h < 1 {
|
||||||
|
h = 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// imaging.Fit ensures the result fits within w,h without cropping.
|
||||||
|
return imaging.Fit(img, w, h, imaging.Lanczos)
|
||||||
|
case ResizeModePad:
|
||||||
|
bg := opt.PadColor
|
||||||
|
if bg == nil {
|
||||||
|
bg = color.White
|
||||||
|
}
|
||||||
|
// First, fit within WxH (no crop).
|
||||||
|
fitted := imaging.Fit(img, w, h, imaging.Lanczos)
|
||||||
|
// Then, paste centered onto WxH canvas.
|
||||||
|
canvas := imaging.New(w, h, bg)
|
||||||
|
x := (w - fitted.Bounds().Dx()) / 2
|
||||||
|
y := (h - fitted.Bounds().Dy()) / 2
|
||||||
|
return imaging.Paste(canvas, fitted, image.Pt(x, y))
|
||||||
|
default:
|
||||||
|
return img
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func encodeUnderSize(img image.Image, format string, maxBytes int64, minQuality, maxRetries int) ([]byte, error) {
|
||||||
|
if maxBytes <= 0 {
|
||||||
|
return nil, errors.New("maxBytes must be > 0")
|
||||||
|
}
|
||||||
|
|
||||||
|
switch format {
|
||||||
|
case "jpeg":
|
||||||
|
// Binary search quality.
|
||||||
|
lo, hi := minQuality, 92
|
||||||
|
var best []byte
|
||||||
|
iterations := 0
|
||||||
|
maxIterations := maxInt(8, maxRetries/2)
|
||||||
|
|
||||||
|
for i := 0; i < maxIterations && lo <= hi; i++ {
|
||||||
|
iterations++
|
||||||
|
q := (lo + hi) / 2
|
||||||
|
b, err := encodeJPEG(img, q)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if int64(len(b)) <= maxBytes {
|
||||||
|
best = b
|
||||||
|
lo = q + 1
|
||||||
|
} else {
|
||||||
|
hi = q - 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if best != nil {
|
||||||
|
return best, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try more aggressive qualities from minQuality down to 1
|
||||||
|
qualities := []int{}
|
||||||
|
for q := minQuality; q >= 1; q -= 5 {
|
||||||
|
qualities = append(qualities, q)
|
||||||
|
}
|
||||||
|
// Ensure we try the lowest qualities
|
||||||
|
if minQuality > 3 {
|
||||||
|
qualities = append(qualities, 3, 1)
|
||||||
|
}
|
||||||
|
|
||||||
|
var lastSize int64
|
||||||
|
for _, q := range qualities {
|
||||||
|
if iterations >= maxRetries {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
iterations++
|
||||||
|
b, err := encodeJPEG(img, q)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
lastSize = int64(len(b))
|
||||||
|
if lastSize <= maxBytes {
|
||||||
|
return b, nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
sizeMB := float64(lastSize) / (1024 * 1024)
|
||||||
|
targetMB := float64(maxBytes) / (1024 * 1024)
|
||||||
|
return nil, fmt.Errorf("cannot compress to %.2fMB (best: %.2fMB at quality %d after %d attempts). Consider increasing MaxSizeMB or enabling AllowResolutionReduction",
|
||||||
|
targetMB, sizeMB, minQuality, iterations)
|
||||||
|
|
||||||
|
case "png":
|
||||||
|
// PNG size depends heavily on content; try best compression.
|
||||||
|
b, err := encodePNG(img, png.BestCompression)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if int64(len(b)) <= maxBytes {
|
||||||
|
return b, nil
|
||||||
|
}
|
||||||
|
sizeMB := float64(len(b)) / (1024 * 1024)
|
||||||
|
targetMB := float64(maxBytes) / (1024 * 1024)
|
||||||
|
return nil, fmt.Errorf("PNG cannot compress to %.2fMB (got %.2fMB). Consider using JPEG format or enabling AllowResolutionReduction",
|
||||||
|
targetMB, sizeMB)
|
||||||
|
|
||||||
|
default:
|
||||||
|
return nil, errors.New("unsupported output format")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func encodeJPEG(img image.Image, quality int) ([]byte, error) {
|
||||||
|
var buf bytes.Buffer
|
||||||
|
// Use 4:2:0 subsampling (default) for smaller size.
|
||||||
|
err := jpeg.Encode(&buf, img, &jpeg.Options{Quality: quality})
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return buf.Bytes(), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func encodePNG(img image.Image, level png.CompressionLevel) ([]byte, error) {
|
||||||
|
var buf bytes.Buffer
|
||||||
|
enc := png.Encoder{CompressionLevel: level}
|
||||||
|
if err := enc.Encode(&buf, img); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return buf.Bytes(), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func imageHasAlpha(img image.Image) bool {
|
||||||
|
switch img.(type) {
|
||||||
|
case *image.NRGBA, *image.NRGBA64, *image.RGBA, *image.RGBA64, *image.Alpha, *image.Alpha16, *image.Paletted:
|
||||||
|
// Need to inspect pixels if we want exactness; but this is good enough and stable.
|
||||||
|
return true
|
||||||
|
default:
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func flattenToWhite(img image.Image) image.Image {
|
||||||
|
b := img.Bounds()
|
||||||
|
dst := image.NewRGBA(b)
|
||||||
|
|
||||||
|
// Fill with white.
|
||||||
|
for y := b.Min.Y; y < b.Max.Y; y++ {
|
||||||
|
for x := b.Min.X; x < b.Max.X; x++ {
|
||||||
|
dst.Set(x, y, image.White)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Draw original image over white background.
|
||||||
|
return imaging.Overlay(dst, img, image.Pt(0, 0), 1.0)
|
||||||
|
}
|
||||||
|
|
||||||
|
func minInt(a, b int) int {
|
||||||
|
if a < b {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
|
||||||
|
func maxInt(a, b int) int {
|
||||||
|
if a > b {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
|
||||||
|
// alreadyMeetsRequirements checks if the image already satisfies the size and dimension requirements
|
||||||
|
func alreadyMeetsRequirements(img image.Image, data []byte, opt Options) bool {
|
||||||
|
// Check file size
|
||||||
|
maxBytes := int64(opt.MaxSizeMB * 1024 * 1024)
|
||||||
|
if int64(len(data)) > maxBytes {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check dimensions based on mode
|
||||||
|
srcW := img.Bounds().Dx()
|
||||||
|
srcH := img.Bounds().Dy()
|
||||||
|
targetW := opt.TargetWidth
|
||||||
|
targetH := opt.TargetHeight
|
||||||
|
|
||||||
|
switch opt.Mode {
|
||||||
|
case ResizeModeFit:
|
||||||
|
// For fit mode, check if image is already within or equal to target dimensions
|
||||||
|
if targetW > 0 && srcW > targetW {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
if targetH > 0 && srcH > targetH {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
// If only one dimension is specified, check aspect ratio compatibility
|
||||||
|
if targetW > 0 && targetH == 0 && srcW <= targetW {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
if targetH > 0 && targetW == 0 && srcH <= targetH {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
if targetW > 0 && targetH > 0 && srcW <= targetW && srcH <= targetH {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
|
||||||
|
case ResizeModeFill, ResizeModePad:
|
||||||
|
// For fill/pad mode, image must be exactly the target dimensions
|
||||||
|
if srcW != targetW || srcH != targetH {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
|
||||||
|
default:
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// tryWithReducedResolution attempts to compress by progressively reducing resolution
|
||||||
|
func tryWithReducedResolution(img image.Image, opt Options, outPath string, maxBytes int64) (string, error) {
|
||||||
|
bounds := img.Bounds()
|
||||||
|
w := bounds.Dx()
|
||||||
|
h := bounds.Dy()
|
||||||
|
|
||||||
|
// Try reducing resolution in steps: 90%, 80%, 70%, 60%, 50%
|
||||||
|
reductions := []float64{0.9, 0.8, 0.7, 0.6, 0.5}
|
||||||
|
|
||||||
|
for _, factor := range reductions {
|
||||||
|
newW := int(float64(w) * factor)
|
||||||
|
newH := int(float64(h) * factor)
|
||||||
|
|
||||||
|
if newW < 100 || newH < 100 {
|
||||||
|
break // Don't reduce too much
|
||||||
|
}
|
||||||
|
|
||||||
|
resized := imaging.Resize(img, newW, newH, imaging.Lanczos)
|
||||||
|
|
||||||
|
// Try to encode with reduced resolution
|
||||||
|
encoded, err := encodeUnderSize(resized, "jpeg", maxBytes, opt.MinQuality, opt.MaxRetries/2)
|
||||||
|
if err == nil {
|
||||||
|
// Success! Save it
|
||||||
|
tmpPath := outPath + ".tmp"
|
||||||
|
if err := os.WriteFile(tmpPath, encoded, 0o644); err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if err := os.Rename(tmpPath, outPath); err != nil {
|
||||||
|
_ = os.Remove(tmpPath)
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
return outPath, nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
targetMB := float64(maxBytes) / (1024 * 1024)
|
||||||
|
return "", fmt.Errorf("cannot compress to %.2fMB even after reducing resolution to 50%%. Original size too large", targetMB)
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue
Block a user