在Vue3+TypeScript中将文件URL转Base64的三种方法
作者:BillKu
这篇文章详细介绍了在Vue3项目中将blob URL转换为Base64格式的三种方法,包括使用FileReader、完整的Vue3组件示例以及使用axios的方案,重点说明了转换过程、性能考虑、错误处理以及后端接收等方面的关键点,需要的朋友可以参考下
在 Vue3 项目中,你已经有了 blob URL,需要将其转换为 Base64 格式。以下是完整的解决方案:
方法一:使用 FileReader
import { ref } from 'vue'
// 将单个 blob URL 转换为 Base64
const blobUrlToBase64 = async (blobUrl) => {
try {
// 1. 通过 fetch 获取 blob 数据
const response = await fetch(blobUrl)
const blob = await response.blob()
// 2. 使用 FileReader 转换为 Base64
return new Promise((resolve, reject) => {
const reader = new FileReader()
reader.onload = () => {
// 移除 data URL 前缀,只保留纯 Base64 数据
const base64 = reader.result.split(',')[1]
resolve(base64)
}
reader.onerror = reject
reader.readAsDataURL(blob)
})
} catch (error) {
console.error('转换失败:', error)
throw error
}
}
// 批量转换多个 blob URL
const convertAllToBase64 = async (blobUrlList) => {
const base64Promises = blobUrlList.map(url => blobUrlToBase64(url))
return await Promise.all(base64Promises)
}
// 在组件中使用
const imageBase64Datas = [
'blob:http://localhost:5173/3125cc04-797d-4736-8e25-cbcee07a05ba',
'blob:http://localhost:5173/0409476c-a2d0-4021-b614-825fadac4e96'
]
// 转换并发送到后端
const handleUpload = async () => {
try {
const base64List = await convertAllToBase64(imageBase64Datas)
// 发送到后端
const response = await fetch('/api/upload', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
images: base64List
})
})
if (response.ok) {
console.log('上传成功')
}
} catch (error) {
console.error('上传失败:', error)
}
}方法二:完整的 Vue3 组件示例
<template>
<div>
<button @click="convertAndUpload" :disabled="loading">
{{ loading ? '转换中...' : '上传图片' }}
</button>
<div v-if="error" class="error">{{ error }}</div>
</div>
</template>
<script setup>
import { ref } from 'vue'
const props = defineProps({
imageBase64Datas: {
type: Array,
required: true
}
})
const loading = ref(false)
const error = ref('')
// 转换单个 blob URL 为 Base64
const blobToBase64 = (blobUrl) => {
return new Promise((resolve, reject) => {
fetch(blobUrl)
.then(response => response.blob())
.then(blob => {
const reader = new FileReader()
reader.onloadend = () => {
const base64 = reader.result.split(',')[1]
resolve({
base64,
mimeType: blob.type,
size: blob.size,
filename: `image_${Date.now()}.${blob.type.split('/')[1]}`
})
}
reader.onerror = reject
reader.readAsDataURL(blob)
})
.catch(reject)
})
}
// 转换所有图片并上传
const convertAndUpload = async () => {
if (!props.imageBase64Datas.length) return
loading.value = true
error.value = ''
try {
// 批量转换所有 blob URL
const conversionPromises = props.imageBase64Datas.map(blobToBase64)
const base64Images = await Promise.all(conversionPromises)
console.log('转换后的 Base64 数据:', base64Images)
// 发送到后端
await sendToBackend(base64Images)
} catch (err) {
error.value = `转换失败: ${err.message}`
console.error('转换错误:', err)
} finally {
loading.value = false
}
}
// 发送数据到后端
const sendToBackend = async (images) => {
try {
const response = await fetch('/api/upload/images', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
images: images,
uploadTime: new Date().toISOString()
})
})
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`)
}
const result = await response.json()
console.log('上传成功:', result)
} catch (err) {
throw new Error(`上传失败: ${err.message}`)
}
}
</script>方法三:使用 axios(如果项目中使用 axios)
import axios from 'axios'
// 使用 axios 的版本
const blobToBase64WithAxios = async (blobUrl) => {
try {
const response = await axios.get(blobUrl, {
responseType: 'blob'
})
return new Promise((resolve, reject) => {
const reader = new FileReader()
reader.onload = () => {
const base64 = reader.result.split(',')[1]
resolve(base64)
}
reader.onerror = reject
reader.readAsDataURL(response.data)
})
} catch (error) {
console.error('转换失败:', error)
throw error
}
}
// 上传到后端
const uploadBase64Images = async (base64List) => {
try {
const response = await axios.post('/api/upload', {
images: base64List
}, {
headers: {
'Content-Type': 'application/json'
}
})
return response.data
} catch (error) {
console.error('上传失败:', error)
throw error
}
}关键点说明
转换过程:
- 使用
fetch获取 blob URL 对应的实际数据 - 通过
FileReader将 blob 转换为 data URL - 从 data URL 中提取纯 Base64 部分
性能考虑:
- 大文件转换可能会影响性能
- 可以考虑分片上传或压缩图片
错误处理:
- 添加适当的错误处理
- 提供用户反馈
后端接收:
- 确保后端能够接收 Base64 字符串
- 可能需要同时发送文件类型信息
选择适合你项目需求的方法即可。方法一提供了最基础的实现,方法二提供了完整的 Vue3 组件示例。
实例代码:
src\views\resources\emergency\comps\EmergencyInDialog.vue
// 确定
const onConfirmClick = async () => {
// 预防性检查,导入期间,点击确定不执行任何操作
if (tableLoading.value) {
ElMessage.warning("正在导入,请等待!");
return;
}
// 检查
if (!check()) {
return;
}
// 遍历选集,处理每个元素的imageBase64Datas,将每个 blob URL 转换为 Base64,回写到 imageBase64Datas
for (const item of tableSelection.value) {
if (item.imageBase64Datas && item.imageBase64Datas.length > 0) {
try {
// 转换 blob URL 为 Base64
const base64Promises = item.imageBase64Datas.map(async (blobUrl) => {
try {
// 返回 blob 数据
return await fileUrlToBase64(blobUrl);
} catch (error) {
console.error(`转换 blob URL 失败: ${blobUrl}`, error);
// 返回 null,因为用的是map必须有返回,如果单个转换失败,不中断整个流程
return null;
}
});
// 等待所有图片转换完成
const base64Results = await Promise.all(base64Promises);
// 过滤掉转换失败的结果,并更新到原数据中
item.imageBase64Datas = base64Results.filter(
(result): result is string => result !== null && result !== undefined
) as string[];
} catch (error) {
console.error(`处理项目 ${item.id} 的图片数据失败:`, error);
// 如果整个项目转换失败,清空图片数据,避免影响后续流程
item.imageBase64Datas = [];
}
} else {
// 如果没有图片数据,确保字段存在且为空数组
item.imageBase64Datas = [];
}
}
// 生成应急物资
await store.fetchGenerateEmergency(tableSelection.value);
// 删除确定的选集数据
deleteConfirmData();
// 关闭模态框
closeDialog();
};src\utils\fileUtils.ts
/**
* 将文件url转换为blob
* @param fileUrl
* @returns blob
*/
export const fileUrlToBlob = async (fileUrl: string): Promise<Blob> => {
const response = await fetch(fileUrl);
return await response.blob();
};
/**
* 将Blob转换为Base64
* @param blob blob数据
* @returns Base64编码字符串
*/
export const blobToBase64 = (blob: Blob): Promise<string> => {
return new Promise((resolve, reject) => {
const reader = new FileReader();
reader.readAsDataURL(blob);
reader.onload = () => resolve(reader.result as string);
reader.onerror = (error) => reject(error);
});
};
/**
* 将文件(类型为FiLe或Blob)转换为Base64
* @param file 文件
* @returns Base64编码字符串
*/
export const fileToBase64 = (file: File | Blob): Promise<string> => {
return new Promise((resolve, reject) => {
const reader = new FileReader();
reader.readAsDataURL(file);
reader.onload = () => resolve(reader.result as string);
reader.onerror = (error) => reject(error);
});
};
/**
* 将文件url转换为Base64
* @param fileUrl
* @returns
*/
export const fileUrlToBase64 = async (fileUrl: string): Promise<string | null> => {
const file = await fileUrlToBlob(fileUrl);
return await fileToBase64(file);
};以上就是在Vue3+TypeScript中将文件URL转Base64的三种方法的详细内容,更多关于Vue3 TypeScript文件URL转Base64的资料请关注脚本之家其它相关文章!
