Files
Iris_back/src/drive/drive.service.ts
T
evenegas 963ec5a765 changes
2026-01-21 10:53:53 -06:00

193 lines
4.7 KiB
TypeScript

// src/drive/drive.service.ts
import {
BadRequestException,
Injectable,
InternalServerErrorException,
} from '@nestjs/common';
import { google } from 'googleapis';
import * as fs from 'fs';
@Injectable()
export class DriveService {
private SCOPES = ['https://www.googleapis.com/auth/drive'];
private loadCredentials() {
try {
const oAuth2Client = new google.auth.OAuth2(
process.env.CLIENT_ID,
process.env.CLIENT_SECRET,
);
oAuth2Client.setCredentials({
refresh_token: process.env.REFRESH_TOKEN,
});
return oAuth2Client;
} catch (err) {
throw new InternalServerErrorException(
'Error al cargar credenciales de Google Drive',
);
}
}
async list(pageToken = '') {
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
try {
const res = await drive.files.list({
corpora: 'user',
supportsAllDrives: true,
includeItemsFromAllDrives: true,
spaces: 'drive',
pageSize: 1000,
pageToken,
orderBy: 'name',
});
return res.data;
} catch (err) {
throw new InternalServerErrorException(
'Error al listar archivos: ' + err.message,
);
}
}
async deleteFile(fileId: string) {
if (fileId === process.env.CARPETA) {
throw new BadRequestException(
'No se puede eliminar este archivo/carpeta.',
);
}
console.log('Eliminando archivo de Drive, ID:', fileId);
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
try {
return await drive.files.delete({ fileId });
} catch (err) {
console.error('Error al eliminar archivo de Drive:', err.message);
return 0;
}
}
async uploadFile(
filePath: string,
name: string,
mimeType: string,
parent: string,
) {
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
const requestBody = {
name,
parents: [parent],
};
const media = {
mimeType,
body: fs.createReadStream(filePath),
};
try {
const res = await drive.files.create({
requestBody,
media,
fields: 'id',
supportsAllDrives: true,
});
fs.unlinkSync(filePath);
console.log('Archivo subido a Drive, ID:', res.data.id);
return res.data.id!;
} catch (err) {
throw new InternalServerErrorException(
'Error al subir archivo: ' + err.message,
);
}
}
async mkDir(name: string): Promise<string> {
if (!name) {
throw new BadRequestException('Nombre de carpeta inválido');
}
if (!process.env.CARPETA) {
throw new InternalServerErrorException('CARPETA no configurada');
}
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
const requestBody = {
name,
mimeType: 'application/vnd.google-apps.folder',
parents: [process.env.CARPETA],
};
try {
const res = await drive.files.create({
requestBody,
fields: 'id',
supportsAllDrives: true,
});
if (!res.data.id) {
throw new BadRequestException('No se pudo crear la carpeta');
}
return res.data.id;
} catch (err) {
throw new InternalServerErrorException(
'Error al crear carpeta: ' + err.message,
);
}
}
async update(fileId: string, addParents: string, removeParents: string) {
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
try {
const res = await drive.files.update({
fileId,
addParents,
removeParents,
supportsAllDrives: true,
});
return res.data;
} catch (err) {
throw new InternalServerErrorException(
'Error al actualizar archivo: ' + err.message,
);
}
}
async folder(numeroCuenta: string): Promise<string> {
if (!process.env.CARPETA) {
throw new InternalServerErrorException('CARPETA no configurada');
}
const authClient = this.loadCredentials();
const drive = google.drive({ version: 'v3', auth: authClient });
const res = await drive.files.list({
q: `
mimeType='application/vnd.google-apps.folder'
and name='${numeroCuenta}'
and '${process.env.CARPETA}' in parents
and trashed=false
`,
fields: 'files(id, name)',
supportsAllDrives: true,
includeItemsFromAllDrives: true,
});
if (res.data.files?.length) {
return res.data.files[0].id!;
}
return this.mkDir(numeroCuenta);
}
}