Ver Fonte

Merge remote-tracking branch 'origin/poser_create'

# Conflicts:
#	services/share_poster.go
Roc há 2 anos atrás
pai
commit
5bd309cffb

+ 2 - 2
controller/public.go

@@ -106,7 +106,7 @@ func GetSharePoster(c *gin.Context) {
 		response.Fail("来源有误", c)
 		return
 	}
-	imgUrl, err := services.CreatePosterFromSource(req.CodePage, req.CodeScene, req.Source, req.Version, req.Pars)
+	imgUrl, err := services.CreatePosterFromSourceV2(req.CodePage, req.CodeScene, req.Source, req.Version, req.Pars)
 	if err != nil {
 		response.FailData("获取分享海报失败", "获取分享海报失败, Err: "+err.Error(), c)
 		return
@@ -131,7 +131,7 @@ func GetSuncodeScene(c *gin.Context) {
 	}
 	pars, err := yb_suncode_pars.GetSceneByKey(reqKey)
 	if err != nil && err != utils.ErrNoRow {
-		response.FailMsg("获取失败", "GetSuncodeScene获取失败, Err: " + err.Error(), c)
+		response.FailMsg("获取失败", "GetSuncodeScene获取失败, Err: "+err.Error(), c)
 		return
 	}
 	scene := ""

+ 9 - 0
models/tables/yb_poster_config/query.go

@@ -0,0 +1,9 @@
+package yb_poster_config
+
+import "hongze/hongze_yb/global"
+
+// GetBySource 根据来源查询配置
+func GetBySource(source string) (item *YbPosterConfig, err error) {
+	err = global.DEFAULT_MYSQL.Where("source = ? ", source).Order("id desc").First(&item).Error
+	return
+}

+ 46 - 0
models/tables/yb_poster_config/yb_poster_config.go

@@ -0,0 +1,46 @@
+package yb_poster_config
+
+import (
+	"time"
+)
+
+// YbPosterConfig 研报海报生成配置
+type YbPosterConfig struct {
+	ID                 uint32    `gorm:"primaryKey;column:id;type:int(9) unsigned;not null" json:"-"`
+	Source             string    `gorm:"index:idx_source;column:source;type:varchar(64);default:''" json:"source"` // 来源
+	Hight              float64   `gorm:"column:hight;type:double(9,2) unsigned;default:0.00" json:"hight"`         // 海报高度
+	Width              float64   `gorm:"column:width;type:double(9,2) unsigned;default:0.00" json:"width"`         // 海报宽度
+	HTMLTemplate       string    `gorm:"column:html_template;type:text" json:"htmlTemplate"`                       // html代码模板
+	HTMLReplaceConfig  string    `gorm:"column:html_replace_config;type:text" json:"htmlReplaceConfig"`            // 模板中的变量替换规则
+	DefaultValueConfig string    `gorm:"column:default_value_config;type:text" json:"defaultValueConfig"`          // 默认值的配置
+	Remark             string    `gorm:"column:remark;type:varchar(255);default:''" json:"remark"`                 // 备注
+	CreateTime         time.Time `gorm:"column:create_time;type:timestamp;default:CURRENT_TIMESTAMP" json:"createTime"`
+}
+
+// TableName get sql table name.获取数据库表名
+func (m *YbPosterConfig) TableName() string {
+	return "yb_poster_config"
+}
+
+// YbPosterConfigColumns get sql column name.获取数据库列名
+var YbPosterConfigColumns = struct {
+	ID                 string
+	Source             string
+	Hight              string
+	Width              string
+	HTMLTemplate       string
+	HTMLReplaceConfig  string
+	DefaultValueConfig string
+	Remark             string
+	CreateTime         string
+}{
+	ID:                 "id",
+	Source:             "source",
+	Hight:              "hight",
+	Width:              "width",
+	HTMLTemplate:       "html_template",
+	HTMLReplaceConfig:  "html_replace_config",
+	DefaultValueConfig: "default_value_config",
+	Remark:             "remark",
+	CreateTime:         "create_time",
+}

+ 252 - 1
services/share_poster.go

@@ -6,6 +6,7 @@ import (
 	"fmt"
 	"github.com/PuerkitoBio/goquery"
 	"hongze/hongze_yb/global"
+	"hongze/hongze_yb/models/tables/yb_poster_config"
 	"hongze/hongze_yb/models/tables/yb_poster_resource"
 	"hongze/hongze_yb/models/tables/yb_suncode_pars"
 	"hongze/hongze_yb/services/alarm_msg"
@@ -505,4 +506,254 @@ func GetRddpShareImg(title string) (imgUrl string, err error) {
 	}
 	imgUrl = res.Data
 	return
-}
+}
+
+// CreatePosterFromSourceV2 生成分享海报(通过配置获取相关信息)
+func CreatePosterFromSourceV2(codePage, codeScene, source, version, pars string) (imgUrl string, err error) {
+	var errMsg string
+	defer func() {
+		if err != nil {
+			global.LOG.Critical(fmt.Sprintf("CreatePosterFromSource: source=%s, pars:%s, errMsg:%s", source, pars, errMsg))
+			reqSlice := make([]string, 0)
+			reqSlice = append(reqSlice, fmt.Sprint("CodePage:", codePage, "\n"))
+			reqSlice = append(reqSlice, fmt.Sprint("CodeScene:", codeScene, "\n"))
+			reqSlice = append(reqSlice, fmt.Sprint("Source:", source, "\n"))
+			reqSlice = append(reqSlice, fmt.Sprint("Version:", version, "\n"))
+			reqSlice = append(reqSlice, fmt.Sprint("Pars:", pars, "\n"))
+			go alarm_msg.SendAlarmMsg("CreatePosterFromSource生成分享海报失败, Msg:"+errMsg+";Err:"+err.Error()+"\n;Req:\n"+strings.Join(reqSlice, ";"), 3)
+		}
+	}()
+	if codePage == "" || source == "" || pars == "" {
+		errMsg = "参数有误"
+		err = errors.New(errMsg)
+		return
+	}
+	path := fmt.Sprint(codePage, "?", codeScene)
+	// 非列表来源获取历史图片,无则生成
+	if !strings.Contains(source, "list") {
+		poster, tmpErr := yb_poster_resource.GetPosterByCondition(path, "poster", version)
+		if tmpErr != nil && tmpErr != utils.ErrNoRow {
+			err = tmpErr
+			return
+		}
+		if poster != nil && poster.ImgURL != "" {
+			imgUrl = poster.ImgURL
+			return
+		}
+	}
+	ybPosterConfig, err := yb_poster_config.GetBySource(source)
+	if err != nil {
+		return
+	}
+	// 图片长宽
+	//heightMap := map[string]int{
+	//	"activity_detail":       1210,
+	//	"activity_list":         1948,
+	//	"special_column_detail": 1480,
+	//	"special_column_list":   1548,
+	//	"chart_detail":          1536,
+	//	"chart_list":            1352,
+	//	"report_detail":         1420,
+	//	"report_list":           1344,
+	//}
+	//widthMap := map[string]int{
+	//	"activity_detail":       1280,
+	//	"activity_list":         1280,
+	//	"special_column_detail": 1176,
+	//	"special_column_list":   1176,
+	//	"chart_detail":          1176,
+	//	"chart_list":            1176,
+	//	"report_detail":         1176,
+	//	"report_list":           1176,
+	//}
+
+	width := ybPosterConfig.Width
+	height := ybPosterConfig.Hight
+	//生成太阳码
+	sunCodeUrl, err := CreateAndUploadSunCode(codePage, codeScene, version)
+	if err != nil {
+		return
+	}
+	//sunCodeUrl := ``
+	// 填充html内容
+	contentStr, newHeight, err := fillContent2HtmlV2(source, pars, sunCodeUrl, height, *ybPosterConfig)
+	if err != nil {
+		errMsg = "html内容有误"
+		return
+	}
+	global.LOG.Critical(contentStr)
+	//return
+	// 请求python服务htm2img
+	htm2ImgReq := make(map[string]interface{})
+	htm2ImgReq["html_content"] = contentStr
+	htm2ImgReq["width"] = width
+	htm2ImgReq["height"] = newHeight
+	res, err := postHtml2Img(htm2ImgReq)
+	if err != nil || res == nil {
+		errMsg = "html转图片请求失败"
+		return
+	}
+	if res.Code != 200 {
+		errMsg = "html转图片请求失败"
+		err = errors.New("html转图片失败: " + res.Msg)
+		return
+	}
+	imgUrl = res.Data
+	// 记录海报信息
+	newPoster := &yb_poster_resource.YbPosterResource{
+		Path:       path,
+		ImgURL:     imgUrl,
+		Type:       "poster",
+		Version:    version,
+		CreateTime: time.Now(),
+	}
+	err = newPoster.Create()
+	return
+}
+
+// HtmlReplaceConfig html替换配置
+type HtmlReplaceConfig struct {
+	TemplateStr string `json:"template_str"`
+	ReplaceStr  string `json:"replace_str"`
+}
+
+// DefaultValueConfig 默认值的配置
+type DefaultValueConfig struct {
+	Key          string `json:"key"`
+	UseOtherKey  string `json:"use_other_key"`
+	Value        string `json:"value"`
+	ConditionKey string `json:"condition_key"`
+}
+
+// fillContent2Html 填充HTML动态内容
+func fillContent2HtmlV2(source, pars, sunCodeUrl string, height float64, ybPosterConfig yb_poster_config.YbPosterConfig) (contentStr string, newHeight float64, err error) {
+	paramsMap := make(map[string]string)
+	if err = json.Unmarshal([]byte(pars), &paramsMap); err != nil {
+		return
+	}
+
+	//fmt.Println(paramsMap)
+
+	//html替换规则
+	htmlReplaceConfigList := make([]HtmlReplaceConfig, 0)
+	if err = json.Unmarshal([]byte(ybPosterConfig.HTMLReplaceConfig), &htmlReplaceConfigList); err != nil {
+		return
+	}
+
+	newHeight = height
+	contentStr = ybPosterConfig.HTMLTemplate
+
+	// 默认数据替换
+	defaultValueConfigMap := make([]DefaultValueConfig, 0)
+	if ybPosterConfig.DefaultValueConfig != `` {
+		if err = json.Unmarshal([]byte(ybPosterConfig.DefaultValueConfig), &defaultValueConfigMap); err != nil {
+			return
+		}
+	}
+	// 列表的动态内容不完整的用默认内容的填充
+	//var emptyTime1, emptyTime2 bool
+	conditionKeyValMap := make(map[string]string)
+	for _, v := range defaultValueConfigMap {
+		if v.ConditionKey == `` {
+			continue
+		}
+		conditionKeyVal, ok := conditionKeyValMap[v.ConditionKey]
+		if !ok {
+			conditionKeyVal = paramsMap[v.ConditionKey]
+			conditionKeyValMap[v.ConditionKey] = conditionKeyVal
+		}
+		if conditionKeyVal == `` {
+			paramsMap[v.Key] = v.Value
+			if v.UseOtherKey != `` {
+				if tmpVal, ok := paramsMap[v.UseOtherKey]; ok {
+					paramsMap[v.Key] = tmpVal
+				}
+			}
+
+		}
+	}
+
+	// 填充指定内容
+	switch source {
+	case "report_detail": //需要将简介处理下
+		reportAbstract := paramsMap["report_abstract"]
+		doc, tmpErr := goquery.NewDocumentFromReader(strings.NewReader(reportAbstract))
+		if tmpErr != nil {
+			err = tmpErr
+			return
+		}
+		abstract := ""
+		doc.Find("p").Each(func(i int, s *goquery.Selection) {
+			phtml, tmpErr := s.Html()
+			if tmpErr != nil {
+				err = tmpErr
+				return
+			}
+			st := s.Text()
+			if st != "" && st != "<br>" && st != "<br style=\"max-width: 100%;\">" && !strings.Contains(phtml, "iframe") {
+				abstract = abstract + "<p>" + phtml + "</p>"
+			}
+		})
+		paramsMap["report_abstract"] = abstract
+	case "activity_list":
+		bgColorMap := map[string]string{
+			"未开始": "#E3B377",
+			"进行中": "#3385FF",
+			"已结束": "#A2A2A2",
+		}
+		statusItemMap := map[string]string{
+			"未开始": "block",
+			"进行中": "none",
+			"已结束": "none",
+		}
+		offlineMap := map[string]string{
+			"线上会议": "none",
+			"线下沙龙": "block",
+		}
+		onlineMap := map[string]string{
+			"线上会议": "block",
+			"线下沙龙": "none",
+		}
+
+		listTitle := paramsMap["list_title"]
+		status1 := paramsMap["status_1"]
+		if status1 != "未开始" {
+			newHeight = 1715
+		}
+		status2 := paramsMap["status_2"]
+		paramsMap["list_title"] = "弘则FICC周度电话会安排"
+		paramsMap["bg_color_1"] = bgColorMap[status1]
+		paramsMap["show_item_1"] = statusItemMap[status1]
+		paramsMap["show_offline_1"] = offlineMap[listTitle]
+		paramsMap["show_online_1"] = onlineMap[listTitle]
+
+		paramsMap["bg_color_2"] = bgColorMap[status2]
+		paramsMap["show_item_2"] = statusItemMap[status2]
+		paramsMap["show_offline_2"] = offlineMap[listTitle]
+		paramsMap["show_online_2"] = onlineMap[listTitle]
+
+		// 用默认内容填充的活动时间字体颜色调至看不见
+		color1 := "#999"
+		color2 := "#999"
+
+		if paramsMap["empty_time_1"] == "true" {
+			color1 = "#fff"
+		}
+		if paramsMap["empty_time_2"] == "true" {
+			color2 = "#fff"
+		}
+		paramsMap["time_color_1"] = color1
+		paramsMap["time_color_2"] = color2
+	}
+
+	contentStr = strings.Replace(contentStr, "{{SUN_CODE}}", sunCodeUrl, 1)
+
+	for _, v := range htmlReplaceConfigList {
+		tmpVal, ok := paramsMap[v.ReplaceStr]
+		if !ok {
+			tmpVal = ``
+		}
+		contentStr = strings.Replace(contentStr, v.TemplateStr, tmpVal, 1)
+	}
+	return
+}