Commit aff14312 authored by AWL's avatar AWL

fix: add local upload

parent dcf368ee
# Etapa 1: build da aplicação
FROM node:22-alpine AS builder
# Diretório de trabalho dentro do container
WORKDIR /app
# Copia os arquivos de dependência
COPY package.json package-lock.json ./
# Instala as dependências
RUN npm ci
# Copia o restante dos arquivos
COPY . .
# Build da aplicação Next.js
RUN npm run build
# Etapa 2: imagem final para produção
FROM node:22-alpine
# Diretório de trabalho
WORKDIR /app
# Copia os arquivos necessários do builder
COPY --from=builder /app/public ./public
COPY --from=builder /app/.next ./.next
COPY --from=builder /app/node_modules ./node_modules
COPY --from=builder /app/package.json ./
# Garante que a pasta imgs exista
RUN mkdir -p ./public/imgs
# Expõe a porta padrão
EXPOSE 3000
# Comando para iniciar a aplicação
CMD ["npm", "start"]
\ No newline at end of file
version: '3.9'
services:
nextjs-app:
build: .
ports:
- "3000:3000"
volumes:
- ./imgs:/app/public/imgs
environment:
- NODE_ENV=production
\ No newline at end of file
......@@ -36,6 +36,7 @@
"next-themes": "^0.3.0",
"nodemailer": "^6.10.0",
"nookies": "^2.5.2",
"path": "^0.12.7",
"react": "^18",
"react-day-picker": "^8.10.1",
"react-dom": "^18",
......@@ -3403,6 +3404,19 @@
"node": ">=18.0.0"
}
},
"node_modules/@smithy/middleware-retry/node_modules/uuid": {
"version": "9.0.1",
"resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz",
"integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==",
"funding": [
"https://github.com/sponsors/broofa",
"https://github.com/sponsors/ctavan"
],
"license": "MIT",
"bin": {
"uuid": "dist/bin/uuid"
}
},
"node_modules/@smithy/middleware-serde": {
"version": "4.0.2",
"resolved": "https://registry.npmjs.org/@smithy/middleware-serde/-/middleware-serde-4.0.2.tgz",
......@@ -7451,6 +7465,16 @@
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/path": {
"version": "0.12.7",
"resolved": "https://registry.npmjs.org/path/-/path-0.12.7.tgz",
"integrity": "sha512-aXXC6s+1w7otVF9UletFkFcDsJeO7lSZBPUQhtb5O0xJe8LtYhj/GxldoL09bBj9+ZmE2hNoHqQSFMN5fikh4Q==",
"license": "MIT",
"dependencies": {
"process": "^0.11.1",
"util": "^0.10.3"
}
},
"node_modules/path-exists": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz",
......@@ -7723,6 +7747,15 @@
"node": ">=6.0.0"
}
},
"node_modules/process": {
"version": "0.11.10",
"resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz",
"integrity": "sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==",
"license": "MIT",
"engines": {
"node": ">= 0.6.0"
}
},
"node_modules/prop-types": {
"version": "15.8.1",
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
......@@ -8866,23 +8899,25 @@
}
}
},
"node_modules/util": {
"version": "0.10.4",
"resolved": "https://registry.npmjs.org/util/-/util-0.10.4.tgz",
"integrity": "sha512-0Pm9hTQ3se5ll1XihRic3FDIku70C+iHUdT/W926rSgHV5QgXsYbKZN8MSC3tJtSkhuROzvsQjAaFENRXr+19A==",
"license": "MIT",
"dependencies": {
"inherits": "2.0.3"
}
},
"node_modules/util-deprecate": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
"integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="
},
"node_modules/uuid": {
"version": "9.0.1",
"resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz",
"integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==",
"funding": [
"https://github.com/sponsors/broofa",
"https://github.com/sponsors/ctavan"
],
"license": "MIT",
"bin": {
"uuid": "dist/bin/uuid"
}
"node_modules/util/node_modules/inherits": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz",
"integrity": "sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==",
"license": "ISC"
},
"node_modules/warning": {
"version": "4.0.3",
......
import { s3 } from '@/lib/cloudflare'
import { PutObjectCommand } from '@aws-sdk/client-s3'
import { writeFile } from 'fs/promises'
import path from 'path'
import { NextRequest, NextResponse } from 'next/server'
export async function POST(req: NextRequest) {
......@@ -10,25 +10,20 @@ export async function POST(req: NextRequest) {
return NextResponse.json({ error: 'No file provided' }, { status: 400 })
}
const arrayBuffer = await file.arrayBuffer()
const buffer = Buffer.from(arrayBuffer)
try {
const arrayBuffer = await file.arrayBuffer()
const buffer = new Uint8Array(arrayBuffer)
const fileName = `${Date.now()}-${file.name}`
const fileName = `${Date.now()}-${file.name}`
const filePath = path.join(process.cwd(), 'public', 'imgs', fileName)
try {
await s3.send(
new PutObjectCommand({
Bucket: process.env.NEXT_PUBLIC_CLOUDFLARE_BUCKET!,
Key: fileName,
Body: buffer,
ContentType: file.type,
}),
)
await writeFile(filePath, buffer)
const fileUrl = `https://${process.env.NEXT_PUBLIC_CLOUDFLARE_URL_PUBLIC_BUCKET}/${fileName}`
const fileUrl = `/imgs/${fileName}` // caminho relativo acessível pela tag <img src=...>
return NextResponse.json({ url: fileUrl })
} catch (error) {
console.error('Upload failed:', error)
return NextResponse.json({ error: 'Upload failed' }, { status: 500 })
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment