当前位置:网站首页>Go language web development series 25: Gin framework: using MD5 to verify the signature for the interface station
Go language web development series 25: Gin framework: using MD5 to verify the signature for the interface station
2022-07-03 13:47:00 【Lao Liu, you are so awesome】
One , Libraries used for installation
1,gin In the framework of github The address of :
https://github.com/gin-gonic/gin
2, Install... From the command line :
[email protected]:/data/go/ginhello# go get -u github.com/gin-gonic/[email protected] explain : Liu Hongdi's go The forest is a focus golang The blog of ,
Address :https://blog.csdn.net/weixin_43881017
explain : author : Liu Hongdi mailbox : [email protected]
Two , Information about the demonstration project
1, Project address :
https://github.com/liuhongdi/digv25
2, Functional specifications : Demonstrate adding signature verification for the interface station , Avoid attacks on interfaces
3, Project structure : Pictured :

3、 ... and ,go Code instructions
1,controller/userController.go
package controller
import (
"github.com/gin-gonic/gin"
"github.com/liuhongdi/digv25/global"
)
type UserController struct{}
func NewUserController() UserController {
return UserController{}
}
// The user login
func (g *UserController) Login(c *gin.Context) {
result := global.NewResult(c)
result.Success("success");
return
}2,global/constants.go
package global
var (
SignAppId string = "wap" //app id
SignAppSecret string = "30c722c6acc64306a88dd93a814c9f0a" //app secret
SignApiVersion string = "1.0" //api version
SignExpire int64 = 180 // Expiration time ,180 second
)3,middleware/sign.go
package middleware
import (
"github.com/gin-gonic/gin"
"github.com/liuhongdi/digv25/global"
"github.com/liuhongdi/digv25/pkg/sign"
"regexp"
)
// Current limiter
func SignMiddleware() gin.HandlerFunc {
return func(c *gin.Context) {
// Check whether the current url
exclude := regexp.MustCompile("/static/*")
path := c.Request.RequestURI
//fmt.Println("path:"+path)
if exclude != nil && exclude.MatchString(path) {
c.Next()
return
}
// from header To obtain parameters
appId := c.Request.Header.Get("appId")
timestamp := c.Request.Header.Get("timestamp")
signcli := c.Request.Header.Get("sign")
nonce := c.Request.Header.Get("nonce")
// Verify that the signature is correct
err := sign.VerifySign(appId,timestamp,signcli,nonce,global.SignAppId,global.SignAppSecret,global.SignApiVersion,global.SignExpire)
if (err != nil) {
resultRes := global.NewResult(c)
resultRes.Error(2004,err.Error())
return
} else {
//fmt.Println("sign passed")
c.Next()
return
}
}
}4,pkg/md5/md5.go
package md5
import (
"crypto/md5"
"encoding/hex"
)
// return md5 result
func MD5(str string) string {
s := md5.New()
s.Write([]byte(str))
return hex.EncodeToString(s.Sum(nil))
}
5,pkg/sign/sign.go
package sign
import (
"errors"
"github.com/liuhongdi/digv25/pkg/md5"
"strconv"
"time"
)
// Verify the signature
func VerifySign(appId,timestamp,sign,nonce,serverAppId,serverAppSecret,serverApiVersion string,signExpire int64) error {
// verification appid
if (serverAppId != appId) {
return errors.New("appId Error")
}
// Validation expiration time
timestampNow := time.Now().Unix()
//fmt.Println("now:")
//fmt.Println(timestampNow)
tsInt, _ := strconv.ParseInt(timestamp, 10, 64)
//fmt.Println("timeint:")
//fmt.Println(tsInt)
if tsInt > timestampNow || timestampNow - tsInt >= signExpire {
return errors.New("timestamp Error")
}
// Get the right sign For inspection
origin := appId + serverAppSecret + timestamp + nonce + serverApiVersion;
signEcrypt := md5.MD5(origin);
if (signEcrypt != sign) {
return errors.New("sign Error")
}
// No mistakes , return
return nil
}6,router/router.go
package router
import (
"github.com/gin-gonic/gin"
"github.com/liuhongdi/digv25/controller"
"github.com/liuhongdi/digv25/global"
"github.com/liuhongdi/digv25/middleware"
"log"
"net/http"
"runtime/debug"
)
func Router() *gin.Engine {
router := gin.Default()
// Handling exceptions
router.NoRoute(HandleNotFound)
router.NoMethod(HandleNotFound)
router.Use(middleware.SignMiddleware())
router.Use(Recover)
//static
router.StaticFS("/static", http.Dir("/data/liuhongdi/digv25/static"))
// Path mapping :index
indexc:=controller.NewIndexController()
router.GET("/index/index", indexc.Index);
// Path mapping :user
userc:=controller.NewUserController()
router.POST("/user/login", userc.Login);
return router
}
func HandleNotFound(c *gin.Context) {
global.NewResult(c).Error(404," Resource not found ")
return
}
func Recover(c *gin.Context) {
defer func() {
if r := recover(); r != nil {
// Print error stack information
log.Printf("panic: %v\n", r)
debug.PrintStack()
global.NewResult(c).Error(500," Server internal error ")
}
}()
// Finished loading defer recover, Continue with subsequent interface calls
c.Next()
}7,static/form.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script type="text/javascript" language="JavaScript" src="jquery-1.6.2.min.js"></script>
<script type="text/javascript" language="JavaScript" src="md5.js"></script>
</head>
<body>
<a href="javascript:login('right')">login(right)</a><br/>
<a href="javascript:login('error')">login(error)</a><br/>
<script>
//vars
var appId="wap";
var version="1.0";
// obtain sign
function getsign(appSecret,timestamp,nonce) {
var origin = appId + appSecret + timestamp + nonce + version;
console.log("origin:"+origin);
var sign = hex_md5(origin);
return sign;
}
// visit login This api
// explain : Here are just examples , stay ios/android In development ,appSecret Compile and save in binary form
function login(isright) {
//right secret
var appSecret_right="30c722c6acc64306a88dd93a814c9f0a";
//error secret
var appSecret_error="aabbccdd";
var timestamp = parseInt((new Date()).getTime()/1000);
var nonce = Math.floor(Math.random()*8999)+1000;
var sign = "";
if (isright == 'right') {
sign = getsign(appSecret_right,timestamp,nonce);
} else {
sign = getsign(appSecret_error,timestamp,nonce);
}
var postdata = {
username:"a",
password:"b"
}
$.ajax({
type:"POST",
url:"/user/login",
data:postdata,
// Return the format of the data
datatype: "json",
// Top note function before request
beforeSend: function(request) {
request.setRequestHeader("appId", appId);
request.setRequestHeader("timestamp", timestamp);
request.setRequestHeader("sign", sign);
request.setRequestHeader("nonce", nonce);
},
// Base note function after successful return
success:function(data){
//alert(data.code);
if (data.code == 0) {
alert(' Successful visit ');
} else {
alert("failed:"+data.msg);
}
},
// Base note
complete: function(XMLHttpRequest, textStatus){
//complete
},
// Call the function executed in error
error: function(){
// Request error handling
}
});
}
</script>
</body>
</html>8, Other related codes can be accessed github
Four , Effect test
1, visit html page :
http://127.0.0.1:8080/static/form.htmlreturn :

