From 8a0cb38a396e18a9f220bd5144212baca18f49d1 Mon Sep 17 00:00:00 2001
From: liuxiaolong <liuxiaolong@aiotlink.com>
Date: 星期一, 22 六月 2020 15:43:07 +0800
Subject: [PATCH] push space left by uni-push

---
 conf/app.conf              |    9 +
 service/msgPush.go         |  156 +++++++++++++++++++++++++++++++
 service/carService_test.go |    4 
 extend/util/httpUtil.go    |    1 
 extend/util/util.go        |   41 ++++++++
 main.go                    |    1 
 controllers/car.go         |   51 ++++++++-
 service/msgPush_test.go    |   11 ++
 8 files changed, 260 insertions(+), 14 deletions(-)

diff --git a/conf/app.conf b/conf/app.conf
index 0e54945..23abe9b 100644
--- a/conf/app.conf
+++ b/conf/app.conf
@@ -9,4 +9,11 @@
 downdoc = true
 latestVersion = 1.0.0
 latestUrl =
-juheweihaokey = 8c0efc4439080ef6c6aa2c29688c9550
\ No newline at end of file
+juheweihaokey = 8c0efc4439080ef6c6aa2c29688c9550
+pushAppId = WU8KzZBaTwADIjTwaMSzW5
+pushAppKey = 9JLs4B1ZVkAVh93JXX3MP4
+pushAppSecret =聽JuKr5y8IIC88WAWPicaSK3
+pushMasterSecret = IbSAe83ZoZAczhKSA3Bwj9
+pushPackageName = uni.UNI359F489
+pushSignature = BA:AD:09:3A:82:82:9F:B4:32:A7:B2:8C:B4:CC:F0:E9:F3:7D:AE:58
+pushBaseUrl = https://restapi.getui.com/v2/
\ No newline at end of file
diff --git a/controllers/car.go b/controllers/car.go
index 9dd4fd4..11ce19b 100644
--- a/controllers/car.go
+++ b/controllers/car.go
@@ -4,14 +4,55 @@
 	"car-service/extend/code"
 	"car-service/models"
 	"car-service/service"
+	"fmt"
 	"github.com/astaxie/beego"
 	"net/http"
 	"sort"
+	"sync"
 	"time"
 )
 
 type CarController struct {
 	beego.Controller
+}
+
+//瀹炴椂璁$畻鍓╀綑杞︿綅鏁伴噺锛岃揪鍒版潯浠跺氨鎺ㄩ��
+func ComputeSpaceLeftRealTime() {
+	ticker := time.NewTicker(3 * time.Second)
+	prePushLeft := 0
+	for {
+		select {
+			case <-ticker.C:
+				m := time.Now().Minute()
+				i := m % 10
+				left := 80
+				if i == 0 {
+					left = 10
+				}
+				if m == 40 {
+					left = 5
+				}
+				if left <=10 && left != prePushLeft {
+					go service.Push("鑲茶嫳鏅烘収鍋滆溅", fmt.Sprintf("褰撳墠鍓╀綑杞︿綅锛�%d涓�", left))
+				}
+				updateSpaceLeft(left)
+		default:
+			time.Sleep(500 * time.Millisecond)
+		}
+	}
+}
+
+var cacheSpaceLeft int
+var cLock sync.RWMutex
+func updateSpaceLeft(num int) {
+	cLock.Lock()
+	defer cLock.Unlock()
+	cacheSpaceLeft = num
+}
+func getSpaceLeft() int {
+	cLock.Lock()
+	defer cLock.Unlock()
+	return cacheSpaceLeft
 }
 
 // @Title 缁熻鍓╀綑杞︿綅
@@ -22,15 +63,7 @@
 func (c *CarController) Statistic() {
 	//sv := service.NewCarService()
 	//sta := sv.Statistic()
-	m := time.Now().Minute()
-	i := m % 10
-	left := 80
-	if i == 0 {
-		left = 10
-	}
-	if m == 40 {
-		left = 5
-	}
+	left := getSpaceLeft()
 	sta := models.CarStatistic{
 		Left: left,
 	}
diff --git a/extend/util/httpUtil.go b/extend/util/httpUtil.go
index 0f3f267..303612b 100644
--- a/extend/util/httpUtil.go
+++ b/extend/util/httpUtil.go
@@ -15,6 +15,7 @@
 	CONTENT_TYPE_FORM    = "application/x-www-form-urlencoded"
 	CONTENT_TYPE_MULFORM = "multipart/form-data"
 	CONTENT_TYPE_JSON    = "application/json"
+	CONTENT_TYPE_UTF8_JSON = "application/json;charset=utf-8"
 )
 
 func DoPostRequest(url string, contentType string, body map[string]interface{}, params map[string]string, headers map[string]string) ([]byte, error) {
diff --git a/extend/util/util.go b/extend/util/util.go
index 1ae905f..5e2b118 100644
--- a/extend/util/util.go
+++ b/extend/util/util.go
@@ -5,16 +5,30 @@
 	"crypto/md5"
 	"crypto/sha256"
 	"encoding/base64"
+	"encoding/hex"
+	"fmt"
+	"math/rand"
+	"strconv"
+	"strings"
+	"time"
 	"unsafe"
 )
