微信小程序获取步数 Golang解码

1,506 阅读1分钟

看到网上没有相关的完整文章,于是自己记录一下

1. 微信小程序请求后端获取session_key并存储到storageSync()

wx.login()获取code,携带code请求后端,后端调用 auth.code2Session,使用 code 换取 session_key 信息。

然后存储到微信小程序本地或存储到服务端,我这里为了方便存在了本地。

2. 微信小程序获取步数

wx.getWeRunData({
	success:(res) => {
		//得到步数数据,包括encryptedData与iv
        this.decryptedData(res.encryptedData, res.iv);
    }
})

3. 请求后端解析加密数据

decryptedData(encryptedData, iv) {
    let SessionKey = wx.getStorageSync("session_key")
    let data = {
      EncryptedData: encryptedData,
      Iv: iv,
      SessionKey,
    }
    //携带data请求后端相应的接口,代码已省略
    ········
    
    tokenRequest({url, data, header, method}).then(res=>{
      if(res.data.code==0) {
        this.setData({
          step: res.data.data.step,
        })
      }
    })
  },

4. 后端解码

type WeRunCryptDataInput struct {
	EncryptedData 	string		`json:"encryptedData" note:""`
	Iv 				string		`json:"iv" note:""`
	SessionKey 		string		`json:"sessionKey" note:""`
}

type WeRunData struct {
	TimeStamp 	uint64	`json:"timestamp" note:"时间"`
	Step 		uint64	`json:"step" note:"步数"`
}

type WeRunDataList struct {
	StepInfoList	[]*WeRunData		`json:"stepInfoList"`
}

func (s *Data) DecryptWeRunData(argument WeRunCryptDataInput) (WeRunData, business.Error) {
	//解码
	aesKey, err := base64.StdEncoding.DecodeString(argument.SessionKey)
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}
	cipherText, err := base64.StdEncoding.DecodeString(argument.EncryptedData)
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}
	ivBytes, err := base64.StdEncoding.DecodeString(argument.Iv)
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}
	block, err := aes.NewCipher(aesKey)
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}
	mode := cipher.NewCBCDecrypter(block, ivBytes)
	mode.CryptBlocks(cipherText, cipherText)
	cipherText, err = pkcs7Unpad(cipherText, block.BlockSize())
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}

	result := &WeRunDataList{}
	err = json.Unmarshal(cipherText, &result)
	if err != nil {
		return nil, business.NewError(errors.InternalError, err)
	}
    // do something else,例如存储数据
    ···
    //代码已省略
	return result.StepInfoList[30], nil
}

// pkcs7Unpad returns slice of the original data without padding
func pkcs7Unpad(data []byte, blockSize int) ([]byte, error) {
	if blockSize <= 0 {
		return nil, fmt.Errorf("invalid block size")
	}
	if len(data)%blockSize != 0 || len(data) == 0 {
		return nil, fmt.Errorf("invalid PKCS7 data")
	}
	c := data[len(data)-1]
	n := int(c)
	if n == 0 || n > len(data) {
		return nil, fmt.Errorf("invalid padding on input")
	}
	for i := 0; i < n; i++ {
		if data[len(data)-n+i] != c {
			return nil, fmt.Errorf("invalid padding on input")
		}
	}
	return data[:len(data)-n], nil
}