2, Click the respectively : Test and verify whether it is effective :

Click on error When linking :

5、 ... and , View the version of the library :
module github.com/liuhongdi/digv25
go 1.15
require (
github.com/gin-gonic/gin v1.6.3
)
边栏推荐
- Flutter动态化 | Fair 2.5.0 新版本特性
- Replace the GPU card number when pytorch loads the historical model, map_ Location settings
- PowerPoint 教程,如何在 PowerPoint 中将演示文稿另存为视频?
- 父亲和篮球
- SQL Injection (AJAX/JSON/jQuery)
- Bidirectional linked list (we only need to pay attention to insert and delete functions)
- 编程内功之编程语言众多的原因
- Flutter dynamic | fair 2.5.0 new version features
- Asp.Net Core1.1版本没了project.json,这样来生成跨平台包
- HALCON联合C#检测表面缺陷——HALCON例程autobahn
猜你喜欢

【电脑插入U盘或者内存卡显示无法格式化FAT32如何解决】

掌握Cypress命令行选项,是真正掌握Cypress的基础

Setting up remote links to MySQL on Linux

Flutter dynamic | fair 2.5.0 new version features

Unable to stop it, domestic chips have made another breakthrough, and some links have reached 4nm

Golang — 命令行工具cobra

Road construction issues

使用Tensorflow进行完整的深度神经网络CNN训练完成图片识别案例2

8皇后问题

SQL Injection (AJAX/JSON/jQuery)
随机推荐
太阳底下无新事,元宇宙能否更上层楼?
Can newly graduated European college students get an offer from a major Internet company in the United States?
untiy世界边缘的物体阴影闪动,靠近远点的物体阴影正常
[how to solve FAT32 when the computer is inserted into the U disk or the memory card display cannot be formatted]
Logback log sorting
常见的几种最优化方法Matlab原理和深度分析
Comprehensive evaluation of double chain notes remnote: fast input, PDF reading, interval repetition / memory
Unity render streaming communicates with unity through JS
8 Queen question
Libuv Library - Design Overview (Chinese version)
There is nothing new under the sun. Can the meta universe go higher?
Leetcode-1175.Prime Arrangements
刚毕业的欧洲大学生,就能拿到美国互联网大厂 Offer?
掌握Cypress命令行选项,是真正掌握Cypress的基础
挡不住了,国产芯片再度突进,部分环节已进到4nm
顺序表(C语言实现)
RichView TRVStyle ListStyle 列表样式(项目符号编号)
TensorBoard可视化处理案例简析
pytorch 载入历史模型时更换gpu卡号,map_location设置
[技术发展-24]:现有物联网通信技术特点