正如聊天中所解释的那样,问题在于,如果缺少标头和签名,则base64解码器无法解码标头和签名。
您只需添加以下代码即可:
if m := len(h_) % 4; m != 0 { h_ += strings.Repeat("=", 4-m) }这是完整的代码:
package mainimport( "strings" "encoding/binary" "errors" "fmt" "log" "encoding/base64" "io/ioutil" "crypto" "crypto/sha256" "crypto/rsa" "bytes" "encoding/json" "net/http" "math/big")func main() { auth_token := "" w := strings.Split(auth_token, ".") h_, s_ := w[0], w[2] if m := len(h_) % 4; m != 0 { h_ += strings.Repeat("=", 4-m) } if m := len(s_) % 4; m != 0 { s_ += strings.Repeat("=", 4-m) } headerOauth, err := base64.URLEncoding.DepreString(h_) res, err := http.Get("https://www.googleapis.com/oauth2/v2/certs") if err != nil { fmt.Println(err) } certs, err := ioutil.ReadAll(res.Body) res.Body.Close() if err != nil { fmt.Println(err) } //extract kid from token header var header interface{} err = json.Unmarshal([]byte(string(headerOauth)), &header) token_kid := header.(map[string]interface{})["kid"] fmt.Println("By 1") //get modulus and exponent from the cert var goCertificate interface{} err = json.Unmarshal(certs, &goCertificate) //k := goCertificate.(map[string]interface{})[token_kid.(string)] k := goCertificate.(map[string]interface{})["keys"] ///*mod & exp part j := k.([]interface{}) x := j[0] if j[0].(map[string]interface{})["kid"] == token_kid { x = j[0] }else{ if j[1].(map[string]interface{})["kid"] == token_kid { x = j[1] }else{ errors.New("Token is not valid, kid from token and certificate don't match") } } h := x.(map[string]interface{})["n"] g := x.(map[string]interface{})["e"] //build the google pub key nStr := h.(string) decN, err := base64.URLEncoding.DepreString(nStr) if err != nil { fmt.Println(err) return } n := big.NewInt(0) n.SetBytes(decN) eStr := g.(string) decE, err := base64.URLEncoding.DepreString(eStr) if err != nil { fmt.Println(err) return } var eBytes []byte if len(decE) < 8 { eBytes = make([]byte, 8-len(decE), 8) eBytes = append(eBytes, decE...) } else { eBytes = decE } eReader := bytes.NewReader(eBytes) var e uint64 err = binary.Read(eReader, binary.BigEndian, &e) if err != nil { log.Println(err) return } pKey := rsa.PublicKey{N: n, E: int(e)} //inblockOauth := base64.URLEncoding.DepreString(w[1]) toHash := w[0] + "." + w[1] digestOauth, err := base64.URLEncoding.DepreString(s_) hasherOauth := sha256.New() hasherOauth.Write([]byte(toHash)) // verification of the signature err = rsa.VerifyPKCS1v15(&pKey,crypto.SHA256,hasherOauth.Sum(nil),digestOauth) if err != nil { fmt.Printf("Error verifying key %s",err.Error()) } fmt.Printf("OK!")}


