PB程序員的第一個go語言開發的http服務程序,實戰經歷(二)

根據接口規範文檔要求,需要通過POST請求發送參數,但是示例卻是Get形式的

http://xxx.xxx.com?method=queryMember&appKey=appkey&jsonData={}×tamp=2012-01-20 08:50:15&sign=7E65B60DCFA42B043FCF57169867082C。

我得計劃是一個關鍵點,一個關鍵點的實現,最後實現功能要求。

第一關鍵點,服務端能接收到請求發送的參數。首先,通過bee new 命令,新建一個web項目。然後在 controllers包內,新建POST方法,通過appKey := c.GetString(“appKey”)來獲取參數的值,beego.info(appKey)將變量值打印出來,驗證數據是否正確。

相關視頻教程:兄弟連區塊鏈教程2:Beego詳解 04.簡單路由 和Go語言Web開發Beego框架深入淺出第6節get請求和post請求的處理。

服務端的go代碼寫好,通過postman來發送請求驗證一下,但是沒有獲得預想的數據。因爲不清楚原因,4月4號、5號兩天時間來查找原因,將beego的controller的封裝瞭解了,官方的Http標準庫文檔看了一遍,還有《GO Web 編程》的第三章,重點理解請求、相應的概念,Http裏post和get發送請求的區別等。理論知識有了,問題還是找不到原因。決定拋開beego,按照3.2的示例,用liteide新建最簡單的項目,做了最簡單web服務,依然獲取不到數據。這樣才懷疑是否postman發送請求有問題,通過瀏覽器複製進示例網址,服務端能正常接收參數,確認是post有問題,受視頻教程通過form發送數據的影響,我以爲應該選form-data。百度一番才瞭解到postman的Body四種選項的區別,form-data一般傳文件選擇,x-www-form-urlencoded傳鍵值對,也就是get方式?後的內容,raw傳任意格式的文本,binary二進制。詳細的介紹見網址:https://blog.csdn.net/ye1992/article/details/49998511。將類型選擇爲x-www-form-urlencoded,服務端程序終於正常接收數據了。

第二個關鍵點,POST參數的驗證。爲了傳遞方便,將參數作爲結構,將參數的檢查作爲結構的成員函數,即方法。時間戳驗證,go的time包來處理時間,將字符串轉化爲time類型要注意時區問題,還有go專門的時間段的概念。簽名驗證通過crypto/md5包內md5函數實現。

相關代碼:

//服務端,處理POST請求
func (c *MainController) Post() {
	var inp inparam
	inp.appkey = c.GetString("appKey")
	inp.jsondata = c.GetString("jsonData")
	inp.method = c.GetString("method")
	inp.timestamp = c.GetString("timestamp")
	inp.sign = c.GetString("sign")

	//檢查post參數
	var rtcode int
	var rtmsg string
	var rtjson string

	rtcode, rtmsg = inp.Check()
	if rtcode < 0 {
		c.Data["json"] = `{"state":0, "msg":"` + rtmsg + `","jsonData":{},"code":null}`
		c.ServeJSON()
		return
	}

	//根據方法,調用函數
	if inp.method == "queryMember" {
		rtcode, rtmsg, rtjson = queryMember(inp.jsondata)
	} else if inp.method == "updateIntegral" {
		rtcode, rtmsg, rtjson = updateIntegral(inp.jsondata)
	} else {
		rtcode = -1
		rtmsg = "不支持的方法"
	}

	//返回信息
	if rtcode < 0 {
		c.Data["json"] = `{"state":0, "msg":"` + rtmsg + `","jsonData":{},"code":null}`
	} else {
		c.Data["json"] = `{"state":1, "msg":"成功","jsonData":` + rtjson + `,"code":null}`
	}

	c.ServeJSON()
}

//參數結構的成員函數,檢查post參數
func (this inparam) Check() (rtcode int, rtmsg string) {
	//返回編碼 成功1 失敗-1

	//檢查時間戳
	const base_format = "2006-01-02 15:04:05"
	tin, _ := time.ParseInLocation(base_format, this.timestamp, time.Local)
	tsys := time.Now()

	if tsys.Sub(tin).Minutes() > 2 || tin.Sub(tsys).Minutes() > 2 {
		rtcode = -1
		rtmsg = "時間戳超時"
		return rtcode, rtmsg
	}

	//檢查簽名
	strparam := "appKey" + this.appkey + "jsonData" + this.jsondata + "method" + this.method + "timestamp" + this.timestamp
	has := md5.Sum([]byte(strparam))
	md5str1 := fmt.Sprintf("%x", has)

	if md5str1 != this.sign {
		rtcode = -1
		rtmsg = "簽名不正確"
		return rtcode, rtmsg
	}

	rtcode = 1
	//返回
	return rtcode, rtmsg
}

後記:使用beego,請訪問beego的官網,https://beego.me/,裏邊的開發文檔挺全面的,MVC的概念要理解。

go的標準庫資料,請訪問https://studygolang.com/pkgdoc,這是官方文檔的中文版,最全最權威。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章