package oss import ( "crypto/hmac" "crypto/sha1" "encoding/base64" "encoding/json" "fmt" "regexp" "strings" "time" ) // IsOSSDomain 判断 CDN 域名是否为阿里云 OSS(据此决定返回 OSS 还是七牛凭证) func IsOSSDomain(cdnDomain string) bool { return strings.Contains(strings.ToLower(cdnDomain), "aliyuncs.com") } // ParseOSSEndpoint 从 CDN 域名解析 OSS endpoint,如 oss-cn-beijing.aliyuncs.com -> oss-cn-beijing func ParseOSSEndpoint(cdnDomain string) string { // oss-cn-beijing.aliyuncs.com -> oss-cn-beijing re := regexp.MustCompile(`^([a-z0-9-]+)\.aliyuncs\.com$`) m := re.FindStringSubmatch(strings.TrimSpace(strings.ToLower(cdnDomain))) if len(m) >= 2 { return m[1] } return "oss-cn-beijing" } // PostPolicy 生成 OSS PostObject 所需的 policy 和 signature // bucket: 桶名, endpoint: 如 oss-cn-beijing, key: 对象 key, accessKeySecret: 密钥, expireSeconds: 有效期 func PostPolicy(bucket, endpoint, key, accessKeySecret string, expireSeconds int) (policyBase64, signature string, err error) { if expireSeconds <= 0 { expireSeconds = 300 } expiration := time.Now().Add(time.Duration(expireSeconds) * time.Second).UTC() expirationStr := expiration.Format("2006-01-02T15:04:05.000Z") keyPrefix := key if idx := strings.LastIndex(key, "/"); idx >= 0 { keyPrefix = key[:idx+1] } if keyPrefix == "" { keyPrefix = "uploads/" } policy := map[string]interface{}{ "expiration": expirationStr, "conditions": []interface{}{ []interface{}{"content-length-range", 0, 10 * 1024 * 1024}, // 10MB []interface{}{"starts-with", "$key", keyPrefix}, }, } policyJSON, err := json.Marshal(policy) if err != nil { return "", "", err } policyBase64 = base64.StdEncoding.EncodeToString(policyJSON) mac := hmac.New(sha1.New, []byte(accessKeySecret)) mac.Write([]byte(policyBase64)) signature = base64.StdEncoding.EncodeToString(mac.Sum(nil)) return policyBase64, signature, nil } // UploadHost 返回 OSS PostObject 的完整上传地址 func UploadHost(bucket, endpoint string) string { return fmt.Sprintf("https://%s.%s.aliyuncs.com", bucket, endpoint) }