|
|
|
package task
|
|
|
|
|
|
|
|
import (
|
|
|
|
"archive/zip"
|
|
|
|
"bytes"
|
|
|
|
"fmt"
|
|
|
|
util "github.com/alibabacloud-go/tea-utils/service"
|
|
|
|
"github.com/alibabacloud-go/tea/tea"
|
|
|
|
"image"
|
|
|
|
"image/jpeg"
|
|
|
|
"image/png"
|
|
|
|
"io"
|
|
|
|
"io/fs"
|
|
|
|
"io/ioutil"
|
|
|
|
"net/http"
|
|
|
|
"net/url"
|
|
|
|
"os"
|
|
|
|
path2 "path"
|
|
|
|
"path/filepath"
|
|
|
|
"recook/internal/back"
|
|
|
|
"recook/internal/dbc"
|
|
|
|
"recook/internal/libs/weibo"
|
|
|
|
"recook/internal/static_path"
|
|
|
|
"recook/internal/v2/model/recook/goods"
|
|
|
|
"recook/internal/v2/model/search_ali"
|
|
|
|
"recook/tools"
|
|
|
|
"strconv"
|
|
|
|
"strings"
|
|
|
|
|
|
|
|
mysql2 "git.oa00.com/go/mysql"
|
|
|
|
"github.com/corona10/goimagehash"
|
|
|
|
"github.com/gin-gonic/gin"
|
|
|
|
"golang.org/x/text/encoding/simplifiedchinese"
|
|
|
|
"golang.org/x/text/transform"
|
|
|
|
"gorm.io/gorm"
|
|
|
|
)
|
|
|
|
|
|
|
|
type Goods struct {
|
|
|
|
}
|
|
|
|
|
|
|
|
type Base struct {
|
|
|
|
goods.RecookGoodsInfoModel
|
|
|
|
Photo goods.RecookGoodsMainPhotoModel `gorm:"foreignKey:goods_id"`
|
|
|
|
}
|
|
|
|
|
|
|
|
const MaxDistance = 5
|
|
|
|
|
|
|
|
func (g *Goods) ZipSync(c *gin.Context) {
|
|
|
|
file, err := c.FormFile("upload")
|
|
|
|
if err != nil {
|
|
|
|
c.String(http.StatusBadRequest, "请求失败1")
|
|
|
|
return
|
|
|
|
}
|
|
|
|
f, err := file.Open()
|
|
|
|
if err != nil {
|
|
|
|
c.String(http.StatusBadRequest, "请求失败2")
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
zipReader, err := zip.NewReader(f, file.Size)
|
|
|
|
if err != nil {
|
|
|
|
c.String(http.StatusBadRequest, "请求失败3")
|
|
|
|
return
|
|
|
|
}
|
|
|
|
for _, v := range zipReader.File {
|
|
|
|
if v.FileInfo().IsDir() {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
decodeName := ""
|
|
|
|
if v.Flags == 0 {
|
|
|
|
i := bytes.NewReader([]byte(v.Name))
|
|
|
|
|
|
|
|
decoder := transform.NewReader(i, simplifiedchinese.GB18030.NewDecoder())
|
|
|
|
|
|
|
|
content, _ := ioutil.ReadAll(decoder)
|
|
|
|
|
|
|
|
decodeName = string(content)
|
|
|
|
} else {
|
|
|
|
decodeName = v.Name
|
|
|
|
}
|
|
|
|
decodeName = strings.Split(decodeName, "/")[1]
|
|
|
|
name := path2.Base(decodeName)
|
|
|
|
ext := path2.Ext(decodeName)
|
|
|
|
|
|
|
|
pathName := filepath.Join(static_path.Dir.Root, static_path.Dir.Photo, tools.MD5(name)+ext)
|
|
|
|
content, _ := v.Open()
|
|
|
|
b, _ := io.ReadAll(content)
|
|
|
|
if err = os.WriteFile(pathName, b, fs.ModePerm); err != nil {
|
|
|
|
c.String(http.StatusBadRequest, "请求失败3")
|
|
|
|
break
|
|
|
|
}
|
|
|
|
brandName := decodeName[0 : len(decodeName)-len(ext)]
|
|
|
|
var brand goods.RecookGoodsBrandModel
|
|
|
|
mysql2.Db.First(&brand, "name = ? AND created_at > '2021-08-26'", brandName)
|
|
|
|
if brand.Id == 0 {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
brand.LogoUrl = filepath.Join(static_path.Dir.Photo, tools.MD5(name)+ext)
|
|
|
|
mysql2.Db.Save(&brand)
|
|
|
|
}
|
|
|
|
c.String(http.StatusBadRequest, "请求成功")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) WeiboSync(c *gin.Context) {
|
|
|
|
go func() {
|
|
|
|
for p := 1; p <= 20; p++ {
|
|
|
|
v := url.Values{}
|
|
|
|
v.Set("containerid", "107603"+"5918987931")
|
|
|
|
v.Set("page", strconv.Itoa(p))
|
|
|
|
data, err := weibo.GetJson(v)
|
|
|
|
if err != nil {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
weibo.ParsePage(data)
|
|
|
|
}
|
|
|
|
}()
|
|
|
|
|
|
|
|
c.JSON(200, gin.H{
|
|
|
|
"status": "success",
|
|
|
|
})
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// Update 更新相关
|
|
|
|
func (g *Goods) Update(c *gin.Context) {
|
|
|
|
var data []Base
|
|
|
|
mysql2.Db.Preload("Photo", func(db *gorm.DB) *gorm.DB {
|
|
|
|
return db.Where("is_master = 1").Where("url <> ''")
|
|
|
|
}).Find(&data, "publish_status = 1")
|
|
|
|
fmt.Println(len(data))
|
|
|
|
var temp []goods.Associate
|
|
|
|
for _, v := range data {
|
|
|
|
if v.Photo.Hash == "" {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
o, err := goimagehash.ImageHashFromString(v.Photo.Hash)
|
|
|
|
if err != nil {
|
|
|
|
back.Fail(c, "err 1: "+err.Error())
|
|
|
|
return
|
|
|
|
}
|
|
|
|
fmt.Println(len(data))
|
|
|
|
for _, j := range data {
|
|
|
|
if j.SecondCategoryID != v.SecondCategoryID || j.Id == v.Id || j.Photo.Hash == "" {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
b, err := goimagehash.ImageHashFromString(j.Photo.Hash)
|
|
|
|
if err != nil {
|
|
|
|
back.Fail(c, "err 2: "+err.Error())
|
|
|
|
return
|
|
|
|
}
|
|
|
|
distance, err := o.Distance(b)
|
|
|
|
if err != nil {
|
|
|
|
back.Fail(c, "err 3: "+err.Error())
|
|
|
|
return
|
|
|
|
}
|
|
|
|
fmt.Println(distance)
|
|
|
|
if distance <= MaxDistance {
|
|
|
|
temp = append(temp, goods.Associate{
|
|
|
|
GoodsID: v.Id,
|
|
|
|
OtherGoodsID: j.Id,
|
|
|
|
Distance: distance,
|
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if err := mysql2.Db.Transaction(func(tx *gorm.DB) error {
|
|
|
|
if err := tx.Where("1 = 1").Delete(&goods.Associate{}).Error; err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
|
|
|
|
var t []goods.Associate
|
|
|
|
fmt.Println("temp:", temp)
|
|
|
|
for _, v := range temp {
|
|
|
|
t = append(t, v)
|
|
|
|
if len(t) == 100 {
|
|
|
|
fmt.Println("新建相似表:", len(t))
|
|
|
|
if err := tx.Create(&t).Error; err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
t = []goods.Associate{}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if len(t) > 0 {
|
|
|
|
fmt.Println("新建相似表:", len(t))
|
|
|
|
if err := tx.Create(&t).Error; err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}); err != nil {
|
|
|
|
back.Fail(c, err.Error())
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
back.Suc(c, "操作完成", nil)
|
|
|
|
}
|
|
|
|
func CalHash(model goods.RecookGoodsMainPhotoModel) (string, error) {
|
|
|
|
uri := filepath.Join(static_path.Dir.Root, model.Url)
|
|
|
|
file, _ := os.Open(uri)
|
|
|
|
defer file.Close()
|
|
|
|
|
|
|
|
var img image.Image
|
|
|
|
|
|
|
|
if strings.HasSuffix(uri, "png") {
|
|
|
|
img1, err := png.Decode(file)
|
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
|
|
|
img = img1
|
|
|
|
fmt.Println("img:", img)
|
|
|
|
} else if strings.HasSuffix(uri, "jpg") || strings.HasSuffix(uri, "jpeg") {
|
|
|
|
img1, err := jpeg.Decode(file)
|
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
|
|
|
img = img1
|
|
|
|
fmt.Println("img:", img)
|
|
|
|
} else {
|
|
|
|
return "", nil
|
|
|
|
}
|
|
|
|
if img == nil {
|
|
|
|
model.Hash = ""
|
|
|
|
return "", nil
|
|
|
|
}
|
|
|
|
hash, err := goimagehash.DifferenceHash(img)
|
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
|
|
|
model.Hash = hash.ToString()
|
|
|
|
fmt.Println("hash:", hash.ToString())
|
|
|
|
dbc.DB.Table(model.TableName()).Where("id=?", model.Id).Updates(model)
|
|
|
|
return hash.ToString(), nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) ShaMaSync(c *gin.Context) {
|
|
|
|
go ShaMaSyncAllSku()
|
|
|
|
c.String(200, "suc")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) Sync(c *gin.Context) {
|
|
|
|
b := c.Query("brand")
|
|
|
|
go SyncAllSku(b)
|
|
|
|
c.String(200, "suc")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) Fix(c *gin.Context) {
|
|
|
|
go SyncJDImage()
|
|
|
|
c.String(200, "suc")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) AttrSync(c *gin.Context) {
|
|
|
|
go AttrSync()
|
|
|
|
c.String(200, "suc")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) Publish(c *gin.Context) {
|
|
|
|
go func() {
|
|
|
|
var gs []goods.RecookGoodsInfoModel
|
|
|
|
mysql2.Db.Find(&gs)
|
|
|
|
for _, v := range gs {
|
|
|
|
var gsk []goods.RecookGoodsSkuModel
|
|
|
|
mysql2.Db.Find(&gsk, "goods_id = ?", v.Id)
|
|
|
|
if len(gsk) == 0 {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
flag := 1
|
|
|
|
price := 1
|
|
|
|
for _, j := range gsk {
|
|
|
|
if j.Inventory != 0 {
|
|
|
|
flag = 0
|
|
|
|
}
|
|
|
|
if j.DiscountPrice.IsZero() {
|
|
|
|
price = 0
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if flag == 0 && price == 1 {
|
|
|
|
mysql2.Db.Table((&goods.RecookGoodsInfoModel{}).TableName()).
|
|
|
|
Where("id = ?", v.Id).Update("publish_status", 1)
|
|
|
|
}
|
|
|
|
if flag == 1 {
|
|
|
|
mysql2.Db.Table((&goods.RecookGoodsInfoModel{}).TableName()).
|
|
|
|
Where("id = ?", v.Id).Update("publish_status", 0)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}()
|
|
|
|
|
|
|
|
c.String(200, "suc")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (g *Goods) OpenSearch(c *gin.Context) {
|
|
|
|
go func() {
|
|
|
|
page := 0
|
|
|
|
size := 1000
|
|
|
|
for {
|
|
|
|
var gs []goods.RecookGoodsInfoModel
|
|
|
|
mysql2.Db.Offset(page * size).Limit(size).Find(&gs)
|
|
|
|
if len(gs) == 0 {
|
|
|
|
break
|
|
|
|
}
|
|
|
|
config := &search_ali.Config{
|
|
|
|
Endpoint: tea.String(search_ali.EndPoint),
|
|
|
|
AccessKeyId: tea.String(search_ali.AccessKeyId),
|
|
|
|
AccessKeySecret: tea.String(search_ali.AccessKeySecret),
|
|
|
|
}
|
|
|
|
client, _clientErr := search_ali.NewClient(config)
|
|
|
|
|
|
|
|
// 如果 NewClient 过程中出现异常. 则 返回 _clientErr 且输出 错误信息.
|
|
|
|
if _clientErr != nil {
|
|
|
|
fmt.Println(_clientErr)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
runTime := &util.RuntimeOptions{
|
|
|
|
ConnectTimeout: tea.Int(5000),
|
|
|
|
ReadTimeout: tea.Int(10000),
|
|
|
|
Autoretry: tea.Bool(false),
|
|
|
|
IgnoreSSL: tea.Bool(false),
|
|
|
|
MaxIdleConns: tea.Int(50),
|
|
|
|
}
|
|
|
|
requestBody := make([]search_ali.Res, 0)
|
|
|
|
for _, v := range gs {
|
|
|
|
cmd := search_ali.ADD
|
|
|
|
if v.PublishStatus == 0 {
|
|
|
|
cmd = search_ali.DELETE
|
|
|
|
}
|
|
|
|
requestBody = append(requestBody, search_ali.Res{
|
|
|
|
Cmd: cmd,
|
|
|
|
Fields: search_ali.F{
|
|
|
|
ID: v.Id,
|
|
|
|
GoodsName: v.GoodsName,
|
|
|
|
},
|
|
|
|
})
|
|
|
|
}
|
|
|
|
fmt.Println("request len:", len(requestBody))
|
|
|
|
|
|
|
|
// 发送请求的方法调用.
|
|
|
|
r1, rr := client.Request(
|
|
|
|
tea.String("POST"),
|
|
|
|
tea.String("/v3/openapi/apps/"+search_ali.App+"/"+search_ali.Table+"/actions/bulk"),
|
|
|
|
nil,
|
|
|
|
nil,
|
|
|
|
requestBody,
|
|
|
|
runTime)
|
|
|
|
page += 1
|
|
|
|
if rr != nil {
|
|
|
|
fmt.Println(rr.Error())
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
fmt.Println(r1)
|
|
|
|
}
|
|
|
|
}()
|
|
|
|
c.String(200, "sync")
|
|
|
|
}
|