132 lines
3.2 KiB
JavaScript
132 lines
3.2 KiB
JavaScript
/**
|
|
* Copyright (c) 2026 Niolla
|
|
* All rights reserved.
|
|
*
|
|
* This source code is proprietary and confidential.
|
|
* Unauthorized copying, modification, distribution, or use
|
|
* of this file, via any medium, is strictly prohibited.
|
|
*/
|
|
|
|
// app/controllers/activity.controller.js
|
|
|
|
const { uploadToS3, getSignedFileUrl } = require("../utils/s3Upload.utill");
|
|
const { log } = require("../utils/consoleLog.utill");
|
|
|
|
const db = require("../models");
|
|
const Upload = db.Upload;
|
|
const Assets = db.Assets;
|
|
|
|
// Constants
|
|
const MAX_IMAGE_SIZE = 3 * 1024 * 1024; // 3MB
|
|
const MAX_PDF_SIZE = 5 * 1024 * 1024; // 5MB
|
|
|
|
const isValidFileType = (mimetype) => {
|
|
return mimetype.startsWith("image/") || mimetype === "application/pdf";
|
|
};
|
|
|
|
const isValidFileSize = (mimetype, size) => {
|
|
if (mimetype.startsWith("image/")) return size <= MAX_IMAGE_SIZE;
|
|
if (mimetype === "application/pdf") return size <= MAX_PDF_SIZE;
|
|
return false;
|
|
};
|
|
|
|
exports.uploadFile = async (req, res) => {
|
|
try {
|
|
// 1. Check file exists
|
|
if (!req.file) {
|
|
return res.status(400).json({
|
|
success: false,
|
|
message: "No file uploaded",
|
|
});
|
|
}
|
|
|
|
const { mimetype, size, originalname } = req.file;
|
|
|
|
// 2. Validate file type
|
|
if (!isValidFileType(mimetype)) {
|
|
return res.status(400).json({
|
|
success: false,
|
|
message: "Only images and PDFs are allowed",
|
|
});
|
|
}
|
|
|
|
// 3. Validate file size
|
|
if (!isValidFileSize(mimetype, size)) {
|
|
return res.status(400).json({
|
|
success: false,
|
|
message: mimetype.startsWith("image/")
|
|
? "Image too large (max 1MB)"
|
|
: "PDF too large (max 5MB)",
|
|
});
|
|
}
|
|
|
|
log("File validation passed:", {
|
|
mimetype,
|
|
size,
|
|
originalname,
|
|
use_for: req.body.use_for,
|
|
});
|
|
|
|
// 4. Upload to S3
|
|
const fileKey = await uploadToS3(req.file, req.body.use_for);
|
|
|
|
const fileUrl = await getSignedFileUrl(fileKey);
|
|
|
|
// 5. Save to DB
|
|
const uploadData = {
|
|
file_path: fileKey,
|
|
file_type: mimetype,
|
|
file_size: size,
|
|
original_name: originalname,
|
|
use_for: req.body.use_for || null,
|
|
uploaded_by: req.user?.id || null,
|
|
};
|
|
|
|
const newUpload = await Upload.create(uploadData);
|
|
|
|
newUpload.dataValues.file_url = fileUrl; // Add URL to response
|
|
|
|
// 6. Response
|
|
return res.status(201).json({
|
|
success: true,
|
|
message: "File uploaded successfully",
|
|
data: newUpload,
|
|
});
|
|
} catch (error) {
|
|
console.error("Upload Controller Error:", error);
|
|
|
|
return res.status(500).json({
|
|
success: false,
|
|
message: "Failed to upload file",
|
|
error: process.env.NODE_ENV === "development" ? error.message : undefined,
|
|
});
|
|
}
|
|
};
|
|
|
|
// Get Uploaded File URL
|
|
exports.getFileUrl = async (req, res) => {
|
|
try {
|
|
const { id } = req.params;
|
|
|
|
const uploadRecord = await Upload.findByPk(id);
|
|
|
|
if (!uploadRecord) {
|
|
return res.status(404).json({
|
|
success: false,
|
|
message: "File not found",
|
|
});
|
|
}
|
|
|
|
const fileUrl = await getSignedFileUrl(uploadRecord.file_path);
|
|
|
|
return res.status(200).json({
|
|
success: true,
|
|
message: "File URL retrieved successfully",
|
|
data: {
|
|
id: uploadRecord.id,
|
|
file_url: fileUrl,
|
|
},
|
|
});
|
|
} catch (error) {}
|
|
};
|