diff --git a/backend/src/middleware/errorHandler.middleware.js b/backend/src/middleware/errorHandler.middleware.js index 163c601..0d72aac 100644 --- a/backend/src/middleware/errorHandler.middleware.js +++ b/backend/src/middleware/errorHandler.middleware.js @@ -57,7 +57,7 @@ const errorHandler = (err, req, res, next) => { const message = error.message || 'Internal Server Error'; res.status(statusCode).json({ - error: true, + error: message, message, ...(config.app.env === 'development' && { stack: err.stack }), }); diff --git a/backend/src/services/minio.service.js b/backend/src/services/minio.service.js index e31c3fd..a7a9c38 100644 --- a/backend/src/services/minio.service.js +++ b/backend/src/services/minio.service.js @@ -100,6 +100,12 @@ class MinIOService { if (error.stderr.includes('Access Denied')) { throw new AppError('Access denied', 403); } + if (error.stderr.includes('already exists')) { + throw new AppError('Resource already exists', 409); + } + if (error.stderr.includes('policy')) { + throw new AppError(`Policy operation failed: ${error.stderr}`, 400); + } } throw new AppError(error.message || 'Command execution failed', 500); @@ -232,9 +238,15 @@ class MinIOService { // Write policy to temp file const policyFile = path.join(this.tempDir, `${policyName}-${Date.now()}.json`); + + // Ensure temp directory exists before writing + await fs.mkdir(this.tempDir, { recursive: true }); await fs.writeFile(policyFile, JSON.stringify(policy, null, 2)); try { + // Verify the file was written + await fs.access(policyFile); + // Create and attach policy await this.executeCommand( `mc admin policy create ${this.alias} ${policyName} ${policyFile}` @@ -328,16 +340,27 @@ class MinIOService { const policyFile = path.join(this.tempDir, `${policyName}-${Date.now()}.json`); try { + // Ensure temp directory exists before writing + await fs.mkdir(this.tempDir, { recursive: true }); + await fs.writeFile(policyFile, typeof policyDocument === 'string' ? policyDocument : JSON.stringify(policyDocument, null, 2) ); + // Verify the file was written + await fs.access(policyFile); + await this.executeCommand( `mc admin policy create ${this.alias} ${policyName} ${policyFile}` ); return { message: 'Policy created successfully', policyName }; + } catch (error) { + // Clean up file if it exists + await fs.unlink(policyFile).catch(() => {}); + throw error; } finally { + // Always try to clean up the temp file await fs.unlink(policyFile).catch(() => {}); } } diff --git a/frontend/src/components/Dashboard/QuickStartWizard.tsx b/frontend/src/components/Dashboard/QuickStartWizard.tsx index db2c4e7..8c6fdfb 100644 --- a/frontend/src/components/Dashboard/QuickStartWizard.tsx +++ b/frontend/src/components/Dashboard/QuickStartWizard.tsx @@ -41,7 +41,7 @@ import { import { useTranslation } from 'react-i18next'; import userService from '../../services/userService'; import policyService from '../../services/policyService'; -import api from '../../services/api'; +import api, { handleApiError } from '../../services/api'; interface QuickStartWizardProps { open: boolean; @@ -219,8 +219,9 @@ const QuickStartWizard: React.FC = ({ setCompletedSetup(results); setActiveStep(steps.length); - } catch (err) { - setError(err instanceof Error ? err.message : t('quickWizard:errors.creationFailed')); + } catch (err: any) { + const errorMessage = handleApiError(err); + setError(errorMessage); setIsCreating(false); } finally { setLoading(false); @@ -297,7 +298,7 @@ const QuickStartWizard: React.FC = ({ value={setupData.userPassword} onChange={(e) => setSetupData({ ...setupData, userPassword: e.target.value })} error={!!error && activeStep === 1} - helperText={error || t('quickWizard:user.passwordHelper')} + helperText={(error && activeStep === 1 ? error : '') || t('quickWizard:user.passwordHelper')} InputProps={{ endAdornment: (