首页
归档
笔记
树洞
搜索
友言

文章详情

Interesting People Record Interesting.

/ JavaScript / 文章详情

SM.MS 通过api上传图片的方法

Sonder
2024-08-10
4055字
10分钟
浏览 (572)

上传图片

复制代码
/**
 * 压缩图片
 */
import Compressor from 'compressorjs'
export function comporessImgToTargetSize(file, targetSize) {
    return new Promise((resolve, reject) => {
        if (!(file instanceof File) && !(file instanceof Blob)) {
            reject(new Error('Invalid input: not a File or Blob object.'))
            return
        }
        compressImg(file, targetSize)
            .then((res) => {
                resolve(res)
            })
            .catch((err) => {
                reject(err)
            })
    })
}
async function compressImg(file) {
    let currentFile = file
    let currentSize = file.size
    let quality = 0.6
    let isError = false
    try {
        await new Promise((resolve1, reject1) => {
            new Compressor(currentFile, {
                quality,
                success(result) {
                    currentFile = result
                    currentSize = result.size
                    resolve1()
                },
                error(err) {
                    reject1(err)
                }
            })
        })
    } catch (error) {
        console.error('compressImg=>压缩失败', error)
        isError = true
    }
    return currentFile
}
/**
 * smms 图床,多图上传
 * @param {*} files 图片列表
 * @returns
Nginx 要做代理转发
location ^~/api/v2/upload {
    proxy_ssl_server_name on;
    proxy_pass https://sm.ms/api/v2/upload;
    proxy_method POST;
}
 *
 */
export async function smmsMultipartUpload(files) {
    const promises = []
    for (let i = 0; i < files.length; i++) {
        /**
         * 压缩图片
         */
        const comporessFile = await comporessImgToTargetSize(files[i])
        if (!comporessFile.type.match('image.*')) {
            continue
        }
        const accessKey = useRuntimeConfig().public.smmsToken
        promises.push(
            new Promise((resolve, reject) => {
                const headers = {
                    Authorization: accessKey
                }
                const data = new FormData()
                data.append('smfile', comporessFile)
                data.append('format', 'json')
                fetch('/api/v2/upload', {
                    method: 'POST',
                    mode: 'cors',
                    headers,
                    referrer: '',
                    body: data
                })
                    .then((response) => response.json())
                    .then((res) => {
                        if (res.success) {
                            return resolve({
                                url: res.data.url,
                                delete: res.data.delete
                            })
                        }
                        return reject(res.message)
                    })
                    .catch((error) => {
                        return reject(error || 'Failed to connect to sm.ms host')
                    })
            })
        )
    }
    return await Promise.all(promises)
}

/**
 * 删除图片
 * 使用 hash
 */
export async function smmsDeleteImg(hash) {
    const url = `/api/v2/delete/${hash}`
    const headers = {
        Authorization: useRuntimeConfig().public.smmsToken
    }
    const response = await fetch(url, {
        headers
    })
    return response.json()
}

开发时添加解决跨域的代码

开发的时候在 vite.config.js 里面添加解决跨域的代码:

复制代码
server: {
   proxy: {
       '/api/v2/upload': {
           target: 'https://sm.ms',
           changeOrigin: true
       },
       '/api/v2/delete': {
           target: 'https://sm.ms',
           changeOrigin: true
       }
   }
},

打包上线后通过 nginx 接口转发

复制代码
location ^~/api/v2/upload {
    proxy_ssl_server_name on;
    proxy_pass https://sm.ms/api/v2/upload;
    proxy_method POST;
}

location ^~/api/v2/delete {
    proxy_ssl_server_name on;
    proxy_pass https://sm.ms/api/v2/delete;
    proxy_method POST;
}

作者不建议用前端直接请求接口

经过实战,发现通过前端上传的话,非常慢。问了 SMMS 站长,他的回答是:接口本来就不是给前端用的

下一篇 / 解决在VScode中配置Prettier不生效

🎯 相关文章

💡 推荐文章

🕵️‍♂️ 评论 (0)