Go SDK 您可使用开源CloudEvents Go SDK发布事件。 前提条件 1. 您已下载Goland等Go研发IDE。 2. 在go.mod中加入依赖。 plaintext require ( github.com/cloudevents/sdkgo/v2 v2.15.1 github.com/google/uuid v1.1.1 ) // 然后执行更新依赖 go mod tidy go mod vendor 注:sdkgo可参考使用版本2.15.1。 签名生成工具 示例代码如下: plaintext package main import ( "bytes" "crypto/hmac" "crypto/sha1" "encoding/base64" "hash" "io" "sort" "strings" ) // Request is used wrap http request type Request struct { Protocol string Port int Method string Pathname string Domain string Headers map[string]string Query map[string]string } // NewRequest is used shortly create Request func NewRequest() (req Request) { return &Request{ Headers: map[string]string{}, Query: map[string]string{}, } } func String(a string) string { return &a } func StringValue(a string) string { if a nil { return "" } return a } type Sorter struct { Keys []string Vals []string } func newSorter(m map[string]string) Sorter { hs : &Sorter{ Keys: make([]string, 0, len(m)), Vals: make([]string, 0, len(m)), } for k, v : range m { hs.Keys append(hs.Keys, k) hs.Vals append(hs.Vals, v) } return hs } // Sort is an additional function for function SignHeader. func (hs Sorter) Sort() { sort.Sort(hs) } // Len is an additional function for function SignHeader. func (hs Sorter) Len() int { return len(hs.Vals) } // Less is an additional function for function SignHeader. func (hs Sorter) Less(i, j int) bool { return bytes.Compare([]byte(hs.Keys[i]), []byte(hs.Keys[j])) < 0 } // Swap is an additional function for function SignHeader. func (hs Sorter) Swap(i, j int) { hs.Vals[i], hs.Vals[j] hs.Vals[j], hs.Vals[i] hs.Keys[i], hs.Keys[j] hs.Keys[j], hs.Keys[i] } / Get the string to be signed according to request @param request which contains signed messages @return the signed string / func GetStringToSign(request Request) (result string) { return String(getStringToSign(request)) } func getStringToSign(request Request) string { resource : StringValue(request.Pathname) queryParams : request.Query // sort QueryParams by key var queryKeys []string for key : range queryParams { queryKeys append(queryKeys, key) } sort.Strings(queryKeys) tmp : "" for i : 0; i < len(queryKeys); i++ { queryKey : queryKeys[i] tmp tmp + "&" + queryKey + "" + StringValue(queryParams[queryKey]) } if tmp ! "" { tmp strings.TrimLeft(tmp, "&") resource resource + "?" + tmp } return getSignedStr(request, resource) } func getSignedStr(req Request, canonicalizedResource string) string { temp : make(map[string]string) for k, v : range req.Headers { if strings.HasPrefix(strings.ToLower(k), "xceb") { temp[strings.ToLower(k)] StringValue(v) } } hs : newSorter(temp) // Sort the temp by the ascending order hs.Sort() // Get the canonicalizedOSSHeaders canonicalizedHeaders : "" for i : range hs.Keys { canonicalizedHeaders + hs.Keys[i] + ":" + hs.Vals[i] + "n" } // Give other parameters values // when sign URL, date is expires date : StringValue(req.Headers["date"]) contentType : StringValue(req.Headers["contenttype"]) contentMd5 : StringValue(req.Headers["contentmd5"]) signStr : StringValue(req.Method) + "n" + contentMd5 + "n" + contentType + "n" + date + "n" + canonicalizedHeaders + canonicalizedResource return signStr } func GetSignature(stringToSign string, secret string) (result string) { h : hmac.New(func() hash.Hash { return sha1.New() }, []byte(StringValue(secret))) io.WriteString(h, StringValue(stringToSign)) signedStr : base64.StdEncoding.EncodeToString(h.Sum(nil)) return String(signedStr) }