import { Base64Utils, RandomUtils, StringUtils } from "@imengyu/imengyu-utils"; import { hmacSha1Base64 } from "./hmac"; import type { UploaderAction, UploaderItem } from "@/components/form/Uploader"; const client = { region: 'oss-cn-shenzhen', accessKeyId: 'LTAI5t5e7wAQ1FvUA4LCsNs5', accessKeySecret: 'lhF0SimpatPMHNjmjtIKsWsYwTmJhx', bucket: 'minnanwenhua', }; function generatePolicyAndSignature(key: string, accessKeySecret: string) { try { const expiration = new Date(Date.now() + 3600 * 1000).toISOString(); const policyText = { expiration: expiration, conditions: [ ["content-length-range", 0, 10485760 * 256], // 256MB限制 ["starts-with", "$key", key.substring(0, key.lastIndexOf('/') + 1)] ] }; const policyBase64 = Base64Utils.encode(JSON.stringify(policyText)); const signature = hmacSha1(policyBase64, accessKeySecret); return { policy: policyBase64, signature: signature }; } catch (error) { console.error("生成policy和signature失败:", error); throw error; } } function hmacSha1(message: string, key: string) { try { return hmacSha1Base64(message, key); } catch (error) { console.error("HMAC-SHA1签名生成失败:", error); throw error; } } function uploadOSS(uploadPath: string, filePath: string, cancelHandler: { cancel: () => void }, onProgress?: (progress: number) => void) { return new Promise((resolve, reject) => { const key = uploadPath; const { policy, signature } = generatePolicyAndSignature(key, client.accessKeySecret); const formData = { key, policy: policy, OSSAccessKeyId: client.accessKeyId, signature: signature, success_action_status: '200' }; const task = uni.uploadFile({ url: `https://${client.bucket}.${client.region}.aliyuncs.com`, filePath, name: 'file', formData, success: res => { if (res.statusCode === 200 || res.statusCode === 204) { resolve(`https://${client.bucket}.${client.region}.aliyuncs.com/${uploadPath}`) } else { reject(new Error('上传失败' + res.statusCode)) } }, fail: reject, complete: () => {} }) task.onProgressUpdate(({ progress }) => onProgress?.(progress)); cancelHandler.cancel = () => { task.abort(); }; }) } export function useAliOssUploadCo( subPath: string, onFinish?: (res: string, item: UploaderItem) => void ) { return (action: UploaderAction) => { const name = StringUtils.path.getFileName(action.item.filePath); const uploadPath = `${subPath}/${name.split('.')[0]}-${RandomUtils.genNonDuplicateID(6)}.${StringUtils.path.getFileExt(name)}`; const cancelHandler: { cancel: () => void } = { cancel: () => {}, }; uploadOSS(uploadPath, action.item.filePath, cancelHandler,(progress) => { action.onProgress?.(progress) }).then((res) => { action.onFinish?.({ uploadedUrl: res, previewUrl: res, }, '上传成功'); onFinish?.(res, action.item); }).catch((err) => { action.onError?.(err); }); return () => { //取消上传 cancelHandler.cancel(); }; } }