大家好这里是梦兽编程,需要看本Next.js
栏目点击进入Next.js实战开发
使用 Next.js 13 上传文件不需要第三方库,因此可以快速移动并减少捆绑包的大小。您可以使用客户端组件的Fetch和api进行开发 或 React Server 组件来实现这一功能。
点击链接加入群聊梦兽编程交流区交流更多技术golang
,node.js
,vue
,java
,react
。
客户端组件和Api路由
1. 客户端组件
如果您的表单是客户端组件,则应将文件保存为状态,然后使用 fetch 请求上传它。
javascript
'use client'
import { useState } from 'react'
export function UploadForm() {
const [file, setFile] = useState<File>()
const onSubmit = async (e: React.FormEvent<HTMLFormElement>) => {
// 阻止表单提交行为
e.preventDefault()
if (!file) return
try {
const data = new FormData()
data.set('file', file)
const res = await fetch('/api/upload', {
method: 'POST',
body: data
})
// handle the error
if (!res.ok) throw new Error(await res.text())
} catch (e: any) {
// Handle errors here
console.error(e)
}
}
return (
<form onSubmit={onSubmit}>
<input
type="file"
name="file"
onChange={(e) => setFile(e.target.files?.[0])}
/>
<input type="submit" value="Upload" />
</form>
)
}
2.Next.js API Route 下一篇.js API 路由
要处理表单上传,您需要创建一个 API 路由来使用数据并对其执行某些操作。 创建文件 app/api/upload/route.ts
并添加以下代码:
javascript
import { writeFile } from 'fs/promises'
import { NextRequest, NextResponse } from 'next/server'
export async function POST(request: NextRequest) {
const data = await request.formData()
const file: File | null = data.get('file') as unknown as File
if (!file) {
return NextResponse.json({ success: false })
}
const bytes = await file.arrayBuffer()
const buffer = Buffer.from(bytes)
// 这里是你要进行保存的文件目录地址
const path = `/tmp/${file.name}`
await writeFile(path, buffer)
console.log(`open ${path} to see the uploaded file`)
return NextResponse.json({ success: true })
}
当客户端通过 HTTP POST 请求将文件发送到此 API 路由时,此代码会读取该文件,将其保存到服务器的文件系统,并返回指示成功或失败的 JSON 响应。
基于React Server Components 实现上传功能
这里我们需要使用到next.js的server action
javascript
import { writeFile } from 'fs/promises'
import { join } from 'path'
export default function ServerUploadPage() {
async function upload(data: FormData) {
'use server'
const file: File | null = data.get('file') as unknown as File
if (!file) {
throw new Error('No file uploaded')
}
const bytes = await file.arrayBuffer()
const buffer = Buffer.from(bytes)
// 这里是你要进行保存的文件目录地址
const path = join('/', 'tmp', file.name)
await writeFile(path, buffer)
console.log(`open ${path} to see the uploaded file`)
return { success: true }
}
return (
<main>
<h1>React Server Component: Upload</h1>
<form action={upload}>
<input type="file" name="file" />
<input type="submit" value="Upload" />
</form>
</main>
)
}
这就是你需要做的!采用 form 作为 action 服务器操作的属性。该操作处理文件上传的方式与 API 路由一样,但您可以直接在组件中内联整个函数。通过这样做,您的表单无需 JavaScript 即可运行,并且发送到客户端的数据更少。
结语
看完这个文章,你上两种方式都是实现文件上传的功能,实际开发过程中我们还需要进行七牛云、阿里云的存储功能开发,这里就不展开讲解,希望大家可以自己动手尝试修改成其他存储方案的代码逻辑。
我的B站视频号更多视频动态。
「微信公众号订阅[梦兽编程]」
本文使用 markdown.com.cn 排版