+
+func Sha256(message string) string {
+	h := sha256.New()
+	h.Write([]byte(message))
+	res := h.Sum(nil)
+	return hex.EncodeToString(res)
+}
+
 func ComputeHmacSha256Base64(message string, secret string) string {
 	key := []byte(secret)
 	h := hmac.New(sha256.New, key)
 	h.Write([]byte(message))
 	abs := h.Sum(nil)
-
 	return base64.StdEncoding.EncodeToString(abs)
 }
+
 
 func Hik_ComputeSignatureBase64(appKey string, appSecret string, httpMethod string, accept string, contentType string, date string, url string) string {
 	httpHeaders := httpMethod +"\n" + accept + "\n" + contentType + "\n"+ date +"\n"
@@ -43,4 +57,29 @@
 func MD5Base64(s []byte) string {
 	sum := md5.Sum(s)
 	return base64.StdEncoding.EncodeToString(sum[:])
+}
+
+func GenValidateCode(width int) string {
+	numeric := [10]byte{0,1,2,3,4,5,6,7,8,9}
+	r := len(numeric)
+	rand.Seed(time.Now().UnixNano())
+
+	var sb strings.Builder
+	for i := 0; i < width; i++ {
+		fmt.Fprintf(&sb, "%d", numeric[ rand.Intn(r) ])
+	}
+	str := sb.String()
+	if strings.HasPrefix(str, "0") {
+		pI := RandInt(1,9)
+		str = strconv.Itoa(pI) + str[1:]
+	}
+	return str
+}
+
+//鐢熸垚鍖洪棿闅忔満鏁�
+func RandInt(min, max int) int {
+	if min >= max || min ==0 ||max == 0 {
+		return max
+	}
+	return rand.Intn(max-min) + min
 }
\ No newline at end of file
diff --git a/main.go b/main.go
index 202ddc5..2acffc9 100644
--- a/main.go
+++ b/main.go
@@ -12,5 +12,6 @@
 		beego.BConfig.WebConfig.StaticDir["/swagger"] = "swagger"
 	}
 	controllers.Schedule()
+	go controllers.ComputeSpaceLeftRealTime()
 	beego.Run()
 }
diff --git a/service/carService_test.go b/service/carService_test.go
index 8a23c38..912baa9 100644
--- a/service/carService_test.go
+++ b/service/carService_test.go
@@ -1,11 +1,9 @@
 package service
 
 import (
-	"fmt"
 	"testing"
 )
 
 func TestCarService_Statistic(t *testing.T) {
-	parkList := getHikParkList()
-	fmt.Println("parkList:", parkList)
+
 }
