pmtool / src /services /attachmentApi.ts
devarshia5's picture
Upload 487 files
d97b8f9 verified
Raw
History Blame Contribute Delete
7.24 kB
import axios from "axios";
import apiClient from '@/lib/api/axios-instance';
import { createHeaders } from '@/lib/api';
import { API_BASE_URL } from "@/config";
// Create API_URL from API_BASE_URL
const API_URL = `${API_BASE_URL}/api`;
export interface Attachment {
attachmentId: number;
fileName: string;
fileType: string;
filePath: string;
entityType: string;
entityId: number;
description?: string;
createdAt?: string;
createdBy?: string;
}
export interface AttachmentCreateRequest {
attachmentId: number;
fileName: string;
fileType: string;
filePath: string;
entityType: string;
entityId: number;
description?: string;
_IFormFile: File;
}
export interface DownloadResult {
blob: Blob;
fileName: string;
contentType: string;
}
export interface DownloadProgressCallback {
(progress: number, totalSize: number): void;
}
export const attachmentApi = {
getAll: async (): Promise<Attachment[]> => {
try {
const response = await apiClient.get(`${API_URL}/Attachments`);
return response.data;
} catch (error) {
console.error("Error fetching all attachments:", error);
throw error;
}
},
getById: async (id: number): Promise<Attachment> => {
try {
const response = await apiClient.get(`${API_URL}/Attachments/${id}`);
return response.data;
} catch (error) {
console.error(`Error fetching attachment with ID ${id}:`, error);
throw error;
}
},
getByEntityTypeAndId: async (entityType: string, entityId: number): Promise<Attachment[]> => {
try {
const response = await apiClient.get(`${API_URL}/Attachments/${entityType}/${entityId}`);
return response.data;
} catch (error) {
console.error(`Error fetching attachments for ${entityType} with ID ${entityId}:`, error);
throw error;
}
},
delete: async (id: number): Promise<boolean> => {
try {
const response = await apiClient.delete(`${API_URL}/Attachments/${id}`);
return response.status === 200;
} catch (error) {
console.error(`Error deleting attachment with ID ${id}:`, error);
throw error;
}
},
upload: async (data: FormData): Promise<Attachment> => {
try {
const response = await apiClient.post(`${API_URL}/Attachments/uploadfile`, data, {
headers: {
'Content-Type': undefined,
},
});
return response.data;
} catch (error) {
console.error("Error uploading attachment:", error);
throw error;
}
},
download: async (id: number, onProgress?: DownloadProgressCallback): Promise<DownloadResult> => {
try {
// First get the attachment info to determine the correct filename
const attachmentInfo = await attachmentApi.getById(id);
// Download the file with the blob response type
const response = await apiClient.get(`${API_URL}/Attachments/download/${id}`, {
responseType: 'blob',
});
// Extract content type from headers or use default
const contentType = response.headers['content-type'] ||
attachmentInfo.fileType ||
'application/octet-stream';
// Extract filename from Content-Disposition header if available
const contentDisposition = response.headers['content-disposition'] || '';
let fileName = attachmentInfo.fileName;
// Try to extract filename from Content-Disposition header
const filenameMatch = contentDisposition.match(/filename[^;=\n]*=((['"]).*?\2|[^;\n]*)/);
if (filenameMatch && filenameMatch[1]) {
const extractedName = filenameMatch[1].replace(/['"]/g, '');
if (extractedName) {
fileName = extractedName;
}
}
console.log(`Downloaded file: ${fileName}, content-type: ${contentType}, size: ${response.data.size} bytes`);
return {
blob: response.data,
fileName,
contentType
};
} catch (error) {
console.error(`Error downloading attachment with ID ${id}:`, error);
throw error;
}
},
// Method to directly trigger a file download
downloadAndSave: async (id: number, onProgress?: DownloadProgressCallback): Promise<void> => {
try {
const result = await attachmentApi.download(id, onProgress);
// Create a URL for the blob
const url = window.URL.createObjectURL(result.blob);
// Create a download link
const link = document.createElement('a');
link.href = url;
link.download = result.fileName;
// Add to document, click and remove
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
// Release the object URL
window.URL.revokeObjectURL(url);
console.log(`File "${result.fileName}" downloaded successfully`);
} catch (error) {
console.error(`Error downloading and saving attachment with ID ${id}:`, error);
throw error;
}
},
// Method to get a temporary view URL for an attachment
getViewUrl: async (id: number): Promise<string> => {
try {
// Get attachment info to check file type
const attachment = await attachmentApi.getById(id);
const fileType = attachment.fileType.toLowerCase();
// Check if it's a viewable file type
const isViewableType =
fileType.includes('image') ||
fileType.includes('pdf') ||
fileType.includes('text') ||
fileType.includes('html') ||
fileType.includes('.jpg') ||
fileType.includes('.jpeg') ||
fileType.includes('.png') ||
fileType.includes('.gif') ||
fileType.includes('.webp') ||
fileType.includes('.pdf') ||
fileType.includes('.txt') ||
fileType.includes('.html');
if (!isViewableType) {
throw new Error(`File type ${fileType} is not supported for preview`);
}
// Download the file as a blob and create a URL
const result = await attachmentApi.download(id);
const url = window.URL.createObjectURL(result.blob);
return url;
} catch (error) {
console.error(`Error creating view URL for attachment with ID ${id}:`, error);
throw error;
}
},
// Check if file is viewable
isViewable: (attachment: Attachment): boolean => {
const fileType = attachment.fileType.toLowerCase();
const fileName = attachment.fileName.toLowerCase();
// Check if it's a viewable file type
return (
fileType.includes('image') ||
fileType.includes('pdf') ||
fileType.includes('text') ||
fileType.includes('html') ||
fileName.endsWith('.jpg') ||
fileName.endsWith('.jpeg') ||
fileName.endsWith('.png') ||
fileName.endsWith('.gif') ||
fileName.endsWith('.webp') ||
fileName.endsWith('.pdf') ||
fileName.endsWith('.txt') ||
fileName.endsWith('.html')
);
}
};