diff --git a/src/api/controls/JobControl.test.ts b/src/api/controls/JobControl.test.ts index f15844f..0398eef 100644 --- a/src/api/controls/JobControl.test.ts +++ b/src/api/controls/JobControl.test.ts @@ -1,4 +1,5 @@ import axios from 'axios'; +import * as fs from 'fs'; import { JobControl } from './JobControl'; import { FiveMClient } from '../../FiveMClient'; import { Control } from './Control'; @@ -6,7 +7,9 @@ import { Endpoints } from '../server/Endpoints'; import { AD5XMaterialMapping } from '../../models/ff-models'; jest.mock('axios'); +jest.mock('fs'); const mockedAxios = axios as jest.Mocked; +const mockedFs = fs as jest.Mocked; jest.mock('./Control'); @@ -106,6 +109,47 @@ describe('JobControl', () => { }); }); + describe('uploadFile', () => { + const testFilePath = '/path/to/test.gcode'; + const testFileSize = 1024; + + beforeEach(() => { + // @ts-ignore + mockedFs.promises = { + access: jest.fn().mockResolvedValue(undefined), + stat: jest.fn().mockResolvedValue({ size: testFileSize } as fs.Stats) + } as any; + // @ts-ignore + fs.promises = mockedFs.promises; + mockedFs.createReadStream.mockReturnValue('dummy-stream' as any); + }); + + it('should return false if file does not exist', async () => { + // @ts-ignore + mockedFs.promises.access.mockRejectedValue(new Error('File not found')); + + const result = await jobControl.uploadFile(testFilePath, false, false); + + expect(result).toBe(false); + expect(mockedFs.promises.access).toHaveBeenCalledWith(testFilePath); + }); + + it('should upload file successfully', async () => { + mockedAxios.post.mockResolvedValue({ + status: 200, + data: { code: 0, message: 'Success' } + }); + + const result = await jobControl.uploadFile(testFilePath, false, false); + + expect(result).toBe(true); + expect(mockedFs.promises.access).toHaveBeenCalledWith(testFilePath); + expect(mockedFs.promises.stat).toHaveBeenCalledWith(testFilePath); + expect(mockedFs.createReadStream).toHaveBeenCalledWith(testFilePath); + expect(mockedAxios.post).toHaveBeenCalled(); + }); + }); + describe('printLocalFile', () => { it('should print local file with new firmware version', async () => { mockFiveMClient.firmVer = '3.1.3'; diff --git a/src/api/controls/JobControl.ts b/src/api/controls/JobControl.ts index c2aa86d..8e75a9c 100644 --- a/src/api/controls/JobControl.ts +++ b/src/api/controls/JobControl.ts @@ -99,12 +99,14 @@ export class JobControl { * @returns A Promise that resolves to true if the file upload (and optional print start) is successful, false otherwise. */ public async uploadFile(filePath: string, startPrint: boolean, levelBeforePrint: boolean): Promise { - if (!fs.existsSync(filePath)) { + try { + await fs.promises.access(filePath); + } catch { console.error(`UploadFile error: File not found at ${filePath}`); return false; } - const stats = fs.statSync(filePath); + const stats = await fs.promises.stat(filePath); const fileSize = stats.size; const fileName = path.basename(filePath); @@ -217,12 +219,14 @@ export class JobControl { } // Validate file exists - if (!fs.existsSync(params.filePath)) { + try { + await fs.promises.access(params.filePath); + } catch { console.error(`UploadFileAD5X error: File not found at ${params.filePath}`); return false; } - const stats = fs.statSync(params.filePath); + const stats = await fs.promises.stat(params.filePath); const fileSize = stats.size; const fileName = path.basename(params.filePath);