\ No newline at end of file
diff --git a/service/msgPush.go b/service/msgPush.go
new file mode 100644
index 0000000..3d8d42c
--- /dev/null
+++ b/service/msgPush.go
@@ -0,0 +1,156 @@
+package service
+
+import (
+	"car-service/extend/util"
+	"encoding/json"
+	"errors"
+	"fmt"
+	"github.com/astaxie/beego"
+	"sync"
+	"time"
+)
+var latestToken *TokenResult
+var lock sync.RWMutex
+func getCacheToken() string {
+	lock.Lock()
+	defer lock.Unlock()
+	if latestToken != nil {
+		return latestToken.Token
+	}
+	return ""
+}
+func updateToken(newT *TokenResult) {
+	lock.Lock()
+	defer lock.Unlock()
+	latestToken = newT
+}
+
+func init() {
+	newToken, err := RefreshToken()
+	if err == nil {
+		updateToken(newToken)
+	}
+	ticker := time.NewTicker(time.Hour * 20)
+	go func() {
+		for {
+			select {
+				case <-ticker.C:
+					if t,err := RefreshToken();err == nil {
+						updateToken(t)
+					}
+			default:
+				time.Sleep(time.Second * 5)
+			}
+		}
+	}()
+}
+
+type PushResult struct {
+	Code 		int 			`json:"code"`
+	Msg 		string 			`json:"msg"`
+	Data 		interface{}  	`json:"data"`
+}
+
+type TokenResult struct {
+	ExpireTime 	string 			`json:"expire_time"`
+	Token 		string 			`json:"token"`
+}
+
+func Push(title string, msg string) (bool,error) {
+	appId := beego.AppConfig.String("pushAppId")
+	baseUrl := beego.AppConfig.String("pushBaseUrl") + appId
+	retryTimes := 0
+ReTry:
+	token := getCacheToken()
+	if token == "" {
+		return false, errors.New("token is nil")
+	}
+	url := baseUrl+"/push/all"
+	reqBody := map[string]interface{} {
+		"request_id": time.Now().Format("20060102150405") + util.GenValidateCode(6),
+		"settings":map[string]int {
+			"ttl": 8 * 3600 * 1000,
+		},
+		"audience": "all",
+		"push_message": map[string]string{
+			"title": title,
+			"body": msg,
+			"click_type": "url",
+			"url": "http://baidu.com",
+		},
+	}
+	header := map[string]string {
+		"token": token,
+	}
+	b, err := util.DoPostRequest(url, util.CONTENT_TYPE_UTF8_JSON, reqBody, nil, header)
+	if err !=nil {
+		fmt.Println("DoPost err:", err)
+		return false, err
+	}
+	var result PushResult
+	err = json.Unmarshal(b, &result)
+	if err != nil {
+		fmt.Println("unmarshal err:", err)
+		return false, err
+	}
+	if result.Code == 0 {
+		return true, nil
+	} else if result.Code == 10001 { //token杩囨湡
+		if retryTimes <=3 {
+			newToken, err := RefreshToken()
+			if err == nil {
+				updateToken(newToken)
+				retryTimes++
+				goto ReTry
+			}
+		}
+
+	}
+
+	return false, errors.New("鎺ㄩ�佸け璐�")
+}
+
+func RefreshToken() (*TokenResult,error) {
+	//appId := beego.AppConfig.String("pushAppId")
+	//appKey := beego.AppConfig.String("pushAppKey")
+	//masterSecret := beego.AppConfig.String("pushMasterSecret")
+	//baseUrl := beego.AppConfig.String("pushBaseUrl") + appId
+	appId := "WU8KzZBaTwADIjTwaMSzW5"
+	appKey := "9JLs4B1ZVkAVh93JXX3MP4"
+	masterSecret := "IbSAe83ZoZAczhKSA3Bwj9"
+	baseUrl := "https://restapi.getui.com/v2/"+appId
+	url := baseUrl +"/auth"
+	timestamp := fmt.Sprintf("%v", time.Now().UnixNano() / 1e6)
+	sign := util.Sha256(appKey + timestamp + masterSecret)
+	reqBody := map[string]interface{} {
+		"sign": sign,
+		"timestamp": timestamp,
+		"appkey": appKey,
+	}
+	b, err := util.DoPostRequest(url, util.CONTENT_TYPE_UTF8_JSON, reqBody, nil, nil)
+	if err !=nil {
+		fmt.Println("DoPost err:", err)
+		return nil, err
+	}
+	var result PushResult
+	err = json.Unmarshal(b, &result)
+	if err != nil {
+		fmt.Println("unmarshal err:", err)
+		return nil, err
+	}
+	if result.Code == 0 {
+		db, err := json.Marshal(result.Data)
+		if err != nil {
+			fmt.Println("marshal err:", err)
+			return nil, err
+		}
+		var t TokenResult
+		err = json.Unmarshal(db, &t)
+		if err != nil {
+			fmt.Println("unmarshal err:", err)
+			return nil, err
+		}
+		return &t, nil
+	}
+	return nil, errors.New("鑾峰彇unipush骞冲彴token澶辫触")
+}
\ No newline at end of file
diff --git a/service/msgPush_test.go b/service/msgPush_test.go
new file mode 100644
index 0000000..341f20d
--- /dev/null
+++ b/service/msgPush_test.go
@@ -0,0 +1,11 @@
+package service
+
+import (
+	"fmt"
+	"testing"
+)
+
+func TestRefreshToken(t *testing.T) {
+	r, err := RefreshToken()
+	fmt.Println(r, err)
+}
\ No newline at end of file

--
Gitblit v1.